Tahapan siklus proses Aktivitas

1. Sebelum memulai

Dalam codelab ini, Anda akan mempelajari bagian dasar Android: siklus proses aktivitas.

Selama masa aktifnya, aktivitas bertransisi, dan terkadang kembali ke, berbagai status. Transisi status ini dikenal sebagai siklus proses aktivitas.

Di Android, aktivitas adalah titik entri untuk berinteraksi dengan pengguna.

Sebelumnya, satu aktivitas akan menampilkan satu layar di aplikasi. Dengan praktik terbaik saat ini, satu aktivitas mungkin menampilkan beberapa layar dengan menukarnya sesuai kebutuhan.

Siklus proses aktivitas mencakup pembuatan aktivitas hingga penghancurannya, saat sistem mengklaim kembali resource aktivitas tersebut. Saat pengguna masuk dan keluar dari aktivitas, setiap aktivitas berganti-ganti status dalam siklus proses aktivitas.

Sebagai developer Android, Anda perlu memahami siklus proses aktivitas. Jika aktivitas Anda tidak merespons perubahan status siklus proses dengan benar, aplikasi Anda dapat menghasilkan bug aneh, perilaku yang membingungkan bagi pengguna, atau menggunakan terlalu banyak resource sistem Android. Memahami siklus proses Android dan merespons perubahan status siklus proses dengan benar adalah bagian penting dari pengembangan Android.

Prasyarat

  • Pengetahuan tentang apa itu aktivitas dan cara membuatnya di aplikasi
  • Mengetahui fungsi metode onCreate() aktivitas dan jenis operasi yang dilakukan dalam metode tersebut

Yang akan Anda pelajari

  • Cara mencetak informasi logging ke Logcat
  • Dasar-dasar siklus proses Activity, dan callback yang dipanggil saat aktivitas berpindah antar-status
  • Cara mengganti metode callback siklus proses untuk menjalankan operasi pada waktu yang berbeda di dalam siklus proses aktivitas

Yang akan Anda bangun

  • Memodifikasi aplikasi awal bernama Dessert Clicker untuk menambahkan informasi logging yang ditampilkan di Logcat
  • Mengganti metode callback siklus proses dan perubahan log pada status aktivitas.
  • Menjalankan aplikasi dan mencatat informasi logging yang muncul saat aktivitas dimulai, dihentikan, dan dilanjutkan.
  • Menerapkan rememberSaveable untuk mempertahankan data aplikasi yang mungkin hilang jika konfigurasi perangkat berubah.

2. Ringkasan Aplikasi

Dalam codelab ini, Anda akan menggunakan aplikasi awal yang disebut Dessert Clicker. Di Dessert Clicker, setiap kali pengguna mengetuk makanan penutup di layar, aplikasi akan "membeli" makanan penutup untuk pengguna. Aplikasi mengupdate nilai dalam tata letak untuk:

  • Jumlah makanan penutup yang "dibeli"
  • Total pendapatan untuk makanan penutup "yang dibeli"

245d0bdfc09f4d54.png

Aplikasi ini berisi beberapa bug yang terkait dengan siklus proses Android. Misalnya, dalam keadaan tertentu, aplikasi mereset nilai makanan penutup ke 0. Memahami siklus proses Android akan membantu Anda memahami penyebab terjadinya masalah ini, serta cara memperbaikinya.

Mendownload kode awal

Di Android Studio, buka folder basic-android-kotlin-compose-training-dessert-clicker.

3. Mempelajari metode siklus proses dan menambahkan logging dasar

Setiap aktivitas memiliki tahapan yang dikenal sebagai siklus proses. Istilah ini merupakan kiasan untuk siklus hidup tanaman dan hewan, seperti siklus hidup kupu-kupu—keadaan kupu-kupu yang berbeda menunjukkan pertumbuhannya, berawal dari telur, ulat, kepompong, kupu-kupu, hingga mati.

Siklus Hidup Kupu-kupu - pertumbuhan dari telur, ulat, kepompong, kupu-kupu, hingga mati.

Demikian pula, siklus proses aktivitas terdiri dari berbagai status yang dapat dilalui oleh aktivitas, dari saat aktivitas pertama kali diinisialisasi hingga dihancurkan, yang pada saat itu sistem operasi (OS) akan mengklaim kembali memorinya. Biasanya, titik entri program adalah metode main(). Namun, aktivitas Android dimulai dengan metode onCreate(); metode ini akan setara dengan tahap telur dalam contoh di atas. Anda sudah menggunakan aktivitas berkali-kali di sepanjang kursus ini, dan Anda mungkin mengenali metode onCreate(). Saat pengguna memulai aplikasi, berganti-ganti aktivitas, serta melakukan navigasi di dalam dan di luar aplikasi Anda, status aktivitas akan berubah.

