Dokumen ini menjelaskan cara sistem Android mengetahui bahwa aplikasi tidak merespons dan menunjukkan cara menjaga aplikasi Anda tetap responsif.
Terlepas dari seberapa baik kode Anda ditulis, aplikasi masih mungkin akan terasa lambat, hang, berhenti selama jangka waktu yang signifikan, atau memakan waktu terlalu lama untuk memproses input. Jika aplikasi berada di latar depan dan tidak responsif, pengguna akan melihat dialog Aplikasi Tidak Merespons (ANR), seperti dalam gambar 1. Dialog ANR memungkinkan pengguna memaksa keluar aplikasi. Jika tidak berada di latar depan, aplikasi akan dihentikan secara diam-diam. Sangat penting untuk mendesain daya respons ke dalam aplikasi Anda guna meminimalkan dialog ANR.
Pemicu ANR
Umumnya, sistem menampilkan ANR jika aplikasi tidak dapat merespons input pengguna di thread utama—juga dikenal sebagai UI thread—sehingga mencegah sistem memproses peristiwa input pengguna yang masuk.
Misalnya, ANR dapat terjadi jika aplikasi menjalankan operasi I/O pemblokir, seperti akses jaringan, di UI thread. Contoh lain adalah saat aplikasi menghabiskan terlalu banyak waktu untuk membangun struktur dalam memori yang rumit atau menghitung langkah berikutnya dalam game di UI thread.
Di Android, daya respons aplikasi dipantau oleh layanan sistem ActivityManager
dan
WindowManager
. Android menampilkan dialog ANR untuk aplikasi
saat mendeteksi salah satu kondisi berikut:
- Tidak ada respons terhadap peristiwa input—misalnya, peristiwa sentuh layar atau tombol—dalam 5 detik.
BroadcastReceiver
tidak selesai berjalan dalam waktu 10 hingga 20 detik, untuk intent latar depan. Untuk mengetahui informasi selengkapnya, lihat Waktu tunggu penerima siaran habis.
Menghindari ANR
Berikut adalah tips umum untuk menghindari ANR. Untuk detail selengkapnya tentang cara mendiagnosis dan men-debug berbagai jenis ANR, lihat halaman lain di bagian ini.
Pastikan thread utama selalu tidak diblokir, dan gunakan thread secara strategis.
Jangan menjalankan operasi pemblokir atau yang berjalan lama di thread utama aplikasi. Sebagai gantinya, buat thread pekerja dan lakukan sebagian besar pekerjaan di sana.
Cobalah untuk meminimalkan pertentangan kunci antara thread utama dan thread lainnya.
Minimalkan pekerjaan yang tidak terkait dengan UI di thread utama, misalnya, saat menangani siaran atau menjalankan layanan. Setiap metode yang berjalan di UI thread harus melakukan pekerjaan sesedikit mungkin di thread tersebut. Secara khusus, aktivitas harus diminimalkan untuk menyiapkan metode siklus proses utama seperti
onCreate()
danonResume()
. Lihat Ringkasan pekerjaan latar belakang untuk informasi selengkapnya tentang solusi yang tersedia guna menjadwalkan pekerjaan di thread latar belakang dan berkomunikasi kembali dengan UI.Berhati-hatilah saat membagikan kumpulan thread antarkomponen. Jangan gunakan thread yang sama untuk operasi yang berpotensi memblokir dalam waktu lama dan tugas yang mendesak, seperti penerimaan siaran.
Pastikan agar startup aplikasi cepat. Minimalkan operasi lambat atau pemblokir dalam kode startup aplikasi, misalnya, metode yang dijalankan selama inisialisasi dagger.
Jika Anda menggunakan
BroadcastReceiver
, pertimbangkan untuk menjalankan penerima siaran di thread non-utama menggunakanContext.registerReceiver
. Untuk mengetahui informasi selengkapnya, lihat ANR di BroadcastReceiver.- Jika Anda menggunakan
goAsync()
, pastikanPendingResult.finish
dipanggil dengan cepat sebelum waktu tunggu ANR.
- Jika Anda menggunakan
ANR di BroadcastReceiver
Waktu eksekusi BroadcastReceiver
dibatasi karena penerima siaran
ditujukan untuk melakukan pekerjaan kecil dan terpisah di latar belakang, seperti
menyimpan setelan atau mendaftarkan Notification
. Jadi, sebagaimana metode
lain yang dipanggil di UI thread, aplikasi harus menghindari operasi atau penghitungan
yang dapat berjalan lama di penerima siaran. Alih-alih melakukan
tugas yang berjalan lama melalui UI thread, jalankan tugas di latar belakang untuk
dieksekusi nanti. Lihat Ringkasan pekerjaan latar belakang untuk mengetahui informasi selengkapnya tentang kemungkinan solusi.
Masalah umum lainnya dengan objek BroadcastReceiver
terjadi jika objek tersebut terlalu
sering dijalankan. Eksekusi latar belakang yang sering dapat mengurangi jumlah memori
yang tersedia untuk aplikasi lain. Untuk mengetahui informasi selengkapnya tentang cara mengaktifkan dan menonaktifkan
objek BroadcastReceiver
secara efisien, lihat Ringkasan siaran.
Memperkuat daya respons
Umumnya, 100 hingga 200 md adalah batas yang akan membuat pengguna merasakan kelambatan di aplikasi. Berikut adalah tips tambahan untuk membuat aplikasi Anda tampak responsif bagi pengguna:
Jika aplikasi melakukan operasi di latar belakang sebagai respons terhadap input pengguna, tunjukkan bahwa progres sedang berlangsung, seperti dengan
ProgressBar
di UI Anda.Khususnya untuk game, lakukan penghitungan untuk gerakan dalam thread pekerja.
Jika aplikasi Anda memiliki fase penyiapan awal yang memakan waktu, pertimbangkan untuk menampilkan layar pembuka atau merender tampilan utama secepat mungkin. Tunjukkan bahwa pemuatan sedang berlangsung dan isi informasinya secara asinkron. Dalam kedua kasus tersebut, sebaiknya tunjukkan apakah progres sedang berlangsung, sehingga pengguna tidak merasa bahwa aplikasi berhenti.
Gunakan alat performa seperti Perfetto dan CPU Profiler untuk menentukan bottleneck dalam daya respons aplikasi Anda.