-
Notifications
You must be signed in to change notification settings - Fork 0
#224 리딩챌린지: 퀴즈확인, 딥타임, 퀴즈풀기 UI 통합 및 디자인 개선 #225
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
base: main
Are you sure you want to change the base?
Conversation
ReadingChallengeQuizWrapScreen 통합 화면 구현 - 퀴즈 확인, 딥타임, 퀴즈 풀기, 정답 확인을 하나의 화면에서 관리 - PageView 기반 탭 네비게이션 구조 - 각 탭별 상태 관리 및 화면 전환 로직 구현 - CustomCountDownController를 활용한 딥타임 타이머 상태 관리 - 잠금 기능(isLock)으로 독서 중 화면 이탈 방지 퀴즈 확인 화면 디자인 개선 (ReadingChallengeQuizCheckScreen) - 기존 퀴즈 상세 화면에서 퀴즈 미리보기 UI로 변경 - "뒷내용이 궁금해지는 오늘의 퀴즈를 확인해 보세요" 안내 문구 추가 - 퀴즈 카드 디자인 개선 - 외곽 빛 효과 (BoxShadow with purple glow) - 하단 그림자 효과 - ic_quiz_check.png 아이콘 추가 - 질문 텍스트만 표시 (선택지 제거) - CTA 버튼 텍스트 변경: "책 속에서 정답 찾기" - BaseScreen 구조 유지, 독립 실행 가능한 컴포넌트로 리팩토링 - 퀴즈 오류 신고 기능 제거 (통합 화면에서 관리) 딥타임 화면 리팩토리 (ReadingChallengeQuizDeepTimeScreen) - BaseScreen에서 ConsumerStatefulWidget으로 변경 - 외부에서 controller, 상태, 콜백을 주입받는 구조로 개선 - onStartTap, onPauseTap, onResumeTap, onStopTap - isLock, onLockToggle - CustomCountDownController controller - AutomaticKeepAliveClientMixin 적용으로 탭 전환 시 상태 유지 - 그라데이션 배경 추가 (bottom to center purple gradient) - 버튼 디자인 개선 - 기존 원형 아이콘 버튼에서 CtaButtonS 텍스트 버튼으로 변경 - "🚀독서 시작하기", "⏸️독서 일시정지", "🚀독서 계속하기", "🧩퀴즈 풀러가기" - 타이머 폰트 적용: Akira Expanded Demo (fontSize: 50, w900) - 잠금 상태에 따른 뒤로가기 제어 제거 (wrap 화면에서 관리) 퀴즈 풀기 화면 리팩토링 (ReadingChallengeQuizScreen) - BaseScreen에서 ConsumerStatefulWidget으로 변경 - 외부에서 onSubmitQuiz 콜백 주입받는 구조 - AutomaticKeepAliveClientMixin 적용 - CTA 버튼을 wrap 화면으로 이동 - 선택지 선택 로직을 wrap 화면과 공유 - 퀴즈 오류 신고 기능 제거 정답 확인 화면 개선 (ReadingChallengeQuizResultScreen) - onNextChapterTap, onRetryTap 콜백 주입 구조 - CTA 버튼을 wrap 화면으로 이동 - 정답/오답 표시 UI 유지 라우터 설정 간소화 - 기존 3개 개별 라우트 통합 - /reading-challenge/:challengeId/quiz/:chapterId/check (삭제) - /reading-challenge/:challengeId/quiz/:chapterId/deep-time (삭제) - /reading-challenge/:challengeId/quiz/:chapterId (삭제) - 새로운 통합 라우트 - /reading-challenge/:challengeId/quiz/:chapterId/wrap - ReadingChallengeScreen, ReadingChallengeStartScreen 네비게이션 업데이트 폰트 및 에셋 추가 - Akira Expanded Demo 폰트 추가 - assets/fonts/Akira Expanded Demo.otf - pubspec.yaml 폰트 패밀리 등록 - main.dart에 FontLoader 추가 - ic_quiz_check.png 이미지 추가 - assets.gen.dart 자동 생성 파일 업데이트 ViewModel 업데이트 - OngoingChallengeViewModel에 resetQuizWrapState 메서드 추가 - 퀴즈 wrap 화면 상태 초기화 로직 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
Summary of ChangesHello @doyou1, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed! 이 PR은 리딩 챌린지 퀴즈 경험을 전반적으로 개선하기 위해 기존의 분리된 퀴즈 관련 화면들을 하나의 통합된 플로우로 재구성합니다. 사용자 경험을 향상시키기 위한 UI/UX 디자인 업데이트와 함께, 화면 간 상태 유지 및 모듈화를 위한 기술적 리팩토링이 이루어졌습니다. 이를 통해 사용자는 더욱 매끄럽고 일관된 퀴즈 진행 경험을 할 수 있으며, 코드 베이스는 더 효율적이고 유지보수하기 쉬워졌습니다. Highlights
🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console. Using Gemini Code AssistThe full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips. Invoking Gemini You can request assistance from Gemini at any point by creating a comment using either
Customization To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a Limitations & Feedback Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here. You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension. Footnotes
|
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.
Code Review
이번 PR은 리딩챌린지 관련 여러 화면을 하나의 통합된 화면으로 재구성하고 UI/UX를 개선하는 대규모 리팩토링을 포함하고 있습니다. PageView와 TabController를 사용하여 탭 기반 네비게이션을 구현하고, 각 화면의 결합도를 낮추기 위해 콜백 패턴을 효과적으로 사용한 점이 인상적입니다. 전체적으로 코드 구조가 개선되고 사용자 경험이 향상될 것으로 기대됩니다.
몇 가지 개선점을 제안했습니다. main.dart에서 폰트를 잘못 로드하는 부분을 수정하여 앱 안정성을 높이고, 일부 위젯에서 불필요한 코드(사용되지 않는 속성, 중복된 setState 호출)를 제거하여 코드의 명확성과 성능을 개선할 수 있도록 제안했습니다.
| final fontLoader = FontLoader('BookkMyungjo'); | ||
| fontLoader.addFont(rootBundle.load(Assets.fonts.bookkMyungjoBold)); | ||
| fontLoader.addFont(rootBundle.load(Assets.fonts.akiraExpandedDemo)); | ||
| await fontLoader.load(); |
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.
새로운 폰트인 'AkiraExpandedDemo'를 로드하는 방식이 잘못되었습니다. FontLoader는 특정 폰트 패밀리에 대한 폰트들을 그룹화합니다. 현재 코드는 'AkiraExpandedDemo' 폰트를 'BookkMyungjo' 패밀리에 추가하고 있어, 의도한 대로 폰트가 적용되지 않을 수 있습니다.
'AkiraExpandedDemo' 폰트 패밀리에 대한 별도의 FontLoader를 생성하여 로드해야 합니다. 아래와 같이 수정하는 것을 제안합니다.
| final fontLoader = FontLoader('BookkMyungjo'); | |
| fontLoader.addFont(rootBundle.load(Assets.fonts.bookkMyungjoBold)); | |
| fontLoader.addFont(rootBundle.load(Assets.fonts.akiraExpandedDemo)); | |
| await fontLoader.load(); | |
| final fontLoader = FontLoader('BookkMyungjo'); | |
| fontLoader.addFont(rootBundle.load(Assets.fonts.bookkMyungjoBold)); | |
| await fontLoader.load(); | |
| final akiraFontLoader = FontLoader('AkiraExpandedDemo'); | |
| akiraFontLoader.addFont(rootBundle.load(Assets.fonts.akiraExpandedDemo)); | |
| await akiraFontLoader.load(); |
| const ReadingChallengeQuizScreen({ | ||
| super.key, | ||
| required this.chapterId, | ||
| required this.challengeId, | ||
| this.showAppBar = true, | ||
| }); |
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.
| onPauseTap: () { | ||
| _timerController.pause(); | ||
| setState(() {}); | ||
| }, | ||
| onResumeTap: () { | ||
| _timerController.resume(); | ||
| setState(() {}); | ||
| }, |
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.
onPauseTap과 onResumeTap 콜백에서 setState를 호출하는 것은 불필요해 보입니다. ReadingChallengeQuizDeepTimeScreen 내부의 버튼들은 CustomCountDownController의 ValueNotifier를 통해 상태 변화를 감지하고 스스로 리빌드됩니다. 불필요한 setState 호출은 위젯 트리의 더 넓은 부분을 리빌드하여 성능에 미미한 영향을 줄 수 있으므로 제거하는 것을 권장합니다.
onPauseTap: () {
_timerController.pause();
},
onResumeTap: () {
_timerController.resume();
}, BaseScreen에 PopScope 추가
- PopScope 위젯으로 전체 Scaffold 감싸서 화면 pop 동작 제어
- canPop() Hook 메서드 추가
- 기본값: true (정상적으로 뒤로가기 허용)
- 하위 클래스에서 오버라이드하여 조건부 제어 가능
- onPopInvoked() Hook 메서드 추가
- pop이 차단되었을 때(didPop = false) 실행되는 콜백
- 필요시 사용자에게 알림 표시 등 추가 동작 구현 가능
- PopScope.onPopInvokedWithResult 사용
- didPop이 false일 때만 onPopInvoked() 호출
ReadingChallengeWrapQuizScreen에 canPop() 구현
- _isLock 상태에 따라 뒤로가기 동작 제어
- _isLock = true: canPop() returns false
- iOS edge swipe back 제스처 차단
- Android 물리 뒤로가기 버튼 차단
- AppBar 뒤로가기 버튼 비활성화 (기존 로직 유지)
- _isLock = false: canPop() returns true
- 모든 뒤로가기 동작 정상 작동
기대 효과
- 딥타임 잠금 활성화 시 사용자가 실수로 화면을 벗어나는 모든 경로 차단
- iOS: edge swipe back 제스처
- Android: 물리/소프트 뒤로가기 버튼
- AppBar: 뒤로가기 버튼
- 독서 집중 시간 중 의도치 않은 화면 이탈 방지
- 사용자 경험 개선
Fixes #224
Summary
리딩챌린지의 퀴즈 확인, 딥타임, 퀴즈 풀기, 정답 확인 화면을 하나의 통합 화면으로 재구성하고, 각 화면의 UI/UX를 개선했습니다.
주요 변경사항
ReadingChallengeQuizWrapScreen 통합 화면 구현
퀴즈 확인 화면 디자인 개선
딥타임 화면 리팩토링
퀴즈 풀기 화면 리팩토링
라우터 간소화
기술적 개선
Test Plan
0117-v2.mov
🤖 Generated with Claude Code