Lapisan dan tampilan

Lapisan dan tampilan adalah dua elemen dasar yang merepresentasikan pekerjaan komposisi dan interaksi dengan hardware layar.

Lapisan

Lapisan adalah unit komposisi yang paling penting. Lapisan adalah kombinasi platform dan instance SurfaceControl. Setiap lapisan memiliki serangkaian properti yang menentukan cara interaksinya dengan lapisan lain. Properti lapisan dijelaskan dalam tabel berikut:

Properti Deskripsi
Posisi Menentukan tempat lapisan muncul di tampilannya. Mencakup informasi seperti posisi tepi lapisan dan urutan Z-nya relatif terhadap lapisan lain (apakah harus berada di depan atau di belakang lapisan lain).
Konten Menentukan cara konten yang ditampilkan di lapisan harus disajikan dalam batas yang ditentukan oleh properti posisi. Mencakup informasi seperti pemangkasan (untuk memperluas sebagian konten agar mengisi batas lapisan) dan transformasi (untuk menampilkan konten yang diputar atau dibalik).
Komposisi Menentukan cara lapisan harus disusun dengan lapisan lain. Mencakup informasi seperti mode campuran dan nilai alfa di seluruh lapisan untuk komposisi alfa.
Pengoptimalan Memberikan informasi yang tidak benar-benar diperlukan untuk menggabungkan lapisan dengan benar, tetapi dapat digunakan oleh perangkat Hardware Composer (HWC) untuk mengoptimalkan cara melakukan komposisi. Mencakup informasi seperti area lapisan yang terlihat dan bagian lapisan yang telah diperbarui sejak frame sebelumnya.

Layar

Tampilan adalah unit komposisi penting lainnya. Sistem dapat memiliki beberapa layar dan layar dapat ditambahkan atau dihapus selama operasi sistem normal. Tampilan ditambahkan atau dihapus atas permintaan HWC atau atas permintaan framework. Perangkat HWC meminta agar tampilan ditambahkan atau dihapus saat tampilan eksternal dihubungkan atau dihentikan hubungannya dari perangkat, yang disebut hotplugging. Klien meminta tampilan virtual, yang kontennya dirender ke buffer di luar layar, bukan ke tampilan fisik.

Layar virtual

SurfaceFlinger mendukung tampilan internal (bawaan ponsel atau tablet), tampilan eksternal (seperti televisi yang terhubung melalui HDMI), dan satu atau beberapa tampilan virtual yang membuat output gabungan tersedia dalam sistem. Tampilan virtual dapat digunakan untuk merekam layar atau mengirim layar melalui jaringan. Frame yang dihasilkan untuk tampilan virtual ditulis ke BufferQueue.

Tampilan virtual dapat menggunakan set lapisan yang sama dengan tampilan utama (tumpukan lapisan) atau memiliki set sendiri. Tidak ada VSync untuk tampilan virtual, sehingga VSync untuk tampilan internal memicu komposisi untuk semua tampilan.

Pada implementasi HWC yang mendukungnya, tampilan virtual dapat dikomposisikan dengan OpenGL ES (GLES), HWC, atau GLES dan HWC. Pada penerapan yang tidak mendukung, tampilan virtual selalu dikomposisikan menggunakan GLES.

Studi kasus: screenrecord

Perintah screenrecord memungkinkan pengguna merekam semua yang muncul di layar sebagai file MP4 di disk. Untuk menerapkan hal ini, sistem menerima frame gabungan dari SurfaceFlinger, menuliskannya ke encoder video, lalu menulis data video yang dienkode ke file. Codec video dikelola oleh proses terpisah (mediaserver), sehingga buffer grafis besar harus dipindahkan ke seluruh sistem. Untuk membuatnya lebih menantang, tujuannya adalah merekam video 60 fps pada resolusi penuh. Kunci agar hal ini berfungsi secara efisien adalah BufferQueue.

Class MediaCodec memungkinkan aplikasi menyediakan data sebagai byte mentah dalam buffer, atau melalui permukaan. Saat screenrecord meminta akses ke encoder video, proses mediaserver membuat BufferQueue, menghubungkan dirinya ke sisi konsumen, lalu meneruskan sisi produsen kembali ke screenrecord sebagai platform.

Utilitas screenrecord kemudian meminta SurfaceFlinger untuk membuat tampilan virtual yang mencerminkan tampilan utama (yaitu, memiliki semua lapisan yang sama), dan mengarahkannya untuk mengirim output ke platform yang berasal dari proses mediaserver. Dalam hal ini, SurfaceFlinger adalah produsen buffer, bukan konsumen.

Setelah konfigurasi selesai, screenrecord akan dipicu saat data yang dienkode muncul. Saat aplikasi menggambar, buffer-nya akan berpindah ke SurfaceFlinger, yang menggabungkannya menjadi satu buffer yang dikirim langsung ke encoder video dalam proses mediaserver. Frame lengkap tidak pernah dilihat oleh proses screenrecord. Secara internal, proses mediaserver memiliki caranya sendiri untuk memindahkan buffer yang juga meneruskan data berdasarkan handle, sehingga meminimalkan overhead.

Studi kasus: menyimulasikan layar sekunder

WindowManager dapat meminta SurfaceFlinger untuk membuat lapisan yang terlihat yang SurfaceFlinger bertindak sebagai konsumen BufferQueue. Anda juga dapat meminta SurfaceFlinger untuk membuat tampilan virtual, yang mana SurfaceFlinger bertindak sebagai produsen BufferQueue.

Jika Anda menghubungkan tampilan virtual ke lapisan yang terlihat, loop tertutup akan dibuat tempat layar gabungan muncul di jendela. Jendela tersebut kini menjadi bagian dari output gabungan, sehingga pada pemuatan ulang berikutnya, gambar gabungan di dalam jendela juga menampilkan konten jendela. Untuk melihat cara kerjanya, aktifkan Opsi developer di Setelan, pilih Simulasikan tampilan sekunder, lalu aktifkan jendela. Untuk melihat tampilan sekunder beraksi, gunakan screenrecord untuk merekam tindakan mengaktifkan tampilan, lalu putar kembali frame demi frame.