본문 바로가기
프로그래밍/Android

안드로이드 액티비티 생명주기

by Daniel.kwak 2019. 2. 16.

안드로이드 액티비티의 수명주기 콜백의 이해



액티비티 인스턴스가 살아있는동안 안드로이드는 계단식 피라미드와 비슷하게 각 생명주기에 해당하는 메소드를 호출한다. 새로운 액티비티가 생성되면 안드로이드는 액티비티의 생명주기를 점차 상향으로 이동시켜서 resumed에서는 사용자와 상호작용 할 수 있는 상태가 된다. 

액티비티가 소멸될 때 피라미드에서 점차 내려오기 위해 해당 메소드를 호출하게 되며, 경우에 따라 완전히 하향 이동되지 않고 기다린다. (사용자가 다른 앱으로 전환했거나) 이런 경우 액티비티는 다시 피라미드의 최상향으로 이동할 수 있다.(다시 원래 액티비티로 돌아간 경우)

액티비티의 수명주기를 올바르게 구현하면, 다음을 포함하여 여러가지 상황에서도 앱이 제대로 동작하는것을 보장할 수 있다.
  • 사용자가 앱을 사용하는 동안 전화가 오거나, 다른 앱으로 전환할 때 충돌하지 않도록 한다.
  • 사용자가 앱을 활발하게 사용하지 않는 경우, 소중한 시스템 리소스를 반환한다. 
  • 사용자가 앱을 나갔다가 나중에 돌아왔을때 사용자의 진행상태를 손실하지 않도록 한다.
  • 화면이 가로,세로방향으로 전환될 때, 충돌하거나 사용자의 진행상태를 손실하지 않도록 한다.

액티비티의 생애주기동안 세 가지 상태에서는 정적으로 오래동안 유지할 수 있다. 
  • 재개됨(resumed) : 액티비티가 전면에 있으며 사용자와 상호작용 할 수 있다.
  • 일시정지됨(paused) : 이 상태에서는 액티비티가 다른 액티비티로 인해 일부 가려져있다. 이 경우, 전면에 있는 액티비티는 반투명이거나 전체화면을 차지하지 않는다. 일시정지된 액티비티는 사용자 코드를 실행할 수 없다.
  • 정지됨(stopped) : 액티비티가 완전히 가려져서 사용자에게 보이지 않는다. 이 상태는 액티비티가 백그라운드에 있는것으로 간주된다. 정지된 동안 액티비티 인스턴스와 멤버변수가 모두 유지된다.


새로운 액티비티 시작
액티비티 전체 수명주기동안 액티비티 시작을 위한 기본 함수들을 작성하기 위해 onCreate는 반드시 구현해야 한다. onCreate에서 setContentView를 실행하여 사용자 인터페이스 레이아웃을 정의하고, 몇몇 클래스의 변수를 인스턴스화 해야 한다. 

onCreate가 끝나면 onStart , onResume이 연달아 실행된다.(머무르지 않는다)
onCreate는 savedInstanceState라는 매개변수를 가지는데, 액티비티 재생성에 대해 다시 다뤄보자.



액티비티 소멸 
액티비티 생애주기의 마지막 메소드는 onDestroy이다. 안드로이드 시스템에서 액티비티가 메모리에서 완전히 해제되는 신호이기도 하다. 대부분의 액티비티는 onPause와 onStop에서 정리작업을 수행하므로 onDestroy를 수행할 일이 많지 않지만 onCreate에서 실행한 백그라운드 쓰레드나 장시간 수행된 다른 리소스를 종료시키기도 한다. 
*onCreate에서 finish()를 호출하면 onStop이나 onPause를 호출하지 않고 바로 onDestroy를 호출한다. 





액티비티 일시정지 및 재개

안드로이드에서 앱이 다중 창 모드에서 실행되거나, 다이얼로그를 띄우는 경우에는 액티비티가 일시정지(onPause)상태로 진입한다. 부분적으로 보이지만 현재 포커스는 내에 있지 않는 한 일시정지된 상태를 유지한다. 


onPause에는 계속 진행되어서는 안되는 지속적인 작업을 멈추거나, 영구 저장되어야 하는 정보를 유지할 수 있다. 일시 중지된 상태에서 액티비티로 돌아오면(onResume) 액티비티는 재개된다. 



액티비티 일시정지

