android/Jetpack

6. ViewModelStore 와 ViewModelStoreOwner

android by kotlin 2022. 11. 18. 01:41

① ViewModelStore 은 ViewModel 객체를 저장하기 위한 클래스입니다. 내부에 ViewModel 을 저장하기 위해 HashMap<String, ViewModel> 을 가지고 있으며, put(ViewModelStore 에 ViewModel 저장), get(ViewModelStore 에 저장된 ViewModel 반환), clear(ViewModelStore 에 저장된 ViewModel 객체 정리) 메서드를 제공합니다. 

 

 

② ViewModelStore 객체는 ViewModelStoreOwner 인터페이스 구현 객체에서 관리합니다.  Activity(ComponentActivity class) 또는 Fragment(Fragment class) 는 ViewModelStoreOwner 인터페이스를 구현한 ViewModelStoreOwner 입니다.

 

public class ComponentActivity extends androidx.core.app.ComponentActivity implements
		...
        LifecycleOwner,
        ViewModelStoreOwner,
		... {
		
	...
    private ViewModelStore mViewModelStore;
	...
	
    @NonNull
    @Override
    public ViewModelStore getViewModelStore() {
        if (getApplication() == null) {
            throw new IllegalStateException("Your activity is not yet attached to the "
                    + "Application instance. You can't request ViewModel before onCreate call.");
        }
        ensureViewModelStore();
        return mViewModelStore;
    }
}

 

public class Fragment implements ComponentCallbacks, OnCreateContextMenuListener, LifecycleOwner,
        ViewModelStoreOwner,
		...{
		
	//Fragment 는 FragmentManagerViewModel class 가 ViewModelStore 를 가지고 있습니다.
    @NonNull
    @Override
    public ViewModelStore getViewModelStore() {
        if (mFragmentManager == null) {
            throw new IllegalStateException("Can't access ViewModels from detached fragment");
        }
        if (getMinimumMaxLifecycleState() == Lifecycle.State.INITIALIZED.ordinal()) {
            throw new IllegalStateException("Calling getViewModelStore() before a Fragment "
                    + "reaches onCreate() when using setMaxLifecycle(INITIALIZED) is not "
                    + "supported");
        }
        return mFragmentManager.getViewModelStore(this);
	
    }
}

 

 

③ ViewModelProvider 생성자에서 ViewModelStoreOwner 객체를 받아서 내부 필드로 저장하고 있다가 get 메서드를 통해 ViewModel 을 요청하면 필드에 저장된 ViewModelStoreOwner 객체에서 관리중인 ViewModelStore 에 요청된 ViewModel 객체가 있는지 확인하고 없다면 생성하여 ViewModelStore 에 저장한 후 반환해줍니다.  

 

 

④ ViewModelProvider 에 전달하는 ViewModelStoreOwner 객체의 종류에 따라(예: MainActivity, SignUpFragment 등등) 생성되는 ViewModel 의 스코프가 결정됩니다. 만약 MainActivity 에 BottomNavigationView 를 사용하여 AFragment, BFragment, CFragment 를 연결하고 각 Fragment 에서 ViewModel 를 생성할 때 ViewModelStoreOwner 로 MainActivity 를 제공했다면 MainActivity 가 관리하는 ViewModelStore 에 ViewModel 이 저장되기 때문에 각 Fragment 들이 파괴되더라도 MainActivity 만 파괴되지 않는다면(Device Configuration 에 의한 파괴를 제외한) ViewModelStore 에서 보관중인 ViewModel 은 파괴되지 않습니다.