A Activity 에 B Fragment 가 있는 상황에서 A Activity 의 복원이 일어나면, A Activity 의 onCreate 보다 B Fragment 의 onViewCreated 가 먼저 호출됩니다. (정확하게는 A Activity super.onCreate 호출 -> B Fragment 의 onViewCreated 호출 -> A Activity onCreate 호출로 진행됩니다)
따라서 A Activity onCreate 에서 어떤 값을 초기화해주고, B 의 onViewCreated 에서 무언가에 접근하는 코드가 있다면 크래시가 발생하게 됩니다. 복원이 아닌 일반적인 경우는 A activity onCreate 이후 B Fragment onViewCreated 가 호출됩니다.
문제가 생겼던 케이스
// activity
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
findNavController(R.id.nav_host_fragment).setGraph(
R.navigation.nav_xxx_graph,
XXXFragmentArgs.Builder()
.setXXX(xxx)
.setXXX(xx)
.build()
.toBundle()
)
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
val navController = findNavController()
binding.toolbar.setupWithNavController(navController) // Crash 발생
}
setupWithNavController 내부에서 navController.getGraph() 를 호출하는데 Activity 에서 아직 setGraph 가 호출되지 않아서 문제가 되었습니다.
위를 해결할 수 있는 방법은 2가지 정도 있는 것 같은데
1. savedInstanceState != null 혹은 isStateSaved() == true 일 때 MainScope().launch 를 활용하여 다음 콜스택으로 넘기거나
2. onActivityCreated 시점으로 문제가 생기는 코드를 이동 시키는 것인데, deprecated 된 라이프 사이클이라 약간 찝찝함이 있는 것 같습니다.
또한 viewModel 에 넣기 애매한 코드를 다루는 경우 많이 생길 수 있는 크래시가 아닐까 싶습니다?.?
그럼 20000 행복한 개발 되세요 :)
'Android > Development Tips' 카테고리의 다른 글
2.4.1 이상 버전에서 Navigation Component 사용할 때 주의점 (0) | 2022.02.23 |
---|---|
DataStore Protocol Buffer 사용시 Tips (0) | 2022.02.06 |
BroadcastReceiver 사용할 때 유의점 (0) | 2021.12.12 |
Coil 썸네일 구현하기 (0) | 2021.11.23 |
안드로이드 하드웨어 비트맵 (0) | 2021.11.20 |