Diagram berikut menampilkan semua status siklus proses aktivitas. Seperti yang terlihat dari namanya, status ini menyatakan status aktivitas. Perlu diperhatikan bahwa, tidak seperti siklus proses kupu-kupu, aktivitas dapat berganti-ganti status di sepanjang siklus proses, bukan hanya bergerak ke satu arah.

ca808edb1c95f07a.png

Sering kali, Anda ingin mengubah beberapa perilaku, atau menjalankan beberapa kode, saat status siklus proses aktivitas berubah. Oleh karena itu, class Activity itu sendiri, dan subclass Activity seperti ComponentActivity, menerapkan sekumpulan metode callback siklus proses. Android mengaktifkan callback ini saat aktivitas berpindah dari satu status ke status lainnya, dan Anda dapat mengganti metode tersebut dalam aktivitas Anda sendiri untuk menjalankan tugas sebagai respons terhadap perubahan status siklus proses tersebut. Diagram berikut menampilkan status siklus proses beserta callback yang bisa diganti.

Skema Siklus Proses Aktivitas

Penting untuk mengetahui kapan Android memanggil callback yang dapat diganti dan tindakan yang harus dilakukan di setiap metode callback, tetapi kedua diagram ini rumit dan bisa membingungkan. Dalam codelab ini, Anda tidak hanya membaca arti setiap status dan callback, tetapi juga melakukan beberapa tugas penyelidikan dan mewujudkan pemahaman Anda tentang siklus proses aktivitas Android.

Langkah 1: Periksa metode onCreate() dan tambahkan logging

Untuk mengetahui aktivitas siklus proses Android, sebaiknya ketahui waktu pemanggilan berbagai metode siklus proses. Informasi ini membantu Anda mengidentifikasi masalah yang terjadi di aplikasi Dessert Clicker.

Cara mudah untuk menentukan informasi ini adalah dengan menggunakan fungsi logging Android. Logging memungkinkan Anda menulis pesan singkat ke konsol saat aplikasi berjalan dan menggunakannya untuk melihat saat callback yang berbeda dipicu.

  1. Jalankan aplikasi Dessert Clicker, lalu ketuk gambar makanan penutup beberapa kali. Perhatikan perubahan nilai dari Makanan penutup yang terjual dan jumlah total uang dalam dolar.
  2. Buka MainActivity.kt dan periksa metode onCreate() untuk aktivitas ini:
override fun onCreate(savedInstanceState: Bundle?) {
    // ...
}

Dalam diagram siklus proses aktivitas, Anda mungkin mengenali metode onCreate(), karena telah menggunakan callback ini sebelumnya. Ini adalah satu metode yang harus diimplementasikan setiap aktivitas. Metode onCreate() menjadi tempat wajib untuk melakukan inisialisasi satu kali untuk aktivitas Anda. Misalnya, dalam onCreate(), Anda memanggil setContent(), yang menentukan tata letak UI aktivitas.

Metode Siklus Proses onCreate

Metode siklus proses onCreate() dipanggil satu kali, tepat setelah aktivitas diinisialisasi—saat OS membuat objek Activity baru di memori. Setelah onCreate() dijalankan, aktivitas dianggap telah dibuat.

  1. Tambahkan konstanta berikut di tingkat teratas MainActivity.kt, di atas deklarasi class class MainActivity.

Akan lebih baik jika Anda mendeklarasikan konstanta TAG dalam file Anda karena nilainya tidak akan berubah.

Untuk menandainya sebagai konstanta waktu kompilasi, gunakan const saat mendeklarasikan variabel. Konstanta waktu kompilasi adalah nilai yang diketahui selama kompilasi.

private const val TAG = "MainActivity"
  1. Dalam metode onCreate(), tepat setelah panggilan ke super.onCreate(), tambahkan baris berikut:
Log.d(TAG, "onCreate Called")
  1. Impor class Log jika perlu (tekan Alt+Enter, atau Option+Enter pada Mac, lalu pilih Import.) Jika Anda mengaktifkan impor otomatis, proses ini akan terjadi secara otomatis.
import android.util.Log

Class Log menulis pesan ke Logcat. Logcat merupakan konsol untuk mencatat pesan. Pesan dari Android tentang aplikasi Anda akan muncul di sini, termasuk pesan yang Anda kirim secara eksplisit ke log dengan metode Log.d() atau metode class Log lainnya.

