-
Notifications
You must be signed in to change notification settings - Fork 0
fix: 버그 수정 및 UX 개선 6종 모음집 #78
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
Merged
The head ref may contain hidden characters: "bugfix/-\uBC84\uADF8\uD1F4\uCE58\uC885\uD569\uBCD1\uC6D0"
Merged
Changes from all commits
Commits
Show all changes
7 commits
Select commit
Hold shift + click to select a range
8dd7d52
style: 상단 하얀 그라데이션 제거
giljihun 614ded6
feat: 탭바 스와이프 백 페이드인 시스템 구현
giljihun 843320c
fix: 뭉치완성뷰에서 X, 보관함 버튼 라우팅 수정
giljihun 916265b
feat: CollectionView에 뭉치탭 시작 여부 플래그 구현
giljihun 95b3cf3
fix: 홈에서 대표뭉치 설정 -> 빈 뭉치면 무한로딩 버그 수정
giljihun 2554619
feat: 뭉치 이미지 저장 - 투명 배경 처리
giljihun e48b692
fix: 홈 화면 리프레시 - 뭉치/키링 수정 후 반영되지 않던 문제
giljihun File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,72 @@ | ||
| // | ||
| // TabBarManager.swift | ||
| // Keychy | ||
| // | ||
| // Created by 길지훈 on 2/11/26. | ||
| // | ||
| // 탭바 표시/숨김을 관리하는 매니저 | ||
| // - show(): 탭바 표시 (애니메이션) | ||
| // - hide(): 탭바 숨김 + 스와이프 백 제스처 연동 설정 | ||
| // - setAlpha(): 탭바 투명도 직접 설정 | ||
| // | ||
|
|
||
| import UIKit | ||
|
|
||
| enum TabBarManager { | ||
|
|
||
| // MARK: - Tab Index | ||
|
|
||
| enum Tab: Int { | ||
| case home = 0 | ||
| case workshop = 1 | ||
| case collection = 2 | ||
| case festival = 3 | ||
| } | ||
|
|
||
| // MARK: - Public Methods | ||
|
|
||
| /// 탭바 표시 (fade in 애니메이션) | ||
| static func show() { | ||
| animate(toAlpha: 1.0) | ||
| } | ||
|
|
||
| /// 탭바 숨김 (fade out) + 스와이프 백 제스처 연동 | ||
| static func hide() { | ||
| animate(toAlpha: 0.0) | ||
| setupSwipeGestureObserver() | ||
| } | ||
|
|
||
| /// 탭바 투명도 직접 설정 (애니메이션 없음) | ||
| static func setAlpha(_ alpha: CGFloat) { | ||
| tabBar?.alpha = alpha | ||
| } | ||
|
|
||
| /// 특정 탭으로 전환 | ||
| static func switchTo(_ tab: Tab) { | ||
| tabBarController?.selectedIndex = tab.rawValue | ||
| } | ||
|
|
||
| // MARK: - Private 변/함 | ||
|
|
||
| private static var tabBarController: UITabBarController? { | ||
| UIApplication.shared.rootViewController?.findTabBarController() | ||
| } | ||
|
|
||
| private static var tabBar: UITabBar? { | ||
| tabBarController?.tabBar | ||
| } | ||
|
|
||
| private static func animate(toAlpha alpha: CGFloat) { | ||
| UIView.animate(withDuration: alpha > 0 ? 0.25 : 0.2) { | ||
| tabBar?.alpha = alpha | ||
| } | ||
| } | ||
|
|
||
| private static func setupSwipeGestureObserver() { | ||
| guard let selectedVC = tabBarController?.selectedViewController, | ||
| let navController = selectedVC.findNavigationController(), | ||
| let gesture = navController.interactivePopGestureRecognizer else { return } | ||
|
|
||
| TabBarSwipeObserver.shared.attach(to: gesture) | ||
| } | ||
| } |
90 changes: 90 additions & 0 deletions
90
Keychy/Keychy/Core/Navigation/TabBar/TabBarSwipeObserver.swift
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,90 @@ | ||
| // | ||
| // TabBarSwipeObserver.swift | ||
| // Keychy | ||
| // | ||
| // Created by 길지훈 on 2/11/26. | ||
| // | ||
| // 스와이프 백 제스처 진행도를 탭바 투명도에 연동 | ||
| // | ||
| // [동작 흐름] | ||
| // 1. TabBarManager.hide() 호출 시 attach(to:) 실행 | ||
| // 2. 스와이프 시작 → handleGesture 호출 | ||
| // 3. 스와이프 진행 → 진행도(0~1)를 탭바 alpha에 반영 | ||
| // 4. 스와이프 완료(50%↑ or 빠른 스와이프) → TabBarManager.show() | ||
| // 5. 스와이프 취소 → TabBarManager.hide() | ||
| // | ||
|
|
||
| import UIKit | ||
|
|
||
| final class TabBarSwipeObserver: NSObject { | ||
|
|
||
| static let shared = TabBarSwipeObserver() | ||
|
|
||
| // MARK: - Constants | ||
|
|
||
| private enum Threshold { | ||
| static let completeProgress: CGFloat = 0.5 // 50% 이상이면 완료 | ||
| static let fastVelocity: CGFloat = 500 // 빠른 스와이프 판정 속도 | ||
| } | ||
|
|
||
| // MARK: - Properties | ||
|
|
||
| private weak var currentGesture: UIGestureRecognizer? | ||
|
|
||
| // MARK: - Init | ||
|
|
||
| private override init() { | ||
| super.init() | ||
| } | ||
|
|
||
| // MARK: - Public | ||
|
|
||
| /// 제스처에 옵저버 연결 | ||
| func attach(to gesture: UIGestureRecognizer) { | ||
| guard currentGesture !== gesture else { return } | ||
|
|
||
| detach() | ||
| currentGesture = gesture | ||
| gesture.addTarget(self, action: #selector(handleGesture(_:))) | ||
| } | ||
|
|
||
| /// 현재 제스처 연결 해제 | ||
| func detach() { | ||
| currentGesture?.removeTarget(self, action: #selector(handleGesture(_:))) | ||
| currentGesture = nil | ||
| } | ||
|
|
||
| // MARK: - Private | ||
|
|
||
| private func calculateProgress(from gesture: UIPanGestureRecognizer) -> CGFloat { | ||
| let translationX = gesture.translation(in: gesture.view).x | ||
| let screenWidth = gesture.view?.window?.screen.bounds.width ?? gesture.view?.bounds.width ?? 393 | ||
| return min(max(translationX / screenWidth, 0), 1) | ||
| } | ||
|
|
||
| private func shouldComplete(progress: CGFloat, velocity: CGFloat) -> Bool { | ||
| progress > Threshold.completeProgress || velocity > Threshold.fastVelocity | ||
| } | ||
|
|
||
| // MARK: - Gesture Handler | ||
|
|
||
| @objc private func handleGesture(_ gesture: UIPanGestureRecognizer) { | ||
| let progress = calculateProgress(from: gesture) | ||
|
|
||
| switch gesture.state { | ||
| case .changed: | ||
| TabBarManager.setAlpha(progress) | ||
|
|
||
| case .ended, .cancelled: | ||
| let velocity = gesture.velocity(in: gesture.view).x | ||
| if shouldComplete(progress: progress, velocity: velocity) { | ||
| TabBarManager.show() | ||
| } else { | ||
| TabBarManager.hide() | ||
| } | ||
|
|
||
| default: | ||
| break | ||
| } | ||
| } | ||
| } | ||
50 changes: 50 additions & 0 deletions
50
Keychy/Keychy/Core/Navigation/TabBar/UIViewController+Find.swift
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,50 @@ | ||
| // | ||
| // UIViewController+Find.swift | ||
| // Keychy | ||
| // | ||
| // Created by 길지훈 on 2/11/26. | ||
| // | ||
| // UIViewController 계층에서 특정 컨트롤러 탐색 | ||
| // | ||
|
|
||
| import UIKit | ||
|
|
||
| extension UIViewController { | ||
|
|
||
| /// 하위 계층에서 UITabBarController 탐색 | ||
| func findTabBarController() -> UITabBarController? { | ||
| if let tabBar = self as? UITabBarController { return tabBar } | ||
|
|
||
| for child in children { | ||
| if let found = child.findTabBarController() { return found } | ||
| } | ||
|
|
||
| return parent?.findTabBarController() | ||
| } | ||
|
|
||
| /// 하위 계층에서 UINavigationController 탐색 | ||
| func findNavigationController() -> UINavigationController? { | ||
| if let nav = self as? UINavigationController { return nav } | ||
|
|
||
| for child in children { | ||
| if let found = child.findNavigationController() { return found } | ||
| } | ||
|
|
||
| return nil | ||
| } | ||
| } | ||
|
|
||
| // MARK: - UIApplication Extension | ||
|
|
||
| extension UIApplication { | ||
|
|
||
| /// 현재 활성 윈도우의 rootViewController | ||
| var rootViewController: UIViewController? { | ||
| connectedScenes | ||
| .compactMap { $0 as? UIWindowScene } | ||
| .first? | ||
| .windows | ||
| .first? | ||
| .rootViewController | ||
| } | ||
| } |
This file was deleted.
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
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.
탭바 스와이프 정로를 감지할 수 있는 건 첨 알았네요...
진짜 아직까지도 UIKit이 이것저것 커스텀하기엔 좋은듯...