Dưới đây là nội dung cập nhật cho các khu vực hiển thị cụ thể này:
Trang trí hệ thống
Android 10 hỗ trợ thêm tính năng định cấu hình phụ màn hình để hiển thị một số thành phần trang trí hệ thống, chẳng hạn như hình nền, thanh điều hướng, và trình chạy. Theo mặc định, màn hình chính sẽ hiện tất cả các thành phần trang trí hệ thống và màn hình phụ sẽ hiển thị những màn hình được bật (không bắt buộc). Hỗ trợ cho Trình chỉnh sửa phương thức nhập (IME) có thể được đặt riêng biệt với các thành phần trang trí hệ thống khác.
Sử dụng DisplayWindowSettings#setShouldShowSystemDecorsLocked()
để hỗ trợ thêm cho phần trang trí hệ thống trên một màn hình cụ thể hoặc cung cấp
một giá trị mặc định trong /data/system/display_settings.xml
. Ví dụ:
xem phần Cài đặt cửa sổ hiển thị.
Triển khai
DisplayWindowSettings#setShouldShowSystemDecorsLocked()
cũng được hiển thị ở
WindowManager#setShouldShowSystemDecors()
để kiểm thử. Kích hoạt phương thức này
nhằm cho phép trang trí hệ thống không thêm cửa sổ trang trí
thiếu trước đó hoặc xoá nếu chúng đã xuất hiện trước đó. Trong hầu hết
trong trường hợp khác, việc thay đổi hỗ trợ thành phần trang trí hệ thống chỉ có hiệu lực hoàn toàn sau
khởi động lại thiết bị.
Kiểm tra khả năng hỗ trợ thành phần trang trí hệ thống trong cơ sở mã WindowManager
thường trải qua DisplayContent#supportsSystemDecorations()
trong khi
kiểm tra các dịch vụ bên ngoài (chẳng hạn như Giao diện người dùng hệ thống) để kiểm tra xem thanh điều hướng
sẽ xuất hiện) hãy sử dụng WindowManager#shouldShowSystemDecors()
.
Để biết những yếu tố do chế độ cài đặt này kiểm soát, hãy khám phá các điểm gọi của
các phương thức này.
Cửa sổ trang trí giao diện người dùng hệ thống
Android 10 bổ sung tính năng hỗ trợ cửa sổ trang trí hệ thống
chỉ cho thanh điều hướng vì thanh điều hướng là thành phần thiết yếu
để di chuyển giữa các hoạt động và ứng dụng. Theo mặc định, thanh điều hướng sẽ hiển thị
Các thành phần tương tác Quay lại và Trang chủ. Thông tin này chỉ được đưa vào nếu màn hình mục tiêu hỗ trợ
trang trí hệ thống (xem DisplayWindowSettings
).
Thanh trạng thái là một cửa sổ hệ thống phức tạp hơn vì thanh này cũng chứa Ngăn thông báo, Cài đặt nhanh và Màn hình khoá. Trong Android 10, thanh trạng thái không được hỗ trợ trên màn hình phụ. Do đó, thông báo, chế độ cài đặt và tính năng bảo vệ bàn phím đầy đủ chỉ có trên màn hình chính.
Cửa sổ hệ thống Overview/Recents (Tổng quan/Gần đây) chưa được hỗ trợ trên cửa sổ phụ màn hình. Trong Android 10, AOSP chỉ hiển thị mục Recents (Gần đây) trên màn hình mặc định và chứa hoạt động từ mọi màn hình. Khi khởi chạy từ Gần đây, một hoạt động trên màn hình phụ sẽ được đưa lên phía trước trên màn hình đó, theo mặc định. Phương pháp này có một số vấn đề đã biết, chẳng hạn như cập nhật ngay lập tức khi các ứng dụng xuất hiện trên các màn hình khác.
Triển khai
Để triển khai các tính năng bổ sung của Giao diện người dùng hệ thống, nhà sản xuất thiết bị nên sử dụng thành phần giao diện người dùng hệ thống duy nhất theo dõi việc bổ sung/loại bỏ màn hình và trình bày nội dung phù hợp.
Thành phần Giao diện người dùng hệ thống hỗ trợ nhiều màn hình (MD) phải xử lý các trường hợp sau:
- Khởi tạo nhiều màn hình khi khởi động
- Đã thêm màn hình trong thời gian chạy
- Đã xoá màn hình trong thời gian chạy
Khi giao diện người dùng hệ thống phát hiện việc thêm một màn hình trước WindowManager, giao diện người dùng sẽ tạo
một tình huống tương tranh. Bạn có thể tránh điều này bằng cách triển khai lệnh gọi lại tuỳ chỉnh từ
WindowManager cho giao diện người dùng hệ thống khi một màn hình được thêm vào thay vì đăng ký
Các sự kiện DisplayManager.DisplayListener
. Để triển khai tham chiếu,
xem CommandQueue.Callbacks#onDisplayReady
để biết thông tin hỗ trợ về thanh điều hướng
và WallpaperManagerInternal#onDisplayReady
để tạo hình nền.
Ngoài ra, Android 10 còn cung cấp các bản cập nhật sau:
- Lớp
NavigationBarController
kiểm soát mọi chức năng dành riêng cho thanh điều hướng. - Để xem một thanh điều hướng tuỳ chỉnh, hãy xem
CarStatusBar
. TYPE_NAVIGATION_BAR
không còn bị hạn chế ở một miền nào thực thể và có thể dùng cho mỗi màn hình.IWindowManager#hasNavigationBar()
được cập nhật để bao gồm Tham sốdisplayId
chỉ cho Giao diện người dùng hệ thống.
Súng phóng lựu
Trong Android 10, từng màn hình được định cấu hình để hỗ trợ
trang trí hệ thống có ngăn xếp nhà riêng cho các hoạt động của trình chạy cùng với kiểu
WindowConfiguration#ACTIVITY_TYPE_HOME
, theo mặc định. Mỗi màn hình
sử dụng một thực thể riêng biệt của hoạt động của trình chạy.
Hình 1. Ví dụ về trình chạy nhiều màn hình cho
platform/development/samples/MultiDisplay
Hầu hết trình chạy hiện có không hỗ trợ nhiều thực thể và không được tối ưu hoá
cho kích thước màn hình lớn. Ngoài ra, một loại trải nghiệm khác thường được mong đợi
trên màn hình phụ/màn hình ngoài. Để cung cấp một hoạt động riêng cho
Android 10 ra mắt danh mục SECONDARY_HOME
trong ý định
bộ lọc. Các thực thể của hoạt động này được dùng trên tất cả màn hình hỗ trợ hệ thống
trang trí, một trang trí cho mỗi màn hình.
<activity> ... <intent-filter> <category android:name="android.intent.category.SECONDARY_HOME" /> ... </intent-filter> </activity>
Hoạt động phải có chế độ chạy không ngăn chặn nhiều
và cần phải thích ứng với nhiều kích thước màn hình. Chế độ chạy
không được là singleInstance
hoặc singleTask
.
Triển khai
Trong Android 10, RootActivityContainer#startHomeOnDisplay()
tự động chọn thành phần và ý định mong muốn tuỳ thuộc vào màn hình
nơi màn hình chính được khởi chạy. RootActivityContainer#resolveSecondaryHomeActivity()
chứa logic để tra cứu thành phần hoạt động của trình chạy, tuỳ thuộc vào
trình chạy đã chọn và có thể sử dụng chế độ mặc định của hệ thống, nếu cần (xem
ActivityTaskManagerService#getSecondaryHomeIntent()
).
Hạn chế về bảo mật
Ngoài các hạn chế áp dụng cho các hoạt động trên màn hình phụ, để tránh khả năng ứng dụng độc hại tạo màn hình ảo khi Trang trí hệ thống và đọc thông tin nhạy cảm của người dùng trên nền tảng, trình chạy sẽ chỉ xuất hiện trên màn hình ảo do hệ thống sở hữu. Trình chạy không hiển thị nội dung trên màn hình ảo ngoài hệ thống.
Hình nền
Trên Android 10 (trở lên), hình nền được hỗ trợ trên màn hình phụ:
Hình 2. Hình nền động trong nội bộ (bên trên) và bên ngoài màn hình (bên dưới)
Nhà phát triển có thể khai báo việc hỗ trợ cho tính năng hình nền bằng cách cung cấp
android:supportsMultipleDisplays="true"
trong
Định nghĩa XML WallpaperInfo
. Nhà phát triển hình nền cũng
sẽ tải thành phần bằng cách sử dụng ngữ cảnh hiển thị trong
WallpaperService.Engine#getDisplayContext()
.
Khung này sẽ tạo một thực thể WallpaperService.Engine
trên mỗi màn hình, vì vậy, mỗi công cụ đều có bối cảnh giao diện và bối cảnh riêng. Chiến lược phát hành đĩa đơn
nhà phát triển cần đảm bảo rằng mỗi công cụ có thể vẽ một cách độc lập,
các tốc độ khung hình khác nhau, tôn trọng VSYNC.
Chọn hình nền cho từng màn hình
Android 10 không hỗ trợ nền tảng trực tiếp để chọn hình nền
cho từng màn hình. Để thực hiện điều này, giá trị nhận dạng màn hình ổn định là
cần thiết để duy trì cài đặt hình nền trên mỗi màn hình.
Display#getDisplayId()
là biến động, vì vậy không có gì đảm bảo rằng
màn hình thực sẽ có cùng mã nhận dạng sau khi khởi động lại.
Tuy nhiên, Android 10 đã thêm DisplayInfo.mAddress
,
chứa các giá trị nhận dạng ổn định cho màn hình thực tế và có thể dùng cho
trong tương lai. Rất tiếc, vẫn còn quá muộn để triển khai logic
cho Android 10. Giải pháp được đề xuất:
- Dùng API
WallpaperManager
để đặt hình nền. WallpaperManager
lấy từContext
và mỗi đối tượngContext
đều có thông tin về màn hình (Context#getDisplay()/getDisplayId()
). Do đó, bạn có thể lấydisplayId
qua một thực thểWallpaperManager
mà không cần thêm phương thức mới.- Về phía khung, hãy sử dụng
displayId
lấy từ mộtContext
và ánh xạ đối tượng đó với một giá trị nhận dạng tĩnh (chẳng hạn như một cổng của một màn hình thực). Hãy dùng giá trị nhận dạng tĩnh để duy trì hình nền đã chọn.
Giải pháp này sử dụng các phương pháp triển khai hiện có cho bộ chọn hình nền. Nếu được mở trên một màn hình cụ thể và sử dụng đúng ngữ cảnh, thì khi lệnh gọi đặt hình nền, hệ thống có thể tự động xác định màn hình.
Nếu cần đặt hình nền cho một màn hình khác với màn hình hiện tại
màn hình mục tiêu, sau đó tạo một đối tượng Context
mới cho màn hình mục tiêu
(Context#createDisplayContext
) và nhận
Thực thể WallpaperManager
qua màn hình đó.
Hạn chế về bảo mật
Hệ thống sẽ không hiển thị hình nền trên những màn hình ảo mà hệ thống không sở hữu. Nguyên nhân là do lo ngại về bảo mật rằng một ứng dụng độc hại có thể tạo tệp ảo màn hình có hỗ trợ các thành phần trang trí hệ thống và đọc thông báo nhạy cảm với người dùng thông tin khỏi nền tảng (chẳng hạn như ảnh cá nhân).
Triển khai
Trong Android 10, IWallpaperConnection#attachEngine()
và giao diện IWallpaperService#attach()
chấp nhận
displayId
để tạo kết nối trên mỗi màn hình.
WallpaperManagerService.DisplayConnector
đóng gói mỗi màn hình
công cụ hình nền và kết nối. Trong WindowManager, bộ điều khiển hình nền
được tạo cho từng đối tượng DisplayContent
khi tạo thay vì
WallpaperController
duy nhất cho mọi màn hình.
Một số cách triển khai phương thức WallpaperManager
công khai (chẳng hạn như
WallpaperManager#getDesiredMinimumWidth()
) đã được cập nhật để điện toán
và cung cấp thông tin để hiển thị tương ứng.
WallpaperInfo#supportsMultipleDisplays()
và một tham số tương ứng
được thêm vào, để nhà phát triển ứng dụng có thể báo cáo
hình nền đã sẵn sàng cho nhiều màn hình.
Nếu dịch vụ hình nền trên màn hình mặc định không hỗ trợ nhiều màn hình, thì hệ thống sẽ hiện hình nền mặc định trên màn hình phụ màn hình.
Hình 3. Logic dự phòng hình nền cho màn hình phụ