Ada tiga aspek penting dari instruksi Log:

  • Prioritas pesan log, yaitu seberapa penting pesan. Dalam hal ini, Log.v() mencatat pesan panjang ke dalam log. Metode Log.d() menulis pesan debug. Metode lain di class Log mencakup Log.i() untuk pesan informasi, Log.w() untuk peringatan, dan Log.e() untuk pesan error.
  • Log tag (parameter pertama), dalam hal ini adalah "MainActivity". Tag adalah string yang memungkinkan Anda menemukan pesan log dengan lebih mudah di Logcat. Tag biasanya berupa nama class.
  • Log pesan yang sebenarnya, yang disebut msg (parameter kedua), adalah string pendek, yang dalam kasus ini adalah "onCreate Called".

a4ff4aa74384ff6.png

  1. Kompilasi dan jalankan aplikasi Dessert Clicker. Anda tidak akan melihat perbedaan perilaku di aplikasi saat mengetuk makanan penutup. Di bagian bawah layar Android Studio, klik tab Logcat.

ed03d4bb1f020995.png

  1. Di jendela Logcat, ketik tag:MainActivity pada kolom penelusuran.

961ea44c4b9ee3c.png

Logcat dapat berisi banyak pesan dan sebagian besar tidak berguna bagi Anda. Anda dapat memfilter entri Logcat dengan berbagai cara, tetapi menggunakan penelusuran adalah cara termudah. Anda telah menggunakan MainActivity sebagai tag log dalam kode. Oleh karena itu, Anda dapat menggunakan tag tersebut untuk memfilter log. Pesan log Anda berisi tanggal dan waktu, tag log Anda, nama paket (com.example.dessertclicker), dan pesan yang sebenarnya. Karena pesan ini muncul di log, Anda tahu bahwa onCreate() telah dieksekusi.

Langkah 2: Terapkan metode onStart()

Metode siklus proses onStart() dipanggil tepat setelah onCreate(). Setelah onStart() berjalan, aktivitas Anda akan terlihat di layar. Tidak seperti onCreate(), yang hanya dipanggil sekali untuk menginisialisasi aktivitas Anda, onStart() dapat dipanggil oleh sistem beberapa kali dalam siklus proses aktivitas Anda.

a357d2291de472d9.png

Perlu diketahui bahwa onStart() dipasangkan dengan metode siklus proses onStop() yang sesuai. Jika pengguna memulai aplikasi Anda lalu kembali ke layar utama perangkat, aktivitas tersebut akan dihentikan dan tidak lagi terlihat di layar.

  1. Di Android Studio, dengan MainActivity.kt terbuka dan kursor ada di dalam class MainActivity, pilih Code > Override Methods... atau tekan Control+O. Dialog akan muncul dan menampilkan daftar panjang berisi semua metode yang dapat Anda ganti di class ini.

11ff93bee1c3940f.png

  1. Mulai masukkan onStart untuk menelusuri metode yang benar. Untuk men-scroll ke item yang cocok berikutnya, gunakan panah bawah. Pilih onStart() dari daftar, lalu klik OK untuk menyisipkan kode pengganti boilerplate. Kode terlihat seperti contoh berikut:
override fun onStart() {
    super.onStart()
}
  1. Di dalam metode onStart(), tambahkan pesan log:
override fun onStart() {
    super.onStart()
    Log.d(TAG, "onStart Called")
}
  1. Kompilasi dan jalankan aplikasi Dessert Clicker, dan buka panel Logcat.
  2. Ketikkan tag:MainActivity di kolom penelusuran untuk memfilter log. Perhatikan bahwa metode onCreate() dan onStart() dipanggil satu demi satu, dan aktivitas Anda akan terlihat di layar.
  3. Tekan tombol Layar Utama di perangkat, lalu gunakan layar Terbaru untuk kembali ke aktivitas. Perhatikan bahwa aktivitas dilanjutkan dari tempat terakhirnya, dengan semua nilai yang sama, dan onStart() dicatat dalam log untuk kedua kalinya di Logcat. Perhatikan juga bahwa metode onCreate() tidak dipanggil lagi.
2024-02-20 10:30:00.231  5684-5684  MainActivity            com.example.dessertclicker           D  onCreate Called
2024-02-20 10:30:00.278  5684-5684  MainActivity            com.example.dessertclicker           D  onStart Called
2024-02-20 10:30:39.020  5684-5684  MainActivity            com.example.dessertclicker           D  onStart Called

Langkah 3: Menambahkan laporan log lainnya

Pada langkah ini, Anda akan menerapkan logging untuk semua metode siklus proses lainnya.

  1. Ganti sisa metode siklus proses di MainActivity Anda dan tambahkan laporan log untuk setiap metode, seperti yang ditunjukkan dalam kode berikut:
override fun onResume() {
    super.onResume()
    Log.d(TAG, "onResume Called")
}

