본문 바로가기
iOS/Swift

[iOS] RootViewController 변경하는법과 이유

by 안녕주 2022. 4. 16.

안녕하세요 안녕주입니다!

오늘은 RootViewController를 변경하는 법과 이유에 대해 기록해 보려고 합니다.

먼저 RootViewController를 변경하는 이유는 아래와 같습니다.

 

로그인을 먼저하고 나서 메인화면으로 가는 플로우가 있다고 생각해봅시다!

아래의 마지막 뷰에서 다음버튼을 누르면 메인 화면으로 이동하는 데요

 

메인화면에서 다시 로그인을 하고싶어져서 로그인 화면으로 갔다가 다시 로그인하고 메인화면으로 가고...

그리고 이 과정을 여러번 반복하면 어떻게 될까요? 뷰 컨트롤러의 스택이 엄청 쌓이겠죠..?

(로그인화면 - 완료 화면 - 메인 화면 - 로그인 화면 - 완료 화면 - 메인 화면 - 로그인 화면 - 완료 화면 - 메인 화면..)

 

로그인 - 회원가입 화면 흐름에서 메인화면으로 전환시 기존에 쌓여있는 뷰 컨트롤러 스택을 어떻게 할지 고민할 필요가 생깁니다..!

스택이 계속 해서 쌓이게 되면 메모리 사용량이 증가하게 되고, 결국엔 앱이 죽게됩니다..🫠

 

 

그래서 우리는 RootViewController를 변경해서 스택이 계속해서 쌓이는 것을 방지해야해요!

iOS13 이전에는 UI LifeCycle관련된 것들이 AppDelegate에 있었는데, 그 이후부터는 Scene Delegate에서 UI LifeCycle을 관리하면서 구글링해본 결과들과 많이 다르더라고요..! 그래서 헷갈리실 분들을 위해 정리합니다!

 

 

그전에 알면 좋은 개념(1) UIWindow

우리는 SceneDelegate에서 var window 프로퍼티를 통해서 rootViewController에 접근 할 수 있습니다.

먼저 UIWindow와 window(구 keyWindow)의 개념부터 알아볼까요?

 

UIWindow는 사용자 인터페이스에 배경을 제공하고, 중요한 이벤트 처리 행동을 제공하는 객체입니다.

스크린에 나타나는 모든 View는 Window로 묶여 있습니다. Windows는 ViewController를 사용하여 반향 변경을 구현하고, 앱 작동의 기본요소인 다른 많은 작업을 수행합니다.

iOS앱은 모든 View들의 컨테이너 역할을 하는 UIWindow인스턴스를 하나 가지는데,(SceneDelegate에 정의되어있다) UIWindow는 UIView의 하위클래스 이므로 Window는 그 자체가 View라고 할 수 있습니다.

요약하자면, UIWindow는 UIView의 하위클래스라는것..!

 

window(구 keyWindow)는 UIWindow입니다

 

 

(1) SceneDelegate 에서 rootViewController 변경하는 함수 작성

SceneDelegate에는 window가 선언되어 있습니다. window를 사용해서 rootViewController 변경!

  • option의 .transitionCrossDissolve 를 사용해서 전화효과를 줄 수 있음!
func changeRootVC(_ vc:UIViewController, animated: Bool) {
    guard let window = self.window else { return }
    window.rootViewController = vc // 전환
    
    UIView.transition(with: window, duration: 0.2, options: [.transitionCrossDissolve], animations: nil, completion: nil)
  }

 

(2) 완료뷰에서 메인뷰로 갈때 RootViewController 변경

완료 뷰에서 메인뷰로 이동할때 RootViewController를 변경해줄 차례입니다!

SceneDelegate에 만들어둔 changeRootVC를 사용해서 instaTBC라는 이름의 메인뷰를 RootViewController로 변경!

let tabbar = UIStoryboard.init(name: "TabBar", bundle: nil)
      guard let instaTBC = tabbar.instantiateViewController(withIdentifier: "InstaTBC") as? InstaTBC else {return}
      
      (UIApplication.shared.connectedScenes.first?.delegate as? SceneDelegate)?.changeRootVC(instaTBC, animated: false)

 

 

 

이번 작업에서 필요한 생각 및 개념은

  1. RootViewController를 왜 변경해야하는가
  2. ViewController 계층 구조 및 스택 생각하기
  3. UIWindow, window(구 keyWindow) 개념
  4. SceneDelegate

공부할 때 도움이 될 링크는 아래에 두겠습니다!

[iOS] AppDelegate와 SceneDelegate

iOS ) UIWindow. 그리고 UIView

[iOS] window 속성에 접근하기, RootViewController 변경하기

[iOS] NavigationController RootView 변경

 

'iOS > Swift' 카테고리의 다른 글

[iOS] 화면 전환 방식 push vs present  (3) 2022.04.15
[iOS] Any, AnyObject, nil  (0) 2022.03.07
[iOS] ARC  (0) 2022.02.20
[iOS] SOLID 원칙 in Swift  (0) 2022.02.19
[iOS] 의존성 주입 DI  (2) 2022.02.19

댓글