계발자 블로그
[JetPack] AAC ViewModel 본문
https://developer.android.com/topic/libraries/architecture/viewmodel?hl=ko
AAC ViewModel이란?
ViewModel이란 Android Jepack의 구성요소 중 하나로, 본래 ViewModel이란 이름은 소프트웨어 개발 디자인 패턴중 하나인 MVVM(Model — View — ViewModel) 디자인 패턴으로부터 파생되었습니다.
MVVM의 관점에서 부르는 ViewModel과 Android Jetpack에 포함된 ViewModel 클래스를 구분하기 위해 흔히 Android Jetpack에 포함된 ViewModel을 Android Architecture Components ViewModel의 약자인 AAC ViewModel이라고 부르기도 합니다.
앱이 사용되고 있는 도중에 여러가지 이유로 Activity가 파괴되고 다시 재생성되는 일이 발생 할 수 있습니다.
그런 경우에 잘 동작하고 있던 Activity는 데이터를 잃어 버리고 다시 onCreate부터 작업을 수행해야 합니다.
예를 들어 스마트폰을 가로로 보게 되면 화면이 전환 되는데 이 때 Activity는 onDestroy가 되고 다시 재생성 되서 데이터를 잃어 버리게 됩니다. 그래서 구글이 제안 한 것이 ViewModel인 것입니다.
ViewModel은 Activity와 독립된 생명주기를 갖고 있습니다.
Activity가 파괴가 되고 재생성 되는 동안에도 ViewModel은 계속 살아있습니다.
앱이 갖고 있어야 하는 정보는 ViewModel에 저장을 해두고 Activity에서는 ViewModel의 데이터를 불러오는 형태로
앱을 구성하면 안정적으로 동작하는 앱을 만들 수 있습니다.
ViewModel은 액티비티가 완전히 종료 될때까지 하나의 LifeCycle을 유지합니다
ViewModel은 왜 필요하지?
MVVM의 관점에서 봤을 때 ViewModel은 View로부터 독립적이며, View가 필요로 하는 데이터만을 소유합니다. 안드로이드 앱 개발시에도 MVVM 디자인 패턴을 적용하면 Activity나 Fragment 같은 UI컨트롤러의 과도한 책임을 분담하여 클래스가 거대해지는 것을 방지하고, 유지보수, 재사용성 그리고 테스트 등을 용이하게 만들어 줍니다.
구글에서도 앱 개발자들에게 MVVM패턴을 사용을 권장하고 있으며, MVVM관점의 ViewModel을 구현할 때 AAC ViewModel을 사용하면 좋습니다.
그럼 ViewModel을 사용하여 화면 전환 시에도 데이터를 유지 하는 코드를 만들어 보겠습니다.
우선 dependency 추가 합니다.
이렇게 하면 Activity는 counter 값을 읽어 오는데 ViewModel을 사용하게 됩니다.
하지만 이렇게 하면 ViewModel을 사용하고는 있지만 onCreate안에 counter 값을 지정하는 로직이 있기 때문에
Activity가 재생성 될 때 마다 다시 100을 돌아가 버리게 됩니다.
이 문제를 해결 하려면 ViewModel을 초기화 할 때 초기 값을 1로 건네주고
나머지 로직에서는 저장된 값을 사용하게 해야 합니다.
ViewModle Provider로 ViewModel 객체를 만들 때 초기값을 전달하는 것을 금지 하기 때문에
Factory Pattern을 사용해야합니다.
ViewModel Provider Factory를 상속 받는 Factory class를 만들어 줍니다.
ViewModel을 만들때 Factory를 통해서 만들게 됩니다 ViewModel을 Factory가 받은 다음에
MainViewModel에 counter를 담아서 다시 ViewModel을 반환하는 형태입니다.
그러면 ViewModel에서 초기값을 전달 받을 수 있게 수정을 해야 합니다.
ViewModel에 전달하고 싶은 초기 값을 Factory에 전달 해주고 ViewModel은 Factory를 같이 받습니다.
ViewModel Provider가 Factory를 통해서 MainViewModel을 생성하도록 했습니다.
그러면 ViewModel이 적용된 counter가 작동을 하게 됩니다.
그러면 화면을 뒤집어도 데이터가 그대로 유지 되는 것을 알 수 있습니다.
위에 코드는 by 키워드를 사용하여 좀 더 간결하게 만들 수 있습니다.
코틀린에서 by 키워드는 위임을 의미합니다.
activity에서 사용 할 때는 activity ktx의 ActivityViewModelLazy의 초기화 작업을 위임하고
fragment에서는 fragment ktx의 FragmentViewModelLazy의 작업이 위임됩니다.
필요한 dependency를 추가합니다.
ViewModel 인스턴스를 Provider를 사용하지 않고 아래처럼 초기화 해주면 됩니다.
'Android' 카테고리의 다른 글
[Android] Intent 사용하기 (0) | 2021.12.07 |
---|---|
[Android] RecyclerView 사용하기 (0) | 2021.11.30 |
[JetPack] Navigation (0) | 2021.11.01 |
LiveData 사용해 보기 (0) | 2021.10.27 |
Room insert 예제 (0) | 2021.10.27 |