Manajemen gerakan: Menangani overlay visual. Bagian 2

Untuk mengantisipasi dimulainya kursus lanjutan dalam pengembangan Android, kami terus berbagi dengan Anda serangkaian terjemahan yang bermanfaat.





Anda membaca artikel kedua dalam seri tentang manajemen gerakan. Anda dapat menemukan bagian pertama di sini .

Di bagian pertama seri, kami mempelajari cara memposisikan aplikasi Anda β€œdari ujung ke ujung” layar. Sayangnya, cara menampilkan ini dapat mengarah pada fakta bahwa beberapa pandangan Anda akan ditempatkan melampaui batas pada area panel sistem, sehingga menyembunyikannya dari pengguna. Pada artikel ini, kita akan mencari cara menambahkan view sedemikian rupa agar tidak mengganggu pengoperasian panel sistem.

Dalam artikel ini, saya akan merujuk pada hal seperti "sistem UI." Ini adalah nama dari setiap antarmuka sistem yang terletak di layar, apakah itu bilah navigasi atau bilah status. Ini juga termasuk bilah notifikasi.

Insets


Istilah insets , sebagai suatu peraturan, menyebabkan ketakutan di antara para pengembang Android, karena suatu hari di masa Android Lollipop mereka selalu mencoba menggunakan area kerja dari status bar. Misalnya, pertanyaan lama tentang StackOverflow ini memiliki jumlah tampilan yang sangat besar.

Insets menunjukkan komponen layar yang bersinggungan dengan antarmuka sistem, misalnya, bilah navigasi atau bilah status. Persimpangan hanya berarti menampilkan di atas konten Anda, tetapi di sini Anda juga bisa mendapatkan informasi tentang gerakan sistem. Kita dapat menggunakan inset untuk mencoba menyelesaikan konflik apa pun, misalnya, dengan memindahkan view dari tepi.

Di Android, insets diwakili oleh kelas WindowInsets , dan di AndroidX oleh kelas WindowInsetsCompat . Dimulai dengan Android Q, kami memiliki 5 jenis inset yang dapat kami gunakan saat membuat layar aplikasi. Jenis inset digunakan tergantung pada situasinya, jadi mari kita lihat setiap jenis secara terpisah dan lihat.

Inset jendela sistem


Metode : getSystemWindowInsets ()

System window inset adalah jenis inset yang paling umum saat ini. Mereka ada dengan API 1 dalam berbagai bentuk dan muncul dalam hierarki view setiap kali UI sistem ditampilkan di atas aplikasi Anda (sepanjang sumbu z). Contoh umum adalah bilah status dan bilah navigasi, dan kadang-kadang keyboard di layar (IME).

Mari kita lihat contoh di mana Anda harus menggunakan insets window sistem . Kami sudah memiliki FloatingActionButton (FAB) , yang terletak di sudut bawah layar dengan lekukan 16dp (sesuai dengan pedoman ).


FAB di aplikasi Google I / O sebelum dikonversi menjadi edge-to-edge

Setelah kami mengikuti langkah 1 dan 2 dari artikel sebelumnya , view kami akan berada di belakang bilah navigasi:


FAB di aplikasi Google I / O, setelah peregangan ke layar penuh

Sekarang Anda melihat bahwa jadwal konferensi Anda terletak di belakang bilah navigasi, dan inilah yang kami tuju - menciptakan pengalaman yang lebih mendalam. Secara lebih rinci tentang cara bekerja dengan daftar / kisi kami akan pertimbangkan nanti.

Mari kita kembali ke contoh. Sekarang Anda melihat bahwa FAB disembunyikan, dan ini pada gilirannya berarti bahwa pengguna tidak akan dapat mengkliknya. Konflik tampilan inilah yang ingin kita hindari. Contohnya terlihat lebih jelas ketika kita menggunakan navigasi tombol (seperti pada gambar), karena panel terletak lebih tinggi. Dalam navigasi gesture dengan adaptasi warna dinamis, ini akan berhasil, tetapi ingat bahwa sistem dapat beralih ke scrim tembus setiap saat, yang dapat mengganggu pengalaman interaksi.
Sekarang adalah saat yang tepat untuk memberi tahu Anda betapa pentingnya menguji aplikasi Anda di semua mode navigasi.

Jadi, bagaimana kita menghadapi konflik visual ini? Pada titik ini, insets jendela sistem ikut bermain. Mereka akan memberi tahu Anda di mana panel sistem berada dalam hierarki tampilan Anda, dan Anda dapat menggunakan nilai-nilai ini untuk memindahkan tampilan lebih jauh dari panel sistem.

Pada contoh di atas, FAB terletak di dekat kanan bawah, sehingga kita dapat menggunakan nilai systemWindowInsets.bottom dan systemWindowInsets.right untuk meningkatkan lekukan view pada setiap sisi untuk memindahkannya lebih jauh dari bilah navigasi.

Setelah kami melakukan ini, kami mendapatkan yang berikut:


Kami akan berbicara tentang bagaimana ini diterapkan sedikit kemudian.