override fun onRestart() {
    super.onRestart()
    Log.d(TAG, "onRestart Called")
}

override fun onPause() {
    super.onPause()
    Log.d(TAG, "onPause Called")
}

override fun onStop() {
    super.onStop()
    Log.d(TAG, "onStop Called")
}

override fun onDestroy() {
    super.onDestroy()
    Log.d(TAG, "onDestroy Called")
}
  1. Kompilasi dan jalankan lagi aplikasi Dessert Clicker dan periksa Logcat.

Perhatikan bahwa kali ini, selain onCreate() dan onStart(), ada pesan log untuk callback siklus proses onResume().

2024-02-20 10:33:36.033  5789-5789  MainActivity            com.example.dessertclicker           D  onCreate Called
2024-02-20 10:33:36.073  5789-5789  MainActivity            com.example.dessertclicker           D  onStart Called
2024-02-20 10:33:36.075  5789-5789  MainActivity            com.example.dessertclicker           D  onResume Called

Saat aktivitas dimulai dari awal, Anda akan melihat ketiga callback siklus proses ini dipanggil secara berurutan:

  • onCreate() saat sistem membuat aplikasi.
  • onStart() membuat aplikasi terlihat di layar, tetapi pengguna belum dapat berinteraksi dengan aplikasi.
  • onResume() membawa aplikasi ke latar depan, dan pengguna kini dapat berinteraksi dengannya.

Terlepas dari namanya, metode onResume() akan dipanggil saat startup meskipun tidak ada yang dapat dilanjutkan.

Skema Siklus Proses Aktivitas

4. Mempelajari kasus penggunaan siklus proses

Setelah menyiapkan aplikasi Dessert Clicker untuk logging, Anda siap untuk mulai menggunakan aplikasi dan mempelajari cara callback siklus proses dipicu.

Kasus penggunaan 1: Membuka dan menutup aktivitas

Anda memulai dengan kasus penggunaan yang paling dasar, yaitu memulai aplikasi untuk pertama kalinya lalu menutup aplikasi.

  1. Kompilasi dan jalankan aplikasi Dessert Clicker jika belum berjalan. Seperti yang Anda lihat, callback onCreate(), onStart(), dan onResume() dipanggil saat aktivitas dimulai pertama kali.
2024-02-20 10:33:36.033  5789-5789  MainActivity            com.example.dessertclicker           D  onCreate Called
2024-02-20 10:33:36.073  5789-5789  MainActivity            com.example.dessertclicker           D  onStart Called
2024-02-20 10:33:36.075  5789-5789  MainActivity            com.example.dessertclicker           D  onResume Called
  1. Ketuk cupcake beberapa kali.
  2. Ketuk tombol Kembali yang ada di perangkat.

Perhatikan dalam Logcat bahwa onPause() dan onStop() dipanggil dalam urutan tersebut.

2024-02-20 10:34:41.974  5789-5789  MainActivity            com.example.dessertclicker           D  onPause Called
2024-02-20 10:34:42.411  5789-5789  MainActivity            com.example.dessertclicker           D  onStop Called

Dalam hal ini, menggunakan tombol Kembali akan menyebabkan aktivitas (dan aplikasi) dihapus dari layar dan dipindahkan ke bagian belakang tumpukan aktivitas.

OS Android mungkin menutup aktivitas Anda jika kode Anda memanggil metode finish() aktivitas secara manual atau jika pengguna menutup aplikasi secara paksa. Misalnya, pengguna dapat menutup atau keluar dari aplikasi secara paksa di layar Terbaru. OS mungkin juga dapat menghentikan aktivitas Anda jika aplikasi tidak digunakan dalam waktu yang lama. Android melakukannya untuk menghemat masa pakai baterai dan untuk mengklaim kembali resource yang digunakan aplikasi sehingga tersedia untuk aplikasi lain. Ini hanyalah beberapa contoh alasan sistem Android menghancurkan aktivitas Anda. Ada kasus tambahan saat sistem Android menghancurkan aktivitas Anda tanpa memberikan peringatan.

Kasus penggunaan 2: Bernavigasi dari dan kembali ke aktivitas

Setelah memulai aplikasi lalu menutupnya, Anda telah melihat sebagian besar status siklus proses saat aktivitas dibuat untuk pertama kalinya. Anda juga telah melihat sebagian besar status siklus proses yang dilewati saat aktivitas ditutup. Namun saat pengguna berinteraksi dengan perangkat Android, mereka berpindah antar-aplikasi, kembali ke layar utama, memulai aplikasi baru, dan menangani gangguan karena aktivitas lain seperti panggilan telepon.