일시정지된 상태에서는 일반적으로 다음 작업을 수행해야 할 수 있다.

  • 액티비티가 보이는지 확인하고, 보이지 않으면 애니메이션, CPU소비를 야기시키는 작업 중지(다중 창 모드에서는 동영상을 재생해도 됨)
  • 저장하지 않는 변경 내용 커밋(단 사용자가 정보를 계속 유지시키기를 원하는 경우 - 이메일 임시저장)
  • 브로드캐스트와 같은 시스템 리소스, GPS수신, 사용자가 필요로 하지 않는 모든 리소스 해제 (Camera 해제)
또한 데이터베이스 쓰기와 같은 CPU소모가 많은 작업은 액티비티 시각적 전환을 느려지지 않기 위해서라도 onPause에서 수행해서는 안된다.(onStop에서 한다) 실제 정지가 되었더라도 사용자가 다음 대상으로 신속히 넘어가기 위해 onPause의 내용은 가능한 가볍게 유지한다. 


액티비티 재개
일시중지된 상태에서 사용자가 액티비티를 재개하면, onResume이 호출된다. 따라서 onPause에서 중지시켰던 작업들을 재개시키거나, 필요한 다른 초기화 작업도 진행한다. (onPause 때 release되었던 카메라 객체를 onResume에서 초기화)




액티비티 정지 및 재시작

액티비티가 정지 되었다가 재시작하는 몇 가지 시나리오를 살펴보자.
  • 사용자가 최근 앱 창을 열고 다른 앱으로 옮겨갈 때 현재 앱의 액티비티가 정지된다. 사용자가 앱의 런쳐 아이콘을 실행하거나, 최근 앱 목록에서 앱으로 돌아올 때 재시작한다. 
  • 사용자 앱에서 새 액티비티를 시작하는 작업. 두 번째 액티비티가 생성되면 현재 액티비티가 정지되고, Back버튼으로 이전 액티비티가 재시작한다. 
  • 사용자가 앱을 실행하는 동안 전화가 걸려온다. 
*액티비티가 정지되면 액티비티 인스턴스를 시스템 메모리에 유지하기 때문에 onStop을 구현하지 않을 수도 있다. 간단한 앱인 경우 onPause를 사용하여 시스템 리소스를 해제하고 진행중인 작업을 종료시키면 된다. 
*액티비티가 정지되고 재시작할 때 onStop -> onRestart -> onStart -> onResume 이 순서대로 호출된다. 어떤 시나리오든 간에, 시스템은 onStop이 호출되기 전에 항상 onPause를 호출한다. 


액티비티 정지
onStop메소드가 호출된 액티비티는 더 이상 사용자에게 보여지지 않게되고, 사용자에게 필요하지 않은 모든 리소스를 해제해야 한다. 시스템이 메모리가 부족한 경우 onDestroy를 호출하지 않고 액티비티 인스턴스를 종료시킬 수 있기 때문. 따라서 메모리 누수를 야기시키는 리소스는 반드시 onStop에서 해제해야 한다.

액티비티가 정지되면 시스템에는 액티비티 인스턴스가 메모리에 유지되며, 액티비티가 재개되면 다시 호출된다. 다시 호출되어도 기존에 초기화를 했던 구성요소들은 다시 초기화 할 필요는 없다. View또한 현재상태를 기록한다. (EditText에 작성한 내용은 정지-재개 되어도 그대로 유지된다.)


액티비티 시작/재시작

액티비티가 정지되었다가 전면으로 돌아올 때 onRestart 콜백이 실행된다. onStart콜백도 실행된다. onRestart 는 액티비티가 정지되었다가 재개되는 경우에만 호출된다. 따라서 정지된 경우에 한하여 특수복원작업을 onRestart에서 진행한다. 


일반적으로 onStart메소드를 onStop메소드의 상대적인 메소드로 사용해야 하는 이유는 onStop 후 재개될 때 onStart가 불리지만, 액티비티가 처음 실행될 때도 onStart가 호출되기 때문이다. 예를 들어 사용자가 앱을 장시간 떠나있다가 다시 돌아왔을 때 onStart에서는 필요한 시스템 기능이 활성화 되었는지 체크하기에 좋은 곳이다. (GPS활성화 여부 확인 등)

'프로그래밍 > Android' 카테고리의 다른 글

안드로이드 서비스 (2)  (0) 2019.02.18
안드로이드 서비스 (1)  (1) 2019.02.18
액티비티 재생성  (0) 2019.02.16
안드로이드 Notification  (0) 2018.12.07
dp/dip/sp/px 단위와 멀티해상도  (0) 2018.12.07
안드로이드 Firebase Auth / Realtime Databsae  (0) 2018.12.06