TL DR: Insets jendela sistem paling cocok untuk memindahkan / membuat indentasi views interaktif yang tidak boleh ditutupi oleh panel sistem.

Insets elemen yang dapat disentuh


Metode : getTappableElementInsets ()

Lebih jauh ke bawah daftar, kami memiliki inset elemen tappable yang baru saja muncul di Android Q. Mereka sangat mirip dengan insets window sistem di atas, tetapi mereka merespons berbagai visibilitas bilah navigasi.

TL; DR: seperti untuk tappable element insets : Anda biasanya dapat mengabaikannya dan menggunakan system window insets . Anda dapat melompat ke bagian Gesture Insets di bawah ini atau melanjutkan membaca.

Insets elemen Tappable menentukan inset minimum yang perlu diterapkan dalam tampilan interaktif (tappable). "Minimal" dalam hal ini berarti bahwa nilai yang diterapkan masih dapat menyebabkan konflik dengan panel sistem. Inilah yang membedakan mereka dari insets window sistem , yang selalu bertujuan menghindari konflik dengan panel sistem.

Mari kita gunakan contoh kita dengan FloatingActionButton untuk menunjukkan perbedaan nilai:


Batas-batas bar navigasi ditampilkan dalam warna pink. Hijau - FAB berbatasan dengan indentasi spesifik dari margin bawah.



Ingatlah bahwa Anda tidak akan pernah dapat mencetak nilai dari tabel di atas, karena bilah navigasi dapat diubah ukurannya. Gunakan inset untuk menghindari konflik.

Kita mungkin telah memperhatikan bahwa tappable element insets dan system gesture insets berperilaku sama ketika perangkat dalam mode navigasi tombol. Perbedaan utama menjadi terlihat ketika perangkat menggunakan kontrol gerakan dan adaptasi warna dinamis dihidupkan. Dalam hal ini, bilah navigasi transparan, yang berarti secara teoritis memungkinkan untuk mengatur views interaktif views , sehingga indentasi dari bawah adalah 0.

Terlepas dari kenyataan bahwa insets tidak tahu di mana pandangan harus ditempatkan, jadi dengan menggunakan inset elemen tappable secara teori Anda bisa mendapatkan sesuatu yang serupa:



Itu tidak berfungsi dengan baik, karena view sangat dekat dengan bilah navigasi, yang tidak akan nyaman bagi pengguna.

Dalam prakteknya, hampir semua kasus penggunaan untuk insets elemen tappable lebih baik ditangani dengan insets window sistem .

Gesture insets


Metode : getSystemGestureInsets () dan getMandatorySystemGestureInsets ()

Jenis insets berikutnya yang akan kita lihat adalah gesture insets , ditambahkan dalam versi Android Q. Saya mengingatkan Anda bahwa Android Q memperkenalkan mode kontrol gerakan baru yang memungkinkan pengguna untuk mengontrol perangkat menggunakan dua gerakan sentuh, yang dapat dilakukan sebagai berikut:

  1. Geser secara horizontal dari salah satu ujung layar. Ini akan memicu tindakan kembali.
  2. Geser ke atas dari tepi bawah layar. Ini akan memungkinkan pengguna untuk pergi ke layar beranda atau ke aplikasi yang terakhir digunakan.


Peragaan gerakan di Android Q

Sisipan gesture sistem mencerminkan area jendela tempat gestur sistem lebih diutamakan daripada gestur sentuh dalam aplikasi Anda. Anda mungkin memperhatikan bahwa saya telah menunjukkan dua metode di atas. Hal ini disebabkan oleh fakta bahwa sebenarnya ada dua jenis inset gesture sistem : satu di antaranya menyimpan semua area isyarat, dan yang kedua merupakan subset yang berisi insets gesture sistem wajib.

Insets gerakan sistem


Sebagai permulaan, kami memiliki inset gerakan sistem . Mereka berisi semua area di layar di mana gerakan sistem didahulukan dari gerakan aplikasi Anda. Di Android Q, ini berarti bahwa insets akan terlihat seperti ini, yaitu berisi lekukan dari tepi bawah untuk gerakan untuk kembali ke layar beranda, lekukan di sebelah kiri dan kanan untuk gerakan belakang:

  0 +--------------+ | | | System | 40 | Gesture | 40 | Insets | | | +--------------+ 60 

Kapan inset sistem gesture berguna? insets ini menunjukkan di mana gerakan sistem lebih diutamakan, sehingga Anda dapat menggunakannya untuk secara proaktif memindahkan tampilan yang memerlukan gerakan gesek.

Contohnya termasuk layar yang memanjang dari bawah , gesek dalam game, komidi putar (seperti ViewPager ). Secara umum, Anda dapat menggunakan insets ini untuk bergerak / indentasi dari tepi layar.

Insets gesture sistem wajib


Inset gesture sistem wajib adalah subset inset gesture sistem dan hanya berisi area yang tidak dapat dihapus dari aplikasi (misalnya, nama). Kami melihat sedikit ke depan dalam topik artikel berikutnya, di mana kita akan berbicara tentang penanganan konflik isyarat, tetapi untuk memahami artikel saat ini, ketahuilah bahwa aplikasi dapat menghapus isyarat sistem dari beberapa area layar.

Insets gerakan sistem wajib menunjukkan area layar di mana gerakan sistem selalu diutamakan dan wajib. Di Android Q, satu-satunya area wajib saat ini adalah area gerakan layar beranda di bagian bawah layar. Ini diperlukan agar pengguna selalu dapat keluar dari aplikasi.
Melihat contoh inset gerakan pada perangkat Android Q, Anda akan melihat yang berikut:

  0 0 +--------------+ +--------------+ | | | Mandatory | | System | | System | 40 | Gesture | 40 0 | Gesture | 0 | Insets | | Insets | | | | | +--------------+ +--------------+ 60 60 

Dapat dilihat bahwa inset gesture sistem berisi lekukan di sebelah kiri, kanan, dan bawah, sedangkan inset yang diperlukan hanya berisi lekukan dari bawah sehingga gestur pengembalian ke layar beranda berfungsi normal. Kami akan berbicara lebih banyak tentang menghapus area gerakan di artikel berikutnya.

Inset yang stabil


Metode : getStableInsets ()

Insets yang stabil adalah jenis insets yang terakhir tersedia di Android. Mereka tidak terlalu penting untuk mengelola gerakan, tetapi saya memutuskan itu layak untuk dibicarakan.

Insets stabil merujuk ke insets window sistem , tetapi mereka menunjukkan di mana antarmuka sistem dapat ditampilkan di atas aplikasi Anda, dan bukan di mana ia ditampilkan pada prinsipnya. Insets yang stabil terutama digunakan ketika antarmuka sistem dikonfigurasikan sedemikian rupa sehingga visibilitasnya dapat dihidupkan atau dimatikan, misalnya, ketika menggunakan mode lean back atau immersive (misalnya, game, melihat foto dan pemutar video).

Menangani insets


Saya harap Anda memiliki pemahaman yang lebih baik tentang berbagai jenis inset , jadi sekarang mari kita lihat bagaimana Anda dapat menggunakannya dalam aplikasi Anda.

Metode utama untuk mengakses WindowInsets adalah metode setOnApplyWindowInsetsListener . Mari kita lihat contoh view , yang ingin kita indentasi sehingga tidak muncul di belakang bilah navigasi:

 ViewCompat.setOnApplyWindowInsetsListener(view) { v, insets -> v.updatePadding(bottom = insets.systemWindowInsets.bottom) // Return the insets so that they keep going down the view hierarchy insets } 

Di sini kita cukup mengatur indentasi bawah view ke nilai indentasi bawah inset jendela sistem .

Catatan : Jika Anda melakukan ini pada ViewGroup , Anda mungkin ingin mengatur android:clipToPadding="false" . Ini disebabkan oleh kenyataan bahwa semua jenis gambar klip diindentasi secara default. Atribut ini biasa digunakan dengan RecyclerView , yang akan kita bahas lebih detail di artikel selanjutnya.

Pastikan fungsi mendengarkan Anda idempoten. Jika dipanggil beberapa kali dengan insets yang sama, hasilnya harus sama setiap kali. Contoh fungsi non-idempoten diberikan di bawah ini:

 ViewCompat.setOnApplyWindowInsetsListener(view) { v, insets -> v.updatePadding(bottom = v.paddingBottom + insets.systemWindowInsets.bottom) insets } 

Seharusnya tidak meningkat (ala + =) di lekukan tampilan setiap kali fungsi mendengarkan dipanggil. Jendela insets dapat terjadi kapan saja dan beberapa kali selama masa hierarki tampilan .

Jetpack


Hal lain yang saya sarankan untuk diingat tentang insets adalah penggunaan kelas WindowInsetsCompat dari Jetpack , terlepas dari versi SDK minimum Anda. WindowInsets API telah meningkat dan berkembang selama bertahun-tahun, dan versi compat memberikan konsistensi dan perilaku API di semua level API.

Jika jenis inset baru yang tersedia di Android Q terpengaruh , metode compat adalah sekumpulan nilai yang valid untuk perangkat host di semua level API. Untuk mengakses API baru di Android X, tingkatkan ke androidx.core:core:1.2.0-xxx (sekarang dalam alpha) atau lebih tinggi. Di sini Anda dapat menemukan versi terbaru.

Mari kita melangkah lebih jauh


Metode yang saya sebutkan di atas adalah cara termudah untuk menggunakan API WindowInsets [Compat], tetapi mereka dapat membuat kode Anda terlalu panjang dan tidak jelas. Sebelumnya, saya menulis sebuah artikel di mana saya menjelaskan dalam metode detail yang secara dramatis dapat meningkatkan ergonomi pemrosesan inset jendela menggunakan pengikat adaptor. Anda bisa membacanya di sini.

Pada artikel berikutnya, kita akan belajar bagaimana menangani konflik apa pun yang mungkin timbul antara gerakan aplikasi Anda dan gerakan sistem.

Itu saja. Kami menunggu semua orang di webinar gratis , di mana spesialis kami akan berbicara secara rinci tentang kursus .

Source: https://habr.com/ru/post/id480778/


All Articles