Aktivitas Anda tidak benar-benar ditutup setiap kali pengguna keluar dari aktivitas tersebut:

  • Jika aktivitas Anda tidak lagi terlihat di layar, status ini dikenal sebagai memindahkan aktivitas ke latar belakang. Kebalikannya adalah saat aktivitas berada di latar depan atau di layar.
  • Saat pengguna kembali ke aplikasi Anda, aktivitas yang sama akan dimulai ulang dan akan terlihat lagi. Bagian siklus proses ini disebut siklus proses aplikasi yang terlihat.

Jika berada di latar belakang, aplikasi Anda seharusnya tidak aktif berjalan karena ingin mempertahankan resource sistem dan masa pakai baterai. Anda menggunakan siklus proses Activity dan callback untuk mengetahui waktu pemindahan aplikasi ke latar belakang sehingga Anda dapat menjeda operasi yang sedang berlangsung. Kemudian, Anda akan memulai ulang operasi tersebut saat aplikasi muncul di latar depan.

Pada langkah ini, Anda melihat siklus proses aktivitas saat aplikasi muncul di latar belakang dan kembali lagi ke latar depan.

  1. Saat aplikasi Dessert Clicker sedang berjalan, klik cupcake beberapa kali.
  2. Tekan tombol Layar Utama di perangkat dan amati Logcat di Android Studio. Saat Anda kembali ke layar utama, aplikasi tersebut tidak akan dimatikan, tetapi akan tetap berjalan di latar belakang. Perhatikan bahwa metode onPause() dan onStop() dipanggil.
2024-02-20 10:35:26.832  5789-5789  MainActivity            com.example.dessertclicker           D  onPause Called
2024-02-20 10:35:27.233  5789-5789  MainActivity            com.example.dessertclicker           D  onStop Called

Saat onPause() dipanggil, aplikasi tidak lagi memiliki fokus. Setelah onStop(), aplikasi tidak lagi akan terlihat di layar. Meskipun aktivitas dihentikan, objek Activity masih ada di memori di latar belakang. Android OS belum menghancurkan aktivitas. Pengguna mungkin kembali ke aplikasi. Jadi karena alasan ini, Android menyimpan resource aktivitas Anda.

c470ee28ab7f8a1a.png

  1. Gunakan layar Terbaru untuk kembali ke aplikasi. Pada emulator, layar Terbaru dapat diakses oleh tombol sistem persegi yang ditampilkan pada gambar di bawah.

Perhatikan dalam Logcat bahwa aktivitas dimulai ulang dengan onRestart() dan onStart(), lalu dilanjutkan dengan onResume().

bc156252d977e5ae.png

2024-02-20 10:36:05.837  5789-5789  MainActivity            com.example.dessertclicker           D  onRestart Called
2024-02-20 10:36:05.839  5789-5789  MainActivity            com.example.dessertclicker           D  onStart Called
2024-02-20 10:36:05.842  5789-5789  MainActivity            com.example.dessertclicker           D  onResume Called

Saat aktivitas kembali ke latar depan, metode onCreate() tidak akan dipanggil lagi. Objek aktivitas tidak dimusnahkan sehingga tidak perlu dibuat lagi. Sebagai ganti onCreate(), metode onRestart() dipanggil. Perhatikan ketika sekarang aktivitas kembali ke latar depan, jumlah Makanan penutup yang terjual tetap dipertahankan.

  1. Mulai dengan minimal satu aplikasi selain Dessert Clicker sehingga ada beberapa aplikasi di layar Terbaru perangkat.
  2. Munculkan layar Terbaru dan buka aktivitas terbaru lainnya. Kemudian, kembali ke aplikasi terbaru dan pindahkan Dessert Clicker ke latar depan.

Perhatikan bahwa di sini Anda melihat callback yang juga Anda lihat di Logcat saat Anda menekan tombol Layar Utama. onPause() dan onStop() dipanggil saat aplikasi beralih ke latar belakang, lalu onRestart(), onStart(), dan onResume() dipanggil saat aplikasi kembali.

Metode ini dipanggil saat aplikasi berhenti dan berpindah ke latar belakang atau saat aplikasi dimulai ulang dan kembali ke latar depan. Jika Anda perlu melakukan beberapa pekerjaan di aplikasi selama proses ini, ganti metode callback siklus proses yang relevan.

Kasus penggunaan 3: Menyembunyikan sebagian aktivitas

Anda telah mempelajari bahwa saat aplikasi dimulai dan onStart() dipanggil, aplikasi akan terlihat di layar. Saat onResume() dipanggil, aplikasi akan mendapatkan fokus pengguna–yaitu, pengguna dapat berinteraksi dengan aplikasi. Bagian dari siklus proses saat aplikasi sepenuhnya ada di layar dan memiliki fokus pengguna disebut masa aktif latar depan.

Saat aplikasi berpindah ke latar belakang, fokus akan hilang setelah onPause(), dan aplikasi tidak lagi terlihat setelah onStop().

Perbedaan antara fokus dan visibilitas itu penting. Ada kemungkinan aktivitas terlihat sebagian di layar, tetapi tidak memiliki fokus pengguna. Pada langkah ini, Anda melihat satu kasus saat aktivitas terlihat sebagian, tetapi tidak memiliki fokus pengguna.

  1. Dengan aplikasi Dessert Clicker masih berjalan, klik tombol Bagikan di kanan atas layar.

Aktivitas berbagi muncul di paruh bawah layar, tetapi aktivitas tersebut juga masih terlihat di paruh atas.

677c190d94e57447.pngca6285cbbe3801cf.png

  1. Periksa Logcat dan perhatikan bahwa hanya onPause() yang dipanggil.
2024-02-20 10:36:42.886  5789-5789  MainActivity            com.example.dessertclicker           D  onPause Called

Dalam kasus penggunaan ini, onStop() tidak dipanggil karena aktivitas masih terlihat sebagian. Namun, aktivitas tersebut tidak mendapatkan fokus pengguna, dan pengguna tidak dapat berinteraksi dengannya—aktivitas "berbagi" yang ada di latar depan mendapatkan fokus pengguna.

Mengapa perbedaan ini penting? Gangguan dengan onPause() saja biasanya berlangsung dalam waktu singkat sebelum kembali ke aktivitas atau membuka aktivitas atau aplikasi lain. Anda biasanya ingin terus mengupdate UI sehingga bagian aplikasi lainnya tidak akan berhenti berfungsi.

Kode apa pun yang berjalan di onPause() akan memblokir aplikasi lain agar tidak ditampilkan. Jadi, pastikan kode dalam mode onPause() selalu ringan. Misalnya, jika panggilan telepon masuk, kode dalam onPause() dapat menunda notifikasi panggilan masuk.

  1. Klik di luar dialog berbagi untuk kembali ke aplikasi, dan perhatikan bahwa onResume() dipanggil.

Baik onResume() maupun onPause() harus memiliki fokus. Metode onResume() dipanggil saat aktivitas mendapatkan fokus, dan onPause() dipanggil saat aktivitas kehilangan fokus.

5. Mempelajari perubahan konfigurasi

Ada kasus lain dalam mengelola siklus proses aktivitas yang penting untuk dipahami: bagaimana perubahan konfigurasi memengaruhi siklus proses aktivitas Anda.

Perubahan konfigurasi terjadi saat status perangkat berubah secara drastis sehingga cara termudah bagi sistem untuk menyelesaikan perubahan adalah dengan benar-benar menonaktifkan dan membangun ulang aktivitas. Misalnya, jika pengguna mengubah bahasa perangkat, seluruh tata letak mungkin perlu diubah untuk mengakomodasi arah teks dan panjang string yang berbeda. Jika pengguna mencolokkan perangkat ke dok atau menambahkan keyboard fisik, tata letak aplikasi mungkin perlu memanfaatkan ukuran tampilan atau tata letak yang berbeda. Selain itu juga, jika orientasi perangkat berubah—jika perangkat diputar dari mode potret ke mode lanskap atau kembali sebaliknya—tata letak mungkin perlu diubah agar sesuai dengan orientasi baru. Mari lihat perilaku aplikasi dalam skenario ini.

Callback siklus proses terakhir yang ditunjukkan adalah onDestroy(), yang dipanggil setelah onStop(). Callback ini dipanggil tepat sebelum aktivitas dihancurkan. Hal ini dapat terjadi saat kode aplikasi memanggil finish(), atau sistem perlu menghancurkan dan membuat ulang aktivitas karena perubahan konfigurasi.

Perubahan konfigurasi menyebabkan onDestroy() dipanggil

Rotasi layar adalah salah satu jenis perubahan konfigurasi yang menyebabkan aktivitas dihentikan dan dimulai ulang. Untuk menyimulasikan perubahan konfigurasi ini dan memeriksa efeknya, selesaikan langkah-langkah berikut:

  1. Kompilasikan dan jalankan aplikasi Anda.
  2. Pastikan kunci rotasi layar di emulator dinonaktifkan.
  3. Putar perangkat atau emulator ke mode lanskap. Anda dapat memutar emulator ke kiri atau kanan menggunakan tombol rotasi.
  4. Periksa Logcat dan pahami bahwa saat dihentikan, aktivitas akan memanggil onPause(), onStop(), dan onDestroy(), dalam urutan tersebut.
2024-02-20 10:37:57.078  5987-5987  MainActivity            com.example.dessertclicker           D  onPause Called
2024-02-20 10:37:57.087  5987-5987  MainActivity            com.example.dessertclicker           D  onStop Called
2024-02-20 10:37:57.102  5987-5987  MainActivity            com.example.dessertclicker           D  onDestroy Called

Kehilangan data di rotasi perangkat

  1. Kompilasi dan jalankan aplikasi Anda, lalu buka Logcat.
  2. Klik cupcake beberapa kali dan perhatikan bahwa makanan penutup terjual dan total pendapatan tidak nol.
  3. Pastikan kunci rotasi layar di emulator dinonaktifkan.
  4. Putar perangkat atau emulator ke mode lanskap. Anda dapat memutar emulator ke kiri atau kanan menggunakan tombol rotasi.

f745d0e2697415fd.png

  1. Periksa output di Logcat. Filter output di MainActivity.
2024-02-20 10:39:22.724  6087-6087  MainActivity            com.example.dessertclicker           D  onCreate Called
2024-02-20 10:39:22.752  6087-6087  MainActivity            com.example.dessertclicker           D  onStart Called
2024-02-20 10:39:22.753  6087-6087  MainActivity            com.example.dessertclicker           D  onResume Called
2024-02-20 10:39:40.508  6087-6087  MainActivity            com.example.dessertclicker           D  onPause Called
2024-02-20 10:39:40.540  6087-6087  MainActivity            com.example.dessertclicker           D  onStop Called
2024-02-20 10:39:40.549  6087-6087  MainActivity            com.example.dessertclicker           D  onDestroy Called
2024-02-20 10:39:40.582  6087-6087  MainActivity            com.example.dessertclicker           D  onCreate Called
2024-02-20 10:39:40.584  6087-6087  MainActivity            com.example.dessertclicker           D  onStart Called
2024-02-20 10:39:40.585  6087-6087  MainActivity            com.example.dessertclicker           D  onResume Called

Perhatikan bahwa saat perangkat atau emulator memutar layar, sistem akan memanggil semua callback siklus proses untuk menghentikan aktivitas. Kemudian, saat aktivitas dibuat ulang, sistem akan memanggil semua callback siklus proses untuk memulai aktivitas.

Saat perangkat diputar, dan aktivitas dihentikan serta dibuat ulang, aktivitas dimulai ulang dengan nilai default—gambar hidangan penutup, jumlah makanan penutup yang terjual, dan total pendapatan direset ke nol.

Untuk mempelajari alasan nilai ini direset dan cara mengoreksinya, Anda perlu mempelajari siklus proses composable dan cara mempelajarinya untuk mengamati dan mempertahankan statusnya.

Siklus proses composable

UI aplikasi Anda awalnya dibuat dari menjalankan fungsi composable dalam proses yang disebut Komposisi.

Saat status aplikasi Anda berubah, rekomposisi dijadwalkan. Rekomposisi adalah saat Compose mengeksekusi fungsi composable yang statusnya mungkin telah berubah dan membuat UI yang diupdate. Komposisi diupdate untuk mencerminkan perubahan ini.

Satu-satunya cara untuk membuat atau mengupdate Komposisi adalah dengan komposisi awal dan rekomposisi berikutnya.

Fungsi composable memiliki siklus prosesnya sendiri yang tidak bergantung pada siklus proses Aktivitas. Siklus prosesnya terdiri dari peristiwa: memasuki Komposisi, merekomposisi 0 kali atau lebih, lalu keluar dari Komposisi.

Agar Compose dapat melacak dan memicu rekomposisi, perlu mengetahui kapan status telah berubah. Untuk menunjukkan kepada Compose bahwa objek harus melacak status objek, objek harus berjenis State atau MutableState. Jenis State tidak dapat diubah dan hanya dapat dibaca. Jenis MutableState dapat diubah dan memungkinkan baca dan tulis.

Anda telah melihat dan menggunakan MutableState di aplikasi Lemonade dan aplikasi Tip Time di codelab sebelumnya.

Untuk membuat variabel revenue yang dapat diubah, Anda mendeklarasikannya menggunakan mutableStateOf. 0 adalah nilai default awalnya.

var revenue = mutableStateOf(0)

Meskipun ini cukup untuk membuat Compose memicu rekomposisi saat nilai pendapatan berubah, namun tidak cukup untuk mempertahankan nilai yang diperbarui. Setiap kali dijalankan ulang, composable akan menginisialisasi ulang nilai pendapatan ke nilai default awal 0.

Untuk menginstruksikan Compose agar mempertahankan dan menggunakan kembali nilainya selama rekomposisi, Anda harus mendeklarasikannya dengan remember API.

var revenue by remember { mutableStateOf(0) }

Jika nilai revenue berubah, Compose menjadwalkan semua fungsi composable yang membaca nilai ini untuk rekomposisi.

Meskipun Compose mengingat status pendapatan selama rekomposisi, Compose tidak mempertahankan status ini selama perubahan konfigurasi. Agar Compose dapat mempertahankan status selama perubahan konfigurasi, Anda harus menggunakan rememberSaveable.

Untuk praktik dan informasi tambahan, lihat codelab Pengantar status di Compose.

Menggunakan rememberSaveable untuk menyimpan nilai di seluruh perubahan konfigurasi

Anda menggunakan fungsi rememberSaveable untuk menyimpan nilai yang diperlukan jika Android OS menghancurkan dan membuat ulang aktivitas.

Untuk menyimpan nilai selama rekomposisi, Anda perlu menggunakan remember. Gunakan rememberSaveable untuk menyimpan nilai selama rekomposisi DAN perubahan konfigurasi.

Menyimpan nilai menggunakan rememberSaveable akan memastikan bahwa nilai tersedia saat aktivitas dipulihkan, jika diperlukan.

  1. Di MainActivity, update grup yang terdiri dari lima variabel yang saat ini menggunakan remember untuk rememberSaveable.
var revenue by remember { mutableStateOf(0) }
...
var currentDessertImageId by remember {
    mutableStateOf(desserts[currentDessertIndex].imageId)
}
var revenue by rememberSaveable { mutableStateOf(0) }
...
var currentDessertImageId by rememberSaveable {
    mutableStateOf(desserts[currentDessertIndex].imageId)
}
  1. Kompilasikan dan jalankan aplikasi Anda.
  2. Klik cupcake beberapa kali dan perhatikan bahwa makanan penutup terjual dan total pendapatan tidak nol.
  3. Putar perangkat atau emulator ke mode lanskap.
  4. Perhatikan bahwa setelah aktivitas dihancurkan dan dibuat ulang, gambar makanan penutup, makanan penutup yang terjual, dan total pendapatan dipulihkan ke nilai sebelumnya.

6. Kode solusi

7. Ringkasan

Siklus proses aktivitas

  • Siklus proses aktivitas merupakan rangkaian status yang dilalui selama aktivitas bertransisi. Siklus proses aktivitas dimulai saat Android OS pertama kali membuat aktivitas dan berakhir saat OS menghancurkan aktivitas.
  • Saat pengguna bernavigasi antar-aktivitas serta di dalam dan di luar aplikasi, setiap aktivitas berpindah-pindah status dalam siklus proses aktivitas.
  • Setiap status dalam siklus proses aktivitas memiliki metode callback yang sesuai dan dapat Anda ganti di class Activity. Rangkaian inti dari metode siklus proses adalah: onCreate(), onRestart(), onStart(), onResume(), onPause(), onStop(), onDestroy().
  • Untuk menambahkan perilaku yang terjadi saat proses transisi aktivitas Anda ke status siklus proses, ganti metode callback status.
  • Untuk menambahkan metode penggantian kerangka ke class di Android Studio, pilih Code > Override Methods... atau tekan Control+O.

Melakukan Logging dengan Log

  • Dengan Logging API Android, dan khususnya class Log, Anda dapat menulis pesan singkat yang ditampilkan di Logcat dalam Android Studio.
  • Gunakan Log.d() untuk menulis pesan debug. Metode ini menggunakan dua argumen: tag log yang biasanya berupa nama class, dan pesan log yang berupa string singkat.
  • Gunakan jendela Logcat di Android Studio untuk melihat log sistem, termasuk pesan yang Anda tulis.

Perubahan konfigurasi

  • Perubahan konfigurasi terjadi saat status perangkat berubah secara drastis sehingga cara termudah bagi sistem untuk menyelesaikan perubahan adalah dengan menghancurkan dan membangun ulang aktivitas.
  • Contoh paling umum dari perubahan konfigurasi adalah bila pengguna memutar perangkat dari mode potret ke mode lanskap, atau sebaliknya. Perubahan konfigurasi juga dapat terjadi saat bahasa perangkat berubah atau pengguna mencolokkan keyboard hardware.
  • Saat terjadi perubahan konfigurasi, Android akan memanggil semua callback penonaktifan siklus proses aktivitas. Android lalu memulai ulang aktivitas dari awal, menjalankan semua callback startup siklus proses.
  • Saat Android menghentikan aplikasi karena perubahan konfigurasi, aplikasi akan memulai ulang aktivitas dengan onCreate().
  • Untuk menyimpan nilai yang perlu dipertahankan saat terjadi perubahan konfigurasi, deklarasikan variabelnya dengan rememberSaveable.

Pelajari lebih lanjut