-
Notifications
You must be signed in to change notification settings - Fork 0
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[WEAV-72] 내 프로필 입력 일부 UI 구현 #26
Conversation
* [WEAV-73] 프로필 입력 - 성별선택 뷰 구현 * [WEAV-73] 오타수정
Walkthrough이 변경 사항은 Changes
Possibly related PRs
Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media? 🪧 TipsChatThere are 3 ways to chat with CodeRabbit:
Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments. CodeRabbit Commands (Invoked using PR comments)
Other keywords and placeholders
CodeRabbit Configuration File (
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 14
🧹 Outside diff range and nitpick comments (15)
Projects/Features/SignUp/Sources/AuthAgreement/AuthAgreementView.swift (1)
31-33
: 변경 사항이 적절해 보입니다.네비게이션 로직이 간소화되어 사용자 경험이 개선되었습니다.
AppCoordinator
를 통한 루트 뷰 변경은 앱의 아키텍처와 일관성이 있습니다.다만, 코드의 가독성을 높이기 위해 다음과 같이 버튼 액션을 별도의 메서드로 추출하는 것을 고려해보세요:
private func navigateToAuthGreeting() { AppCoordinator.shared.changeRootView(.signUp(.authGreeting)) }그리고 버튼에서 이 메서드를 호출하도록 변경할 수 있습니다:
CTABottomButton(title: "다음", action: navigateToAuthGreeting)이렇게 하면
body
프로퍼티의 복잡성을 줄이고 코드의 의도를 더 명확하게 표현할 수 있습니다.Projects/App/Sources/Navigation/NavigationStack.swift (1)
30-38
: LGTM! 새로운 케이스들이 잘 추가되었습니다.새로운 케이스들이 PR 목표와 일치하며 기존 코드 구조를 잘 따르고 있습니다. 이는 성별 입력, 생년 입력, 이름 입력에 대한 UI 구현을 잘 반영하고 있습니다.
가독성을 높이기 위해 각 케이스 그룹 사이에 빈 줄을 추가하는 것을 고려해 보세요. 예를 들어:
case .authAgreement: AuthAgreementView() case .authGreeting: AuthGreetingView() case .authProfileGender: AuthProfileGenderInputView() case .authProfileAge: AuthProfileAgeInputView() case .authName: AuthNameInputView()이렇게 하면 각 기능 그룹을 시각적으로 구분하기 쉬워집니다.
Projects/Core/CommonKit/Sources/Path/PathTypes.swift (2)
33-37
: LGTM! 새로운 케이스들이 잘 추가되었습니다.새로운
SignUpSubViewType
케이스에 대한name
속성 값들이 적절하게 추가되었습니다. 코드의 일관성과 가독성이 유지되고 있습니다.다만, 향후 유지보수를 위해 각 케이스에 대한 간단한 주석을 추가하는 것을 고려해보시는 것은 어떨까요? 예를 들어:
case .authGreeting: return "가입 후 환영" // 사용자 가입 완료 후 환영 메시지 표시 case .authProfileGender: return "성별 입력" // 사용자 프로필 성별 정보 입력 // ... 기타 케이스들에 대해서도 비슷하게 적용
47-51
: 새로운 회원가입 단계들이 잘 추가되었습니다.
SignUpSubViewType
열거형에 새로운 케이스들이 적절하게 추가되었습니다. 이는 회원가입 프로세스의 다양한 단계를 잘 표현하고 있습니다.코드의 구조를 개선하기 위해, 관련된 케이스들을 그룹화하는 것을 고려해보시는 것은 어떨까요? 예를 들어:
public enum SignUpSubViewType: Hashable { // 인증 관련 case authPhoneInput case authPhoneVerify case authAgreement case authGreeting // 프로필 정보 입력 case authProfileGender case authProfileAge case authName }이렇게 구성하면 각 단계의 목적을 더 명확히 할 수 있고, 향후 새로운 케이스를 추가할 때 적절한 위치를 쉽게 찾을 수 있습니다.
Projects/DesignSystem/DesignCore/Sources/NavigationBar.swift (2)
21-28
: LGTM: 조건부 백 버튼 렌더링 구현
showLeftBackButton
속성을 사용하여 백 버튼을 조건부로 렌더링하는 구현이 잘 되었습니다. 코드 구조가 깔끔하고 이해하기 쉽습니다.가독성을 더 높이기 위해, 백 버튼 렌더링 로직을 별도의 메서드로 추출하는 것을 고려해 보세요. 예를 들어:
private func backButton() -> some View { Button { handler() } label: { DesignCore.Images.leftArrow.image } }그리고
ToolbarItem
내에서 이 메서드를 호출하면 됩니다:ToolbarItem(placement: .topBarLeading) { backButton() }이렇게 하면
body
메서드가 더 간결해지고, 백 버튼 로직을 별도로 테스트하기도 쉬워집니다.
36-45
: LGTM:setNavigation
메서드 업데이트
setNavigation
메서드의 변경사항이 새로운 기능을 올바르게 구현하면서도 이전 버전과의 호환성을 유지하고 있습니다.showLeftBackButton
의 기본값을true
로 설정한 것은 기존 코드의 동작을 보장하는 좋은 접근 방식입니다.메서드의 문서화를 개선하는 것을 고려해 보세요. 예를 들어:
/// 네비게이션 바를 설정합니다. /// - Parameters: /// - showLeftBackButton: 왼쪽 백 버튼을 표시할지 여부. 기본값은 `true`입니다. /// - handler: 백 버튼이 탭되었을 때 실행될 클로저. /// - Returns: 수정된 뷰. func setNavigation( showLeftBackButton: Bool = true, handler: @escaping () -> Void ) -> some View { // ... (existing implementation) }이렇게 문서화를 추가하면 API 사용자가 메서드의 기능과 매개변수를 더 쉽게 이해할 수 있습니다.
Projects/Features/SignUp/Sources/ProfileInput/AuthGreeting/AuthGreetingView.swift (3)
13-16
: 구조체 선언과 초기화가 잘 되어 있습니다.
AuthGreetingView
구조체가 적절히 선언되어 있고, 애니메이션을 위한 상태 변수도 잘 설정되어 있습니다. 다만, 코드의 가독성을 높이기 위해 다음과 같은 작은 개선을 제안합니다:public struct AuthGreetingView: View { - @State var isAppeared = false + @State private var isAppeared = false public init() {}
isAppeared
변수를private
으로 선언하면 뷰 내부에서만 사용됨을 명확히 할 수 있습니다.
18-53
: 뷰의 구조와 애니메이션이 잘 구현되어 있습니다.전체적인 뷰의 구조와 애니메이션 구현이 잘 되어 있습니다. 사용자 경험을 향상시키는 세부적인 요소들이 잘 적용되어 있습니다. 다만, 애니메이션 지연에 대해 작은 개선을 제안합니다:
.textureBackground() .task { - try? await Task.sleep(nanoseconds: 500_000_000) + try? await Task.sleep(for: .milliseconds(500)) withAnimation(.easeInOut(duration: 0.6)) { isAppeared = true } }
Task.sleep(for:)
메서드를 사용하면 코드의 가독성이 향상되고, 시간 단위를 더 명확하게 표현할 수 있습니다.
56-58
: 프리뷰가 기본적으로 구현되어 있습니다.SwiftUI 프리뷰가 구현되어 있어 개발 중 빠른 시각적 확인이 가능합니다. 다만, 더 유용한 프리뷰를 위해 다음과 같은 개선을 제안합니다:
#Preview { NavigationView { AuthGreetingView() } }
NavigationView
로 감싸면 실제 앱에서의 모습에 더 가깝게 프리뷰를 확인할 수 있습니다. 또한, 다크 모드 프리뷰도 추가하면 좋을 것 같습니다:#Preview { Group { NavigationView { AuthGreetingView() } .preferredColorScheme(.light) NavigationView { AuthGreetingView() } .preferredColorScheme(.dark) } }이렇게 하면 라이트 모드와 다크 모드에서의 뷰 모습을 동시에 확인할 수 있습니다.
Projects/Features/SignUp/Sources/ProfileInput/ProfileInputTemplatedView.swift (2)
12-19
: 구조가 잘 설계되었습니다. 타입 안전성을 위한 작은 제안이 있습니다.구조체의 설계가 잘 되어 있습니다. 제네릭을 사용하여 유연한 콘텐츠 주입이 가능하고, 속성들도 페이지네이션된 입력 뷰에 적합합니다. @ViewBuilder의 사용도 적절합니다.
타입 안전성을 높이기 위해
currentPage
와maxPage
를Int
에서UInt
로 변경하는 것을 고려해 보세요. 이렇게 하면 음수 값이 입력되는 것을 방지할 수 있습니다.- let currentPage: Int - let maxPage: Int + let currentPage: UInt + let maxPage: UInt
20-50
: 구현이 잘 되었습니다. 접근성 개선을 위한 제안이 있습니다.레이아웃 구조가 명확하고 잘 정리되어 있습니다. 간격과 패딩을 적절히 사용하여 일관된 레이아웃을 만들었고, DesignCore를 활용하여 색상과 타이포그래피를 잘 적용했습니다.
접근성을 개선하기 위해 다음과 같은 변경을 제안합니다:
- 페이지 표시기에 접근성 레이블을 추가하세요:
HStack(spacing: 0) { Text("\(currentPage)") .foregroundStyle(DesignCore.Colors.blue300) Text("/\(maxPage)") .foregroundStyle(DesignCore.Colors.grey300) } .accessibilityLabel("페이지 \(currentPage) / \(maxPage)")
- VoiceOver 사용자를 위해
subMessage
와mainMessage
를 하나의 요소로 그룹화하세요:VStack(spacing: 0) { LeftAlignText(subMessage) .typography(.regular_14) .foregroundStyle(DesignCore.Colors.grey200) LeftAlignText(mainMessage) .typography(.semibold_24) .foregroundStyle(DesignCore.Colors.grey500) } .accessibilityElement(children: .combine) .accessibilityLabel("\(subMessage) \(mainMessage)")이러한 변경사항들은 화면 읽기 프로그램 사용자들에게 더 나은 경험을 제공할 것입니다.
Projects/Features/SignUp/Sources/ProfileInput/AuthName/AuthNameInputView.swift (3)
1-13
: UIKit 임포트 필요성 확인현재 코드에서 UIKit을 직접적으로 사용하는 부분이 보이지 않습니다. SwiftUI 뷰에서는 일반적으로 UIKit이 필요하지 않습니다.
만약 UIKit의 기능을 직접 사용하지 않는다면, 다음과 같이 import 문을 제거하는 것이 좋습니다:
import SwiftUI import DesignCore import CommonKit - import UIKit
이렇게 하면 코드의 의존성을 줄이고 컴파일 시간을 약간 개선할 수 있습니다.
14-20
: 불필요한 빈 이니셜라이저 제거현재 이니셜라이저가 비어 있어 특별한 기능을 추가하지 않습니다. Swift의 기본 이니셜라이저로 충분할 것 같습니다.
다음과 같이 빈 이니셜라이저를 제거하는 것이 좋습니다:
public struct AuthNameInputView: View { @State var inputText = String() - public init() { - - } // ... 나머지 코드 ... }이렇게 하면 코드가 더 간결해지고 불필요한 부분을 제거할 수 있습니다.
84-88
: 프리뷰 기능 확장 제안현재 프리뷰 구현이 잘 되어 있습니다. 하지만 개발 과정에서 더 유용할 수 있도록 몇 가지 시나리오를 추가하는 것이 좋겠습니다.
다음과 같이 프리뷰를 확장해 보세요:
#Preview("빈 입력") { NavigationView { AuthNameInputView() } } #Preview("유효한 이름 입력") { NavigationView { AuthNameInputView() } .onAppear { // 미리보기에서 상태를 설정하기 위해 @State 래퍼를 사용 let view = AuthNameInputView() view._inputText.wrappedValue = "김위브" } } #Preview("긴 이름 입력") { NavigationView { AuthNameInputView() } .onAppear { let view = AuthNameInputView() view._inputText.wrappedValue = "매우긴이름을가진사용자" } }이렇게 하면 다양한 상황에서 뷰의 동작을 쉽게 확인할 수 있습니다.
Projects/Features/SignUp/Sources/ProfileInput/AuthProfileAge/AuthProfileAgeInputView.swift (1)
1-97
: 전반적인 구조는 양호하나 개선이 필요한 부분이 있습니다이 뷰의 전체적인 구조는 잘 설계되어 있습니다. 하지만 다음 사항들에 대해 개선이 필요합니다:
- 하드코딩된 값들 (예:
targetGender
,VerifyCodeInputView
파라미터)- 오류 메시지 처리 (
errorMessage
의 초기값)- 나이 확인 버튼의 기능 구현
- 네비게이션 로직 및 TODO 항목 해결
이러한 개선사항들을 적용하면 코드의 유지보수성과 재사용성이 향상될 것입니다.
위에서 언급한 개선사항들에 대해 더 자세한 구현 방법이나 추가적인 도움이 필요하시면 말씀해 주세요.
🧰 Tools
🪛 SwiftLint
[Warning] 80-80: TODOs should be resolved (순서 재정의)
(todo)
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
⛔ Files ignored due to path filters (21)
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_selected.imageset/female_selected.png
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_selected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_selected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_unselected.imageset/female_unselected.png
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_unselected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_unselected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_selected.imageset/male_selected.png
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_selected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_selected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_unselected.imageset/male_unselected.png
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_unselected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_unselected.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/icon-information.imageset/icon-information.png
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/icon-information.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/icon-information.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/name-paper.imageset/name-paper.png
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/name-paper.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/name-paper.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/pencil.imageset/pencil.png
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/pencil.imageset/[email protected]
is excluded by!**/*.png
Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/pencil.imageset/[email protected]
is excluded by!**/*.png
📒 Files selected for processing (21)
- Projects/App/Sources/Navigation/NavigationStack.swift (1 hunks)
- Projects/Core/CommonKit/Sources/AppCoordinator.swift (1 hunks)
- Projects/Core/CommonKit/Sources/Path/PathTypes.swift (2 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_selected.imageset/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_unselected.imageset/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_selected.imageset/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_unselected.imageset/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/icon-information.imageset/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/name-paper.imageset/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/pencil.imageset/Contents.json (1 hunks)
- Projects/DesignSystem/DesignCore/Sources/CTAButton/CTABottomButton.swift (1 hunks)
- Projects/DesignSystem/DesignCore/Sources/NavigationBar.swift (2 hunks)
- Projects/Features/SignUp/Sources/AuthAgreement/AuthAgreementView.swift (1 hunks)
- Projects/Features/SignUp/Sources/AuthPhoneInput/AuthPhoneInputView.swift (1 hunks)
- Projects/Features/SignUp/Sources/AuthPhoneVerify/AuthPhoneVerifyView.swift (2 hunks)
- Projects/Features/SignUp/Sources/ProfileInput/AuthGreeting/AuthGreetingView.swift (1 hunks)
- Projects/Features/SignUp/Sources/ProfileInput/AuthName/AuthNameInputView.swift (1 hunks)
- Projects/Features/SignUp/Sources/ProfileInput/AuthProfileAge/AuthProfileAgeInputView.swift (1 hunks)
- Projects/Features/SignUp/Sources/ProfileInput/AuthProfileGenderInput/AuthProfileGenderInputView.swift (1 hunks)
- Projects/Features/SignUp/Sources/ProfileInput/ProfileInputTemplatedView.swift (1 hunks)
✅ Files skipped from review due to trivial changes (8)
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/Contents.json
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_selected.imageset/Contents.json
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/female_unselected.imageset/Contents.json
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_selected.imageset/Contents.json
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/Gender/male_unselected.imageset/Contents.json
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/icon-information.imageset/Contents.json
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/name-paper.imageset/Contents.json
- Projects/DesignSystem/DesignCore/Resources/Images/Images.xcassets/pencil.imageset/Contents.json
🧰 Additional context used
🪛 SwiftLint
Projects/Features/SignUp/Sources/ProfileInput/AuthProfileAge/AuthProfileAgeInputView.swift
[Warning] 80-80: TODOs should be resolved (순서 재정의)
(todo)
🔇 Additional comments (14)
Projects/Core/CommonKit/Sources/AppCoordinator.swift (2)
20-20
:@MainActor
속성 추가가 적절합니다.
changeRootView
메서드에@MainActor
속성을 추가한 것은 좋은 변경입니다. 이는 UI 관련 작업이 메인 스레드에서 실행되도록 보장하며, 클래스의 다른 메서드들과 일관성을 유지합니다.
22-24
:⚠️ Potential issue
changeRootView
메서드의 변경사항 검토변경사항은 다음과 같습니다:
push(path)
직접 호출로 코드가 간소화되었습니다.- 0.3초 지연 후 첫 번째 네비게이션 스택 요소를 제거하는 비동기 작업이 추가되었습니다.
이 변경은 애니메이션 타이밍과 동기화하려는 의도로 보입니다. 그러나 몇 가지 고려해야 할 사항이 있습니다:
changeRootView
가 빠르게 여러 번 호출될 경우 잠재적인 경쟁 상태가 발생할 수 있습니다.- 하드코딩된 지연 시간(0.3초)은 장치 성능에 따라 일관되지 않을 수 있습니다.
다음 개선 사항을 고려해보세요:
- 애니메이션 완료 콜백을 사용하여 더 안정적으로 첫 번째 요소를 제거합니다.
- 여러 번의 빠른 호출을 처리할 수 있는 방법을 구현합니다.
아래 스크립트를 실행하여
changeRootView
메서드의 사용을 확인해주세요:이 스크립트의 결과를 바탕으로
changeRootView
의 사용 패턴을 분석하고, 필요한 경우 추가적인 안전장치를 구현하는 것이 좋습니다.✅ Verification successful
changeRootView
메서드 변경사항 검증 완료현재 코드베이스에서
changeRootView
메서드가 연속으로 여러 번 호출되는 사례는 발견되지 않았습니다. 따라서 잠재적인 경쟁 상태에 대한 우려는 해소된 것으로 보입니다.추가적으로, 0.3초의 하드코딩된 지연 시간은 현재 사용 패턴에서는 문제가 발생하지 않지만, 애니메이션 최적화가 필요할 경우 재검토를 고려해볼 수 있습니다.
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # Description: Verify the usage of changeRootView method across the codebase # Test: Search for changeRootView method calls echo "Searching for changeRootView method calls:" rg --type swift -A 3 "changeRootView\(" # Test: Check if there are any places where changeRootView is called multiple times in succession echo "Checking for multiple changeRootView calls in succession:" rg --type swift -A 10 "changeRootView\(" | rg -C 2 "changeRootView\("Length of output: 2422
Projects/DesignSystem/DesignCore/Sources/NavigationBar.swift (1)
12-12
: LGTM:showLeftBackButton
속성 추가
showLeftBackButton
속성의 추가는 네비게이션 바의 모양을 더 유연하게 제어할 수 있게 해줍니다. 기본값을true
로 설정한 것은 기존 코드와의 호환성을 유지하는 좋은 접근 방식입니다.Projects/Features/SignUp/Sources/ProfileInput/AuthGreeting/AuthGreetingView.swift (1)
1-12
: LGTM: 파일 헤더와 import 문이 적절합니다.파일 헤더와 import 문이 SwiftUI 뷰에 적합하게 구성되어 있습니다. CommonKit과 DesignCore를 import하여 커스텀 디자인 요소를 사용할 수 있도록 준비되어 있습니다.
Projects/Features/SignUp/Sources/ProfileInput/ProfileInputTemplatedView.swift (1)
38-43
:LeftAlignText
뷰의 가용성을 확인해주세요.
LeftAlignText
뷰가 사용되고 있지만 이 파일에서 정의되지 않았습니다. 이 뷰가 다른 파일에서 정의되어 있고 올바르게 임포트되었는지 확인해주세요. 아마도 DesignCore 모듈의 일부일 수 있습니다.
LeftAlignText
뷰의 정의와 임포트를 확인하기 위해 다음 스크립트를 실행해주세요:이 스크립트의 결과를 바탕으로
LeftAlignText
의 가용성을 확인하고, 필요하다면 추가 임포트를 고려해주세요.✅ Verification successful
DesignCore
모듈에서LeftAlignText
의 공개 정의를 다시 확인해주세요.이전 스크립트에서
DesignCore/**/*.swift
패턴으로LeftAlignText
의 공개 정의를 찾지 못했습니다. 정확한 경로를 사용하여 다시 검색해 주세요.
DesignCore
모듈에서LeftAlignText
의 공개 정의를 다시 확인해주세요.기존 경로에서 파일을 찾지 못했습니다.
LeftAlignText.swift
파일의 정확한 위치를 찾기 위해 다음 스크립트를 실행해주세요:이 스크립트는 먼저
LeftAlignText.swift
파일의 위치를 찾고, 해당 파일 내에서public struct LeftAlignText
정의를 확인합니다. 결과를 바탕으로 다음 단계를 진행해주세요.
LeftAlignText
뷰의 가용성이 확인되었습니다.
LeftAlignText
는DesignCore
모듈에서 올바르게 정의되고 임포트되었습니다.🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # LeftAlignText 뷰의 정의를 검색합니다. echo "Searching for LeftAlignText definition:" rg --type swift "struct\s+LeftAlignText\s*:\s*View" -g '!ProfileInputTemplatedView.swift' # DesignCore 모듈에서 LeftAlignText의 익스포트를 확인합니다. echo "\nChecking DesignCore module for LeftAlignText export:" rg --type swift "public\s+struct\s+LeftAlignText" -g 'DesignCore/**/*.swift' # ProfileInputTemplatedView.swift 파일에서 추가 임포트를 확인합니다. echo "\nChecking for additional imports in ProfileInputTemplatedView.swift:" rg --type swift "^import" Projects/Features/SignUp/Sources/ProfileInput/ProfileInputTemplatedView.swiftLength of output: 912
Script:
#!/bin/bash # DesignCore 모듈에서 LeftAlignText의 공개 정의를 재검색합니다. echo "DesignCore 모듈에서 'public struct LeftAlignText' 정의를 검색 중:" rg --type swift "public\s+struct\s+LeftAlignText" DesignSystem/DesignCore/Sources/**/*.swiftLength of output: 306
Script:
#!/bin/bash # 프로젝트 전체에서 LeftAlignText.swift 파일을 검색합니다. echo "프로젝트에서 'LeftAlignText.swift' 파일을 검색 중:" file_path=$(fd LeftAlignText.swift) if [ -z "$file_path" ]; then echo "LeftAlignText.swift 파일을 찾을 수 없습니다." exit 1 fi echo "파일 경로: $file_path" # 해당 파일에서 public struct LeftAlignText 정의를 검색합니다. echo "\n$file_path 파일에서 'public struct LeftAlignText' 정의를 검색 중:" rg "public\s+struct\s+LeftAlignText" "$file_path"Length of output: 777
Projects/Features/SignUp/Sources/ProfileInput/AuthName/AuthNameInputView.swift (1)
22-34
: 배경 뷰 구현이 잘 되었습니다배경 뷰의 구현이 시각적으로 매력적이고 이름 입력 필드에 적합한 레이아웃을 만들어냅니다. DesignCore의 이미지를 효과적으로 활용하여 사용자 경험을 향상시키고 있습니다.
계속해서 이런 방식으로 UI를 개선해 나가시기 바랍니다. 사용자에게 더 나은 시각적 경험을 제공할 수 있을 것입니다.
Projects/Features/SignUp/Sources/AuthPhoneInput/AuthPhoneInputView.swift (1)
16-16
: 전화번호 입력 필드에 기본값 추가에 대한 검토전화번호 입력 필드에 "010-"를 기본값으로 설정한 것은 사용자 경험을 개선하는 좋은 방법입니다. 대부분의 사용자에게 편리할 것입니다.
다만, 모든 사용자의 전화번호가 "010"으로 시작하지 않을 수 있다는 점을 고려해야 합니다. 다음 사항을 확인해 주세요:
- "010" 이외의 번호를 입력할 수 있는 방법이 있는지
- 사용자가 쉽게 기본값을 수정할 수 있는지
이를 확인하기 위해 다음 스크립트를 실행해 주세요:
이 스크립트의 결과를 바탕으로 필요한 경우 추가적인 수정을 고려해 주세요.
✅ Verification successful
<!-- [monologue] [task review_file_1/1 review_change_1/1] Analyze the shell script output to verify the ability to input non-"010" phone numbers and the validation mechanism. [observations] - The `phoneTextInput` is initialized with "010-" in `AuthPhoneInputView.swift`. - In `DesignTextInputPreview.swift`, `phoneTextInput` is initialized as an empty string. - The validation function `isValidPhoneNumber` is implemented and has multiple test cases handling different formats. - The presence of `isValidPhoneNumber` in various parts of the codebase indicates a robust validation mechanism. [analysis] - The default value "010-" in `AuthPhoneInputView.swift` improves user experience for users with "010" numbers. - The empty initialization in `DesignTextInputPreview.swift` suggests flexibility for other prefixes. - The validation function supports various phone number formats, ensuring that non-"010" numbers can be handled appropriately. - No evidence of restrictions limiting input to only "010-" numbers. [actions] - Conclude that the change is appropriately handled and does not restrict users to "010-" numbers. - Finalize the review comment indicating successful verification. --> **전화번호 입력 필드 기본값 검증 완료** `phoneTextInput`을 "010-"으로 기본 설정한 변경 사항을 검토한 결과, 다른 번호 접두사도 문제없이 입력하고 검증할 수 있는 것으로 확인되었습니다. `isValidPhoneNumber` 함수가 다양한 전화번호 형식을 지원하여 유연하게 처리됩니다.🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash # Description: Verify the phone number input handling # Test: Check if there's a way to input non-"010" numbers rg --type swift 'phoneTextInput' -A 10 -g '!*.generated.swift' # Test: Check if there's any validation for the phone number format rg --type swift 'isValidPhoneNumber|validatePhoneNumber' -g '!*.generated.swift'Length of output: 11280
Projects/Features/SignUp/Sources/ProfileInput/AuthProfileGenderInput/AuthProfileGenderInputView.swift (2)
1-12
: 파일 헤더와 import 문이 적절합니다.파일 헤더에 저작권 정보와 생성 날짜가 올바르게 포함되어 있습니다. SwiftUI, DesignCore, CommonKit의 import는 이 뷰의 기능에 필요한 것으로 보입니다.
1-90
: 전반적인 구현이 잘 되어 있습니다만, 몇 가지 개선 사항이 있습니다.이 파일은 성별 입력을 위한 UI를 잘 구현하고 있습니다. 하지만 다음과 같은 부분들을 개선하면 더 좋은 코드가 될 것 같습니다:
- 성별 옵션을 더 포괄적으로 만들기
selectedGender
를@Binding
으로 변경하여 뷰의 재사용성 높이기- 성별 선택 UI를 별도의 뷰로 분리하여 코드 가독성 개선
- 접근성 레이블 추가로 시각 장애인 사용자 경험 향상
- 문자열 지역화로 국제화 지원
이러한 개선사항들을 적용하면 더 포괄적이고, 유지보수가 쉬우며, 접근성이 높은 코드가 될 것입니다.
Projects/DesignSystem/DesignCore/Sources/CTAButton/CTABottomButton.swift (3)
12-14
: 구조체의 제네릭 파라미터 제거로 인한 코드 간결화CTABottomButton 구조체에서 제네릭 파라미터를 제거하여 코드가 더욱 간결해졌습니다.
25-30
: backgroundStyle의 타입 변경으로 인한 초기화 로직 수정
backgroundStyle
파라미터가some ShapeStyle
로 변경되어 초기화 로직이 수정되었습니다. 이는 다양한ShapeStyle
을 지원하기 위한 것으로 보이며, 코드의 유연성을 높입니다.
35-37
: 비활성 상태의 버튼 배경 색상 처리 개선
isActive
가false
일 때 버튼 배경 색상을DesignCore.Colors.grey100
으로 설정하여 비활성화 상태를 명확히 표시합니다.Projects/Features/SignUp/Sources/AuthPhoneVerify/AuthPhoneVerifyView.swift (2)
130-130
: 텍스트 박스에 그림자를 추가하여 시각적 효과를 향상시켰습니다텍스트 박스에
.shadow(.default)
를 적용하여 시각적인 깊이감을 더했습니다.
138-143
: 속성을 활용하여 UI의 유연성을 높였습니다하드코딩된 값 대신 속성들을 사용하여 UI 요소의 스타일을 동적으로 조절할 수 있게 되었습니다. 이를 통해 코드의 재사용성과 유지보수성이 향상됩니다.
Also applies to: 146-146, 148-148
public var body: some View { | ||
VStack(spacing: 44) { | ||
VStack(spacing: 0) { | ||
Text("이제 마지막이에요.") | ||
.typography(.regular_14) | ||
.foregroundStyle(DesignCore.Colors.grey200) | ||
Text("당신의 이름은 무엇인가요?") | ||
.typography(.semibold_24) | ||
.foregroundStyle(DesignCore.Colors.grey500) | ||
} | ||
|
||
ZStack { | ||
backgroundView | ||
TextField( | ||
"김위브", | ||
text: $inputText | ||
) | ||
.keyboardType(.namePhonePad) | ||
.interactiveDismissDisabled() | ||
.textInputAutocapitalization(.never) | ||
.autocorrectionDisabled() | ||
.speechAnnouncementsQueued(false) | ||
.speechSpellsOutCharacters(false) | ||
.multilineTextAlignment(.center) | ||
.pretendard(weight: ._400, size: 28) | ||
.foregroundStyle(DesignCore.Colors.grey500) | ||
.offset(y: -4) | ||
} | ||
|
||
Spacer() | ||
|
||
CTABottomButton( | ||
title: "다음", | ||
backgroundStyle: LinearGradient.gradientA, | ||
isActive: inputText.count >= 2 | ||
) { | ||
|
||
} | ||
} | ||
.ignoresSafeArea() | ||
.padding(.top, 10) | ||
.textureBackground() | ||
.setNavigation { | ||
AppCoordinator.shared.pop() | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
메인 뷰 구현에 대한 개선 제안
전반적으로 구현이 잘 되어 있습니다만, 몇 가지 개선할 점이 있습니다:
- 입력 유효성 검사를 위한 매직 넘버 '2'를 상수로 추출하는 것이 좋습니다.
- CTA 버튼의 액션 클로저가 비어 있습니다. 구현이 필요합니다.
- 단순 길이 체크 외에 추가적인 입력 유효성 검사를 고려해보세요.
다음과 같이 코드를 개선할 수 있습니다:
public struct AuthNameInputView: View {
private let minimumNameLength = 2
// ... 기존 코드 ...
public var body: some View {
VStack(spacing: 44) {
// ... 기존 코드 ...
CTABottomButton(
title: "다음",
backgroundStyle: LinearGradient.gradientA,
isActive: isValidName(inputText)
) {
// TODO: 다음 단계로 이동하는 로직 구현
}
}
// ... 기존 코드 ...
}
private func isValidName(_ name: String) -> Bool {
// TODO: 추가적인 유효성 검사 로직 구현
return name.count >= minimumNameLength && name.trimmingCharacters(in: .whitespacesAndNewlines).count > 0
}
}
이렇게 하면 코드의 가독성과 유지보수성이 향상됩니다. 또한, 사용자 이름에 대한 더 강력한 유효성 검사를 구현할 수 있습니다.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
지금은 테스트 단계라 나중에 할께 ~
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@jisu15-kim 알겠습니다. 추후에 작업하실 때 도움이 필요하시면 언제든지 말씀해주세요.
(_/)
( ;_;)
(/ )
enum GenderType: CaseIterable { | ||
case male | ||
case female | ||
|
||
var unselectedImage: Image { | ||
switch self { | ||
case .male: DesignCore.Images.maleUnselected.image | ||
case .female: DesignCore.Images.femaleUnselected.image | ||
} | ||
} | ||
|
||
var selectedImage: Image { | ||
switch self { | ||
case .male: DesignCore.Images.maleSelected.image | ||
case .female: DesignCore.Images.femaleSelected.image | ||
} | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
성별 옵션을 더 포괄적으로 만들어 보는 것은 어떨까요?
현재 GenderType
enum은 male과 female만을 포함하고 있습니다. 더 포괄적인 접근을 위해 다음과 같은 옵션을 고려해 보시는 것이 어떨까요?
- "기타" 또는 "명시하고 싶지 않음" 옵션 추가
- 사용자가 직접 입력할 수 있는 옵션 제공
이렇게 하면 더 다양한 성 정체성을 가진 사용자들을 포용할 수 있을 것 같습니다.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
그렇게 되면 우리 비즈니스를 아예 다시 기획해야해 ...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@jisu15-kim, 이해했습니다. 현재 비즈니스 방향에 맞춰 구현을 유지하겠습니다.
✏️ Learnings added
Learnt from: jisu15-kim
PR: Student-Center/3days-ios#26
File: Projects/Features/SignUp/Sources/ProfileInput/AuthProfileGenderInput/AuthProfileGenderInputView.swift:13-30
Timestamp: 2024-10-03T13:21:40.755Z
Learning: `GenderType` enum은 `male`과 `female`만을 포함하며, 추가적인 성별 옵션은 비즈니스 범위에서 제외됩니다.
Note: Learnings are effective only in the context of similar code segments. To apply general coding guidelines, please configure review instructions. You can manage existing learnings in the app.
...Features/SignUp/Sources/ProfileInput/AuthProfileGenderInput/AuthProfileGenderInputView.swift
Show resolved
Hide resolved
public var body: some View { | ||
VStack { | ||
ProfileInputTemplatedView( | ||
currentPage: 1, | ||
maxPage: 5, | ||
subMessage: "만나서 반가워요!", | ||
mainMessage: "당신의 성별은 무엇인가요?" | ||
) { | ||
HStack(spacing: 0) { | ||
Spacer() | ||
ForEach(GenderType.allCases, id: \.self) { type in | ||
if selectedGender == type { | ||
type.selectedImage | ||
.resizable() | ||
.frame(width: 130, height: 130) | ||
} else { | ||
type.unselectedImage | ||
.resizable() | ||
.frame(width: 130, height: 130) | ||
.onTapGesture { | ||
withAnimation { | ||
selectedGender = type | ||
} | ||
} | ||
} | ||
} | ||
Spacer() | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
성별 선택 UI를 별도의 뷰로 분리하는 것이 어떨까요?
현재 성별 선택을 위한 HStack
이 body
프로퍼티 내에 직접 구현되어 있습니다. 이 부분을 별도의 뷰로 추출하면 코드의 가독성과 재사용성이 향상될 것 같습니다. 예를 들어:
struct GenderSelectionView: View {
@Binding var selectedGender: GenderType?
var body: some View {
HStack(spacing: 0) {
Spacer()
ForEach(GenderType.allCases, id: \.self) { type in
// 현재 구현과 동일한 내용
}
Spacer()
}
}
}
그리고 AuthProfileGenderInputView
의 body
에서 이를 사용할 수 있습니다:
GenderSelectionView(selectedGender: $selectedGender)
이렇게 하면 AuthProfileGenderInputView
의 body
가 더 간결해지고, 성별 선택 로직을 별도로 관리할 수 있습니다.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
추후 그 뷰를 재사용 하게 되면 고려해도 될것같아.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@jisu15-kim, 네, 이해했습니다. 추후 재사용할 때 고려하시면 좋을 것 같습니다.
(_/)
( •_•)
/ 💧
🧠 Learnings used
Learnt from: jisu15-kim
PR: Student-Center/3days-ios#26
File: Projects/Features/SignUp/Sources/ProfileInput/AuthProfileGenderInput/AuthProfileGenderInputView.swift:13-30
Timestamp: 2024-10-03T13:21:40.978Z
Learning: `GenderType` enum은 `male`과 `female`만을 포함하며, 추가적인 성별 옵션은 비즈니스 범위에서 제외됩니다.
...Features/SignUp/Sources/ProfileInput/AuthProfileGenderInput/AuthProfileGenderInputView.swift
Show resolved
Hide resolved
Projects/Features/SignUp/Sources/ProfileInput/AuthProfileAge/AuthProfileAgeInputView.swift
Show resolved
Hide resolved
// TODO: 순서 재정의 | ||
AppCoordinator.shared.push(.signUp(.authName)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💡 Codebase verification
TODO 항목과 네비게이션 로직의 하드코딩 문제 확인
TODO 주석이 여전히 존재하며, 여러 파일에서 AppCoordinator.shared.push
의 하드코딩된 사용이 발견되었습니다. 이는 앱의 전체 네비게이션 흐름과 일관성을 저해할 수 있습니다. 네비게이션 로직을 리팩토링하여 일관성과 유연성을 확보하는 것이 필요합니다.
🔗 Analysis chain
TODO 주석 및 네비게이션 로직 검토 필요
TODO 주석이 있으며, 네비게이션 로직이 하드코딩되어 있습니다.
TODO 항목을 해결하고 네비게이션 로직을 검토해 주세요. 앱의 전체 네비게이션 흐름과 일관성이 있는지 확인이 필요합니다.
다음 스크립트를 실행하여 AppCoordinator
의 사용을 확인할 수 있습니다:
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash
# AppCoordinator 사용 패턴 확인
rg --type swift "AppCoordinator\.shared\.push" -A 2 -B 2
Length of output: 3021
🧰 Tools
🪛 SwiftLint
[Warning] 80-80: TODOs should be resolved (순서 재정의)
(todo)
private let title: String | ||
private let backgroundStyle: BackgroundStyle | ||
private let backgroundStyle: AnyShapeStyle |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
AnyShapeStyle 사용에 따른 타입 소거 및 성능 영향
backgroundStyle
을 AnyShapeStyle
로 선언하면 타입 소거(type erasure)가 발생하여 런타임 성능에 영향을 줄 수 있습니다. 가능하다면 제네릭 파라미터를 유지하여 구체적인 ShapeStyle
타입을 사용하는 것을 고려해 보세요.
let boxHeight: CGFloat | ||
let textColor: Color | ||
let borderWidth: CGFloat | ||
let borderColor: Color | ||
let backColor: Color | ||
let cornerRadius: CGFloat |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
초기화 메서드의 매개변수 수를 줄이기 위해 스타일 구조체 사용을 고려하세요
여러 개의 스타일 관련 속성이 추가되어 초기화 메서드의 매개변수 수가 많아졌습니다. 이러한 속성들을 하나의 구조체나 설정 객체로 묶어 전달하면 코드의 가독성과 유지보수성이 향상됩니다.
다음과 같이 스타일 구조체를 도입하여 코드를 개선할 수 있습니다:
struct TextBoxStyle {
var boxHeight: CGFloat = 72
var textColor: Color = .black
var borderWidth: CGFloat = 0
var borderColor: Color = .white
var backColor: Color = .white
var cornerRadius: CGFloat = 10
}
초기화 메서드와 속성을 다음과 같이 변경합니다:
public struct VerifyCodeInputView: View {
@Binding var verifyCode: String
@Binding var errorMessage: String?
var verifyCodeMaxCount: Int
@FocusState private var isTextFieldFocused: Bool
- let boxHeight: CGFloat
- let textColor: Color
- let borderWidth: CGFloat
- let borderColor: Color
- let backColor: Color
- let cornerRadius: CGFloat
+ let style: TextBoxStyle
public init(
verifyCode: Binding<String>,
errorMessage: Binding<String?>,
verifyCodeMaxCount: Int = 6,
- boxHeight: CGFloat = 72,
- textColor: Color = .black,
- borderWidth: CGFloat = 0,
- borderColor: Color = .white,
- backColor: Color = .white,
- cornerRadius: CGFloat = 10,
focused: FocusState<Bool>,
+ style: TextBoxStyle = TextBoxStyle()
) {
self._verifyCode = verifyCode
self._errorMessage = errorMessage
self.verifyCodeMaxCount = verifyCodeMaxCount
self._isTextFieldFocused = focused
- self.boxHeight = boxHeight
- self.textColor = textColor
- self.borderWidth = borderWidth
- self.borderColor = borderColor
- self.backColor = backColor
- self.cornerRadius = cornerRadius
+ self.style = style
}
Also applies to: 98-103
boxHeight: CGFloat = 72, | ||
textColor: Color = .black, | ||
borderWidth: CGFloat = 0, | ||
borderColor: Color = .white, | ||
backColor: Color = .white, | ||
cornerRadius: CGFloat = 10, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
💡 Codebase verification
VerifyCodeInputView
초기화 메서드 호환성 문제 발견
VerifyCodeInputView
의 초기화 메서드가 업데이트되면서 새로운 매개변수가 추가되었습니다. 현재 초기화 호출은 새로운 매개변수를 포함하고 있지 않아 컴파일 오류가 발생할 수 있습니다. 다음 위치에서 초기화 호출을 수정해야 합니다:
Projects/Features/SignUp/Sources/AuthPhoneVerify/AuthPhoneVerifyView.swift
Projects/Features/SignUp/Sources/ProfileInput/AuthProfileAge/AuthProfileAgeInputView.swift
🔗 Analysis chain
초기화 메서드 변경으로 인한 기존 코드 영향 확인 필요
VerifyCodeInputView
의 초기화 메서드에 새로운 매개변수가 추가되어, 이 뷰를 사용하는 기존 코드에 영향이 있을 수 있습니다. 특히 위치 기반 인자를 사용하는 경우 컴파일 오류가 발생할 수 있으므로, 기존 사용처를 확인하고 필요한 경우 수정해야 합니다.
다음 스크립트를 사용하여 VerifyCodeInputView
의 초기화 메서드 사용 현황을 확인하세요:
VerifyCodeInputView
초기화 구문의 매개변수 호환성 확인 필요
초기화 호출의 매개변수가 업데이트된 초기화 메서드와 호환되는지 확인하기 위해 아래 스크립트를 실행하여 초기화 구문의 세부사항을 확인해주세요:
[/run_scripts]
🏁 Scripts executed
The following scripts were executed for the analysis:
Script:
#!/bin/bash
# Description: Verify usage of VerifyCodeInputView initializer
# Test: Search for all initializations of VerifyCodeInputView
# Expect: Ensure all initializations are compatible with the updated initializer
rg --type swift 'VerifyCodeInputView\('
Length of output: 285
Script:
#!/bin/bash
# Description: Fetch all initializations of VerifyCodeInputView with surrounding lines for context
rg --type swift 'VerifyCodeInputView\(' -A 3
Length of output: 1086
구현사항
Summary by CodeRabbit
릴리스 노트
신규 기능
버그 수정
문서화
스타일