안녕하세요! ✋
주니오스입니다.
오늘은 커스텀 탭바를 만들어봄과 동시에 컨테이너 뷰 컨트롤러에 대해서도 학습해 보려고 합니다.
먼저, 아시다시피 뷰 컨트롤러에는 두가지 역할이 있는데요.
바로 컨텐츠를 표시할 UIView를 관리하는 역할인 컨텐츠 뷰 컨트롤러가 있습니다.
그리고 다수의 뷰 컨트롤러들을 자식 뷰 컨트롤러표 보유하며 관리하는 컨테이너 뷰 뷰컨트롤러가 있습니다.
전자의 경우는 익숙하지만, 후자의 경우 조금 어렵더군요.
먼저 커스텀 탭바를 만들어 볼 것인데요 구조는 아래와 같습니다.

오른쪽 UIWindow위에 그려진 것이 디바이스 화면에 표시되는 레이아웃입니다.
아래에 화면을 선택할 수 있는 탭바가 있고, 바로위에 이에 상응하는 화면이 나오게 됩니다.
왼쪽그림에서 우선 가장 바깥쪽에 있는 것이 TabBarContainer로 Scene에 rootViewController입니다.
탭바 컨테이너는 네비게이션 컨테이너를 자식으로 둡니다.
네비게이션 컨테이너와 탭바 컨테이너에 있는 view는 해당 뷰 컨트롤러의 기본 UIView(뷰계층의 루트)입니다. (아시는 그게 맞습니다.)
여기서 주목할 점은 서로다른 뷰 컨트롤러가 하나의 뷰계층을 구성한다는 것입니다.
탭바 컨테이너는 탭바를, 네비게이션 컨트롤러는 탭바위 화면을 구성하고 있습니다.
특정 뷰계층에 다수의 뷰컨트롤러가 개입하려면 부모-자식 관계를 설정해야 합니다.
위 구조에서 네비게이션 컨테이너는 탭바 컨테이너의 자식 뷰컨트롤러입니다.
addChild매서드를 통해서 자식 뷰컨트롤러를 설정할 수 있습니다.
private func setupView() {
// 뷰 컨트롤러들을 배열에 저장해두고 가져오는 식으로 진행
let selectedVC = viewControllers[selectedIndex]
// willMove를 자동으로 호출한다.
// 현재 뷰컨트롤러의 자식뷰컨트롤러를 지정하는 경우에 호출된다
self.addChild(selectedVC)
// ✅ 커스텀 컨테이너 구현시, addChild이후에 반드시 호출해야한다.
selectedVC.didMove(toParent: self)
// 컨테이너의 뷰계층에 selectedVC.view를 추가한다.
view.insertSubview(selectedVC.view, belowSubview: tabBarView)
...
}
위 함수는 특정 탭바위 아이템을 클릭했을 때 화면에 보일 뷰컨트롤러를 업데이트 합니다.
addChild호출 이후 insertSubView가 호출되는 것을 확인할 수 있습니다.
특정 뷰컨트롤러를 삭제하는 경우 아래 함수가 호출됩니다.
private func deleteView() {
guard let prev = previewsIndex else { return }
let previousVC = viewControllers[prev]
previousVC.view.removeFromSuperview()
// ✅ 커스텀 컨테이너 구현시 removeFromParent호출전 willMove를 반드시 호출해야한다.
previousVC.willMove(toParent: nil)
previousVC.removeFromParent()
// 제거후, didMove를 자동으로 호출
}
코드를 보면 willMove, didMove함수를 볼 수 있는데요 아래 설명해 두었습니다.
willMove, didMove에 대해서
뷰 컨트롤러는 자신이 특정 뷰 컨트롤러의 자식 뷰 컨트롤러가 되거나, 그 상태에서 벗어나는 경우
특정 함수를 자동으로 호출합니다.
그것이 willMove와 didMove입니다.
일반적으로 애플에서 구현한 UINavigationController와 같은 뷰 컨트롤러에 포함되는 경우
자동으로 이 함수들이 호출됩니다.
하지만, 위와같이 커스텀으로 컨테이너를 구현하는 경우는 예외사항이 있습니다.
수동으로 해당함수들을 호출해야하는 시점이 있습니다.
addChild | removeFromParent | |
willMove | 자동 | 수동 |
didMove | 수동 | 자동 |
이 부분을 유의해서 구현하시면 됩니다. :D
구현한 커스텀 탭바는 다음과 같습니다.

여기까지 커스텀 탭바를 구현하는데 필요한 코어 개념들을 알아보았습니다.
전체코드가 궁금하시다면 아래 Gist를 참고해 주세요!
감사합니다~
CustomTabBarView(UIKit)
CustomTabBarView(UIKit). GitHub Gist: instantly share code, notes, and snippets.
gist.github.com
'UIKit' 카테고리의 다른 글
[UIKit] UIViewController, modal 화면표시에 대해서(+커스텀) (1) | 2024.09.05 |
---|---|
[UIkit] 키보드 어보이던스(with 카카오톡 채팅방 만들기) (0) | 2024.06.27 |
[UIKit] convert매서드를 이용한 상대 좌표 구하기 (0) | 2024.04.01 |
[UIKit] UIKit 앱실행부터 UIView까지(iOS 13 ⬆) (0) | 2024.03.12 |