[UIViewController] ViewController의 생명주기에 대하여 알아보자

2021. 9. 13. 22:02UIKit, H.I.G

728x90

0️⃣ ViewController의 생명주기는 무엇이고, 왜 공부를 해야하는거지?

ViewController의 생명주기에 대해 들어본 적이 있는가?

혹여나 들어본 적이 없다 하더라도, iOS 개발을 하고자 Xcode를 켜본 적이 있다면 적어도 아래 화면을 한 번쯤은 본 적이 있을 것이다.

뷰컨을 만들면 자동으로 생성되는 메서드, ViewDidLoad()

도대체 이 녀석은 어떤 기능을 하길래, Xcode에서 알아서 친절하게 만들어주는 건지 생각을 해본적이 있을까?

이 녀석을 잘 이해하기 위해서는 "ViewController의 생명주기"라는 것을 알아야 한다.
대충 생명주기(Life Cycle)라는 말만 들어도, 무엇인가가 태어나는 순간부터 죽는 순간까지의 주기를 떠올릴 수 있을 것이다.
즉, 여기서는 ViewController의 생명주기이니까 iOS에서 화면을 구성하는 요소인 ViewController가 나타나고부터 사라지기까지의 주기를 의미한다고 생각하면 된다.

💡 ViewController의 생명주기
= iOS에서 뷰가 나타나고부터(=메모리에 할당되고부터) 사라지기(= 메모리에서 해제되기)까지의 주기

viewController의 Life Cycle은 위 그림으로 요약해볼 수 있다.

각 주기의 순서와 직관적인 뜻은 아래와 같다.

참고로 반복되고 있는 will~과 did~ 키워드에 대해서 쉬운 이해를 위해 한번 정리하고 넘어가자면,
will ~할 것이다라는 뜻을 가지고 있고, did는 do의 과거형으로 ~했다의 의미를 지니고 있다는 것만 알아두면 직관적으로 해석이 가능할 것이다.

init (메모리 할당) -> loadView (뷰를 로드) -> viewDidLoad (뷰가 로드 되었다) -> viewWillAppear (뷰가 나타날 것이다)
-> viewDidAppear (뷰가 나타났다) -> viewWillDisappear (뷰가 사라질 것이다) -> viewDidDisappear (뷰가 사라졌다)
-> deinit (메모리 해제)

이제 아래에서 각 주기별로 순서대로 하나씩 알아보겠다.

 

1️⃣ loadView : ViewController에서 사용되는 View를 로드한다.

ViewController는 너무도 당연하게 View를 가지고 있다. (View + Controller = View를 관리하는 역할)

기본적으로 Xcode의 인터페이스 빌더 (Storyboard 또는 Xib)를 사용해 ViewController의 view 작업을 하는 경우, 해당 생명주기 메서드를 직접 호출해서는 안된다고 명시되어 있다. (= You should never call this method directly)
단, Stroyboard를 사용하지 않고 Custom View를 Code로 생성하고자 할 때는 해당 메서드를 오버라이드하여 ViewController에 View를 생성해줄 수 있다.

override func loadView() {
    super.loadView()
    
    let myView = UIView()
    myView.backgroundColor = .white
    view = myView
}

 

2️⃣ viewDidLoad : 뷰가 로드 되었다.

viewDidLoad는 viewController를 생성할 때 기본으로 생성되는 메서드이다.

viewController의 View가 메모리에 로드된 후 호출되며, 메모리에 처음 로딩될 때 "딱 1번"만 자동적으로 호출된다.
(= viewController의 변화와 관련 x, 처음 viewController의 초기 화면 세팅에 관한 작업을 해당 메서드에서 사용하게 된다.)

 

3️⃣ viewWillAppear : 뷰가 나타날 것이다.

이름처럼 뷰가 나타나기 직전에 호출되는 메서드이다.
viewDidLoad와 마찬가지로 뷰의 초기화 역할을 수행할 때 사용된다고 이해하면 된다.

단 차이점은, viewDidLoad가 메모리에 로딩될 때 처음 1번만 자동으로 호출되는 메서드이기 때문에,
화면전환이 이루어진 후, 다시 이 화면으로 돌아왔을 때 처리를 해주고 싶은 것들(ex. View의 업데이트)은 viewWillAppear에 대해 처리를 해줄 수 있겠다.

 

4️⃣ viewDidAppear : 뷰가 나타났다.

뷰가 나타난 직후에 호출되는 메서드이다.

즉, 뷰가 나타났다는 것을 정상적으로 컨트롤러에게 알리는 역할을 하는 것이다.
뷰를 보여준 이후에 추가적으로 필요한 (대표적으로 애니메이션 작업) 것들이 여기에 들어가게 된다.

💡 viewWillAppear와 viewDidAppear에서 알고가야 할 Note
: If a view controller is presented by a view controller inside of a popover, this method is not invoked on the presenting view controller after the presented controller is dismissed.

[무슨 말인고 하면?]
: ViewControllerA가 팝오버로 ViewControllerC를 표시하고 -> viewControllerC.modalPresentationStyle = .popover
ViewControllerC가 모달로 ViewControllerB를 표시하는 상황에서 -> present(ViewControllerB)
ViewControllerB가 해제된다면, ViewControllerC는 생명주기 메서드(viewWillAppear, viewDidApprea)는 다시 뷰가 나타났기 때문에 호출되고, ViewControllerA의 생명주기 메서드는 팝오버 상태이기 때문에 호출되지 않는다.

 

5️⃣ viewWillDisappear : 뷰가 사라질 것이다.

뷰가 사라지기 직전에 호출되는 메서드이다.

잘 사용되지는 않지만, 보통 애니메이션을 중지시키거나 화면이 사라지기 전에 백그라운드에 데이터를 저장해야하는 상황에서 사용된다고 한다.
예를 들어, 사용자의 작업에 의해 뷰가 변경되고, 다시 들어왔을 때 초기 화면으로 되돌려야 하는 경우 이 시점에서 뷰를 초기화시키는 셈!

 

6️⃣ viewDidDisappear : 뷰가 사라졌다.

뷰가 사라지고 난 직후, 호출되는 메서드이다.

사라지고 난 직후이므로, 정상적으로 뷰가 사라졌다는 것을 알리는 역할을 담당하게 된다.

예를 들어 notification을 듣는 행위를 멈추기, 다른 객체의 속성을 observing 하는 것을 멈추기, 디바이스의 센서를 점검하거나 네트워크를 호출하는 행위들은 화면이 사라지고 나서는 필요 없는 작업들이라고 한다. [출처: 이동건의 이유있는 코드]

순서대로 호출되는 메서드!

728x90