본문 바로가기

안드로이드 Android

안드로이드 개발 (28) ViewLifeCycleOwner

블로그 재작성 시작입니다. jetpack 라이브러리를 사용하다보면 뷰모델 프로바이더를 생성할 때나 라이브 데이타 observe 함수에 매개 변수로 lifeCycleOwner 를 전달해줘야하는 경우가 있습니다.

검색을 하다보면 주로 viewLifeCycleOwner 를 매개변수로 전달하는 예제가 많은데

viewLifeCycleOwner에 대해 알아보도록 하겠습니다.

 

0. viewLifeCycleOwner 란?

 

Fragment 를 사용하다보면 onCreateView() 함수이 호출 될 때, view 를 생성하고

onViewCreated() 함수에서 이미 생성한 view를 사용하는 경우가 많습니다.

 

viewLifeCycleOwner 는 onCreateView() 에서 생성되는 view의 LifeCycle 를 뜻 합니다.

그래서 onCreateView() ~ onDestoryView()  라이프 사이클을 가집니다.

 

  * <ol>
     * <li>{@link Lifecycle.Event#ON_CREATE created} after {@link #onViewStateRestored(Bundle)}</li>
     * <li>{@link Lifecycle.Event#ON_START started} after {@link #onStart()}</li>
     * <li>{@link Lifecycle.Event#ON_RESUME resumed} after {@link #onResume()}</li>
     * <li>{@link Lifecycle.Event#ON_PAUSE paused} before {@link #onPause()}</li>
     * <li>{@link Lifecycle.Event#ON_STOP stopped} before {@link #onStop()}</li>
     * <li>{@link Lifecycle.Event#ON_DESTROY destroyed} before {@link #onDestroyView()}</li>
     * </ol>

 

1. Fragment LifeCycle과 viewLifeCycle의 차이 

 

Fragment LifeCycle은 onAttch ~ onDestroy 의 생명주기를 가지며, 

Fragment ViewLifeCycle 은 createView ~ destoryView 를 가집니다. 

 

Fragment LifeCycle은 프레그먼트가 생성되는 create 과정부터, 프레그먼트가 제거되는 destory 까지 거칩니다.

반면 Fragment ViewLifeCycle은 View 가 생성되는 onCreateView 부터 뷰가 제거되는 onDestoryView 까지만 진행이 됩니다. 

즉, ViewLifeCycle은 Fragment LifeCycle 보다 라이프사이클이 짦습니다.

 

그래서 onCreateView ~ onDestoryView를 제외한 Fragment LifeCycle에서

viewLifeCycleOwner를 호출 할 때, 아래와 같은 IllegalStateException 문구가 뜰것 입니다.

 

   @MainThread
    @NonNull
    public LifecycleOwner getViewLifecycleOwner() {
        if (mViewLifecycleOwner == null) {
            throw new IllegalStateException("Can't access the Fragment View's LifecycleOwner when "
                    + "getView() is null i.e., before onCreateView() or after onDestroyView()");
        }
        return mViewLifecycleOwner;
    }

 

2. viewLifeCycleOwner 를 사용 해야할 때

 

Activity는 onDestory가 호출되지 않은 상황에서 onCreate()가 호출 될일이 없지만

Fragment는 onDestroy 가 호출되지 않은 상태에서 onCreateView() 가 여러 번 호출될 수 있습니다.

만약 Lifecycle 에 따라 호출하는 CallBack 함수가 있다면 해당 LifeCycle이 Fragment 일때,

경우에 따라 fragment Destory 가 되지않았는데 CallBack 함수가 여러번 호출되는 상황을 경험 할 수도 있습니다.

 

//onAttch ~ onDestory
viewModel.liveData.observe(this, { itemId ->
           //LifeCycle이 Destory 되지 않았는데 옵저버 다수 생성 가능성 up
          ...
        })
//onCreateView ~ onDestoryView
viewModel.liveData.observe(viewLifecycleOwner, { itemId ->
           
          ...
        })

 

대표적으로 LiveData의 매개변수로 this(현재 Fragment)를 전달했다면 경우에 따라 Fragment 가 Destory 되지 않았는데 새로운 observer가 등록되어 복수의 Observer가 호출되는 현상이 발생할 수 있습니다. 

 

그래서 과거에 google Android 개발자 len lake님이 일반적으로 UI를 업데이트 용으로

FragmentView LifeCycle를 사용하기를 권장한다는 수정 로그를 남겨 놓기도 했습니다.

 

https://android.googlesource.com/platform/frameworks/support/+/eb89fcf1decf9044f53330ea4bb689d25d2328b1%5E!/fragment/src/main/java/androidx/fragment/app/Fragment.java 

 

Diff - eb89fcf1decf9044f53330ea4bb689d25d2328b1^! - platform/frameworks/support - Git at Google

authorIan Lake Mon Mar 12 12:57:20 2018 -0700

android.googlesource.com

 

Android 를 잠시 놔두고 컴퓨터 기본 지식, 면접 준비, 개인 사업, 댄스 디렉팅 등등 많은 일을 하고 나니 Android에 대한 지식이 많이 잊혀져 가는 것 같았습니다. 최근 다행히도 좋은 지인을 멘토를 둬서 부족한 기본기가 무엇인지 다시 깨닫게 되었고 차츰 고쳐가는 중입니다.

 

이상 viewLifeCycleOwner에 대해 알아 봤습니다.