Obsługa reklam displayowych

Poniżej znajdziesz informacje o zmianach w obszarach związanych z wyświetlaniem:

Zmień rozmiar aktywności i wyświetlaczy

Aby wskazać, że aplikacja może nie obsługiwać trybu wielu okien ani zmiany rozmiaru, aktywności używają atrybutu resizeableActivity=false. Powszechny Przy zmianie rozmiaru aktywności aplikacje napotykają następujące problemy:

  • Aktywność może mieć inną konfigurację niż aplikacja niewizualne. Częstym błędem jest odczytywanie danych o wyświetlaniu z aplikacji i dodaje kontekst. Zwrócone wartości nie będą dostosowywane do danych dotyczących widocznych obszarów w w którym ma być wyświetlana aktywność.
  • Aktywność może nie obsługiwać zmiany rozmiaru ani awarii, wyświetlać zniekształcony interfejs użytkownika. lub utracą stan z powodu ponownego uruchomienia bez zapisania stanu instancji.
  • Aplikacja może próbować użyć bezwzględnych współrzędnych wejściowych (zamiast tych względem pozycji okna), co może spowodować uszkodzenie danych wejściowych tryb wielu okien.

W Androidzie 7 (lub nowszym) aplikację można skonfigurować resizeableActivity=false, aby zawsze działać w trybie pełnoekranowym. W W tym przypadku platforma zapobiega rozdzielaniu działań, których nie można zmienić, ekranu. Jeśli użytkownik próbuje wywołać w Menu z aplikacjami działanie, którego nie można zmienić gdy platforma jest już w trybie podzielonego ekranu, wyjdzie z niego, uruchamia aktywność, której nie można zmienić, w trybie pełnoekranowym.

Aplikacje, które wprost ustawiają ten atrybut na false w pliku manifestu nie można uruchamiać w trybie wielu okien, chyba że stosowany jest tryb:

  • Ta sama konfiguracja jest stosowana do procesu, który obejmuje wszystkie działania i komponenty bez aktywności.
  • Zastosowana konfiguracja spełnia wymagania CDD dotyczące zgodności z aplikacjami i wyświetlacze.

W Androidzie 10 platforma nadal uniemożliwia aktywności, których nie można zmienić, z trybu podzielonego ekranu. tymczasowo skalowane, jeśli aktywność ma zadeklarowaną stałą orientację lub aspekt współczynnik proporcji. W przeciwnym razie aktywność zmienia rozmiar, aby wypełnić cały ekran – tak jak na Androidzie. 9 i niższych.

Domyślna implementacja stosuje te zasady:

Gdy aktywność zadeklarowana jako niezgodna z trybem wielu okien przez użycia atrybutu android:resizeableActivity oraz gdy to aktywność spełnia jeden z warunków opisanych poniżej, a następnie po zastosowaniu zastosowania musi zmienić konfigurację ekranu, aktywność i proces są zapisywane do oryginalnej konfiguracji, a użytkownik ma możliwość ponownego uruchomienia proces aplikacji, aby używał zaktualizowanej konfiguracji ekranu.

  • ma stałą orientację dzięki zastosowaniu android:screenOrientation
  • Aplikacja ma domyślny maksymalny lub minimalny współczynnik proporcji zgodnie z kierowaniem na poziom interfejsu API lub wyraźnie deklaruje format obrazu

Ta ilustracja pokazuje aktywność, której nie można zmienić, o zadeklarowanym współczynniku proporcji. Po złożeniu urządzenia okno jest pomniejszane, aby pasowało do obszaru. z zachowaniem proporcji obrazu za pomocą odpowiednich czarnych pasów. Dodatkowo opcja ponownego uruchamiania jest udostępniana użytkownikowi za każdym razem, gdy obszar wyświetlania aktywność zostanie zmieniona.

Po rozłożeniu urządzenia sprawdź konfigurację, rozmiar i format obrazu nie zmienia się, ale wyświetla się opcja ponownego uruchomienia aktywności.

Gdy zasada resizeableActivity jest nieskonfigurowana (lub ma wartość true), aplikacja w pełni obsługuje zmianę rozmiaru.

Implementacja

Aktywność bez możliwości zmiany rozmiaru o stałej orientacji lub współczynniku proporcji to tzw. trybu zgodności rozmiaru (SCM). Warunek jest zdefiniowany w ActivityRecord#shouldUseSizeCompatMode() Gdy działanie SCM jest konfiguracji dotyczącej ekranu (np. rozmiaru lub gęstości) jest stała w żądanej konfiguracji zastępowania, więc aktywność nie jest już zależna w bieżącej konfiguracji wyświetlacza.

Jeśli działanie SCM nie może wypełnić całego ekranu, jest wyrównane do góry i wyśrodkowany w poziomie. Granice aktywności są obliczane według wzoru AppWindowToken#calculateCompatBoundsTransformation()

Gdy aktywność w SCM używa innej konfiguracji ekranu niż jej kontener (np. zmieniono rozmiar wyświetlacza lub działanie zostało przeniesione do innego ), ActivityRecord#inSizeCompatMode() ma wartość prawda i SizeCompatModeActivityController (w interfejsie systemu) otrzymuje wywołanie zwrotne, aby wyświetlić przycisk ponownego uruchamiania procesu.

Rozmiary i formaty obrazu

Android 10 obsługuje nowe formaty obrazu od wysokich współczynników długich i cienkich ekranów do 1:1. Aplikacje mogą zdefiniować ApplicationInfo#maxAspectRatio i ApplicationInfo#minAspectRatio ekranu, które da się radzić sobie z czymś.

proporcje dotyczące aplikacji na Androidzie 10

Rysunek 1. Przykładowe formaty aplikacji obsługiwane na Androidzie 10

Implementacje urządzeń mogą mieć ekrany dodatkowe o różnych rozmiarach i rozdzielczości mniejszych niż wymagane przez Androida 9 i mniejszych (minimum 2, 5 cal szerokości lub wysokości, minimum 320 DP dla jednostki reklamowej smallestScreenWidth), ale można umieszczać tylko te aktywności, które obsługują te małe ekrany tam.

Aby udostępnić aplikację, zadeklaruj minimalny obsługiwany rozmiar, który jest mniejszy niż lub równy docelowemu rozmiarowi wyświetlacza. Korzystaj z dokumentów android:minHeight oraz Atrybuty układu aktywności android:minWidth w AndroidManifest.

Zasady wyświetlania

Android 10 oddziela i przesuwa niektóre wyświetlacze zasady z domyślnej implementacji WindowManagerPolicy w PhoneWindowManager do poszczególnych klas, takich jak:

  • Stan wyświetlania i obrót
  • Niektóre klawisze i śledzenie zdarzeń ruchu
  • Interfejs systemu i okna dekoracji

W Androidzie 9 (i starszych wersjach) obsługiwana jest klasa PhoneWindowManager zasady wyświetlania, stan i ustawienia, obrót, ramka okna dekoracji śledzenia konwersji i nie tylko. Android 10 wprowadza większość tych zmian klasy DisplayPolicy, z wyjątkiem śledzenia rotacji, które ma został przeniesiony do DisplayRotation.

Ustawienia okna wyświetlacza

W Androidzie 10 opcje konfiguracji dla poszczególnych wyświetlaczy rozszerzyliśmy ustawienie okienowania na:

  • Domyślny tryb okna wyświetlania
  • Nadmiarowość obrazu
  • Tryb rotacji i rotacji użytkowników
  • Wymuszony rozmiar, gęstość i tryb skalowania
  • Tryb usuwania treści (po wyjęciu wyświetlacza)
  • Obsługa dekoracji systemu i IME

Zajęcia DisplayWindowSettings zawierają te ustawienia: . Są one zapisywane na dysku na /data partycji w display_settings.xml po każdej zmianie ustawienia. Dla: Więcej informacji: DisplayWindowSettings.AtomicFileStorage i DisplayWindowSettings#writeSettings() Producenci urządzeń mogą podać domyślne wartości dla urządzenia w display_settings.xml konfiguracji. Plik znajduje się jednak w lokalizacji /data, przywrócenie danych w przypadku usunięcia przez funkcję czyszczenia może wymagać dodatkowych funkcji logicznych.

Domyślnie Android 10 używa DisplayInfo#uniqueId jako identyfikator wyświetlacza, który jest trwały ustawienia. W przypadku wszystkich wyświetlaczy należy wypełnić pole uniqueId. W ale również na wyświetlaczach fizycznych i sieciowych. Możesz też użyj portu fizycznego wyświetlacza jako identyfikatora, który można ustawić DisplayWindowSettings#mIdentifier Przy każdym zapisie wszystkie ustawienia są zapisane, więc można bezpiecznie zaktualizować klucz używany do wyświetlania wpisu w pamięci masowej. Więcej informacji: Statyczne identyfikatory displayowe.

Ustawienia są zachowywane w katalogu /data na potrzeby danych historycznych . Początkowo służyły one do zachowywania ustawień użytkownika, takich jak: obrót wyświetlacza.

Statyczne identyfikatory displayowe

Android 9 (i starsze wersje) nie udostępniał stabilnych identyfikatorów wyświetlaczy platformy. Po dodaniu wyświetlacza do systemu Poprzednia wartość „Display#mDisplayId” lub „DisplayInfo#displayId” to generowanych dla danego wyświetlacza przez zwiększenie wartości licznika statycznego. Jeśli system użytkownik dodał i usunął ten sam wyświetlacz, wyświetlił się inny identyfikator.

Jeśli po uruchomieniu urządzenia było dostępnych kilka wyświetlaczy, można je było mają przypisane różne identyfikatory w zależności od czasu. Android 9 (oraz wcześniej) obejmował(a) DisplayInfo#uniqueId, miał za mało aby rozróżniać ekrany, ponieważ fizyczne wyświetlacze były określane jako local:0 lub local:1, co reprezentuje z wbudowanym i zewnętrznym wyświetlaczem.

Zmiany w Androidzie 10: DisplayInfo#uniqueId do dodania stabilnego identyfikatora oraz odróżniania lokalnych, sieciowych i sieciowych wirtualnych wyświetlaczy.

Typ wyświetlacza Format
Lokalne
local:<stable-id>
Sieć
network:<mac-address>
Wirtualna
virtual:<package-name-and-name>

Oprócz aktualizacji usługi uniqueId, DisplayInfo.address zawiera DisplayAddress, identyfikator wyświetlania, który jest niezmienny po ponownym uruchomieniu. Na Androidzie 10, DisplayAddress obsługuje fizyczne i wyświetlacze sieciowe. DisplayAddress.Physical zawiera stabilny ciąg wyświetlany identyfikator (taki sam jak w polu uniqueId) i można go utworzyć za pomocą DisplayAddress#fromPhysicalDisplayId()

Android 10 zapewnia też wygodną metodę informacje o porcie (Physical#getPort()). Tej metody można używać w statyczną podstawę do statycznego identyfikowania wyświetlaczy. Jest używane na przykład w DisplayWindowSettings). DisplayAddress.Network zawiera adres MAC i można go utworzyć za pomocą DisplayAddress#fromMacAddress()

Te dodatki pozwalają producentom urządzeń rozpoznawać wyświetlacze w statycznym układzie. konfiguracji na kilku wyświetlaczach oraz do konfigurowania różnych ustawień i funkcji systemu za pomocą statycznych identyfikatorów wyświetlania, np. portów do fizycznego wyświetlacza. Te metody są ukryte i są przeznaczone do użycia wyłącznie system_server

Po przeanalizowaniu identyfikatora wyświetlania HWC (który może być nieprzezroczysty i nie zawsze stabilny), funkcja zwraca (właściwy dla platformy) 8-bitowy numer portu, który identyfikuje fizyczne złącze wyjścia wyświetlacza oraz obiekt blob EDID wyświetlacza. SurfaceFlinger wyodrębnia informacje o producencie lub modelu z EDID do pozwala wygenerować stabilne 64-bitowe identyfikatory wyświetlania dostępne dla platformy. Jeśli ta metoda nie jest obsługiwany lub występują błędy, SurfaceFlinger wraca do starszego trybu MD, gdzie DisplayInfo#address ma wartość null, a Parametr DisplayInfo#uniqueId jest zakodowany na stałe, jak opisano powyżej.

Aby sprawdzić, czy ta funkcja jest obsługiwana, uruchom polecenie:

$ dumpsys SurfaceFlinger --display-id
# Example output.
Display 21691504607621632 (HWC display 0): port=0 pnpId=SHP displayName="LQ123P1JX32"
Display 9834494747159041 (HWC display 2): port=1 pnpId=HWP displayName="HP Z24i"
Display 1886279400700944 (HWC display 1): port=2 pnpId=AUS displayName="ASUS MB16AP"

Korzystanie z więcej niż 2 wyświetlaczy

Android 9 (i starsze wersje), SurfaceFlinger i DisplayManagerService przyjęto, że istnieją maksymalnie 2 wyświetlacze fizyczne o zakodowanych na stałe identyfikatorami 0. oraz 1.

Począwszy od Androida 10, SurfaceFlinger może wykorzystać Interfejs Hardware Composer (HWC) API do generowania stabilnych identyfikatorów wyświetlania, który umożliwia zarządzanie dowolną liczbę fizycznych wyświetlaczy. Więcej informacji: Statyczne identyfikatory displayowe.

Platforma może wyszukać token IBinder dla wyświetlić przez SurfaceControl#getPhysicalDisplayToken po uzyskaniu 64-bitowy identyfikator wyświetlania z SurfaceControl#getPhysicalDisplayIds lub z wydarzenia Hotplug (DisplayEventReceiver).

W Androidzie 10 (i starszych) podstawowy ekran wewnętrzny jest TYPE_INTERNAL i wszystkie wyświetlacze dodatkowe są oznaczone jako TYPE_EXTERNAL niezależnie od typu połączenia. Dlatego dodatkowe ekrany wewnętrzne są traktowane jako zewnętrzne. Aby obejść ten problem, kod na urządzeniu może generować założenia dotyczące DisplayAddress.Physical#getPort, jeśli usługa HWC jest znana, a przydział portów jest znany że logika jest przewidywalna.

To ograniczenie zostało usunięte w Androidzie 11 (i nowszych).

  • W Androidzie 11 pierwszym wyświetlaczem zgłoszonym podczas uruchamiania jest głównym wyświetlaczu. Typ połączenia (wewnętrzne lub zewnętrzne) jest nieistotny. Prawda jest jednak taka, że nie można odłączyć głównego wyświetlacza, zgodnie z tym w praktyce musi to być ekran wewnętrzny. Pamiętaj, że niektóre składane telefony mają kilka wewnętrznych wyświetlaczy.
  • Wyświetlacze dodatkowe są prawidłowo klasyfikowane jako Display.TYPE_INTERNAL lub Display.TYPE_EXTERNAL (dawniej Display.TYPE_BUILT_IN) i Display.TYPE_HDMI) w zależności od ich typu połączenia.

Implementacja

W Androidzie 9 i starszych ekranach wyświetlane są identyfikatory 32-bitowe, gdzie 0 to wyświetlacz wewnętrzny, 1 to wyświetlacz zewnętrzny, [2, INT32_MAX] to wyświetlacze wirtualne HWC, a -1 oznacza nieprawidłowy wyświetlacz lub wyświetlacz niewirtualny.

Począwszy od Androida 10 wyświetlacze będą miały stabilną wersję i trwałe identyfikatory, które umożliwiają SurfaceFlinger i DisplayManagerService śledzić więcej niż dwa wyświetlacze i rozpoznawać wcześniej wyświetlane wyświetlacze. Jeśli HWC obsługuje IComposerClient.getDisplayIdentificationData i udostępnia wyświetlacz danych identyfikacyjnych, SurfaceFlinger analizuje strukturę EDID i przydziela stabilne 64-bitowe identyfikatory wyświetlaczy fizycznych i wirtualnych ekranów HWC. Identyfikatory są wyrażone za pomocą typ opcji, w którym wartość null oznacza nieprawidłowe wyświetlanie lub wirtualny wyświetlacz inny niż HWC wyświetlacz. Bez obsługi HWC SurfaceFlinger wraca do starszego sposobu działania z z większości 2 ekranów.

Zaznaczenie według wyświetlacza

Do obsługi kilku źródeł danych wejściowych kierowanych na poszczególne wyświetlacze w tym samym czasie Android 10 można skonfigurować tak, aktywne okna, najwyżej jedno na wyświetlacz. Jest przeznaczone wyłącznie do stosowania specjalnych typów urządzeń, gdy wielu użytkowników korzysta z tego samego urządzenia czasu i używać różnych metod wprowadzania lub urządzeń, np. Androida Motoryzacja.

Zdecydowanie zalecamy, aby ta funkcja nie była włączona w przypadku na zwykłych urządzeniach, w tym urządzeniach wieloekranowych i takich jak komputery. i aplikacji. Wynika to przede wszystkim z obaw związanych z bezpieczeństwem, które mogą powodować aby się dowiedzieć, które okno ma zaznaczone dane wejściowe.

Wyobraź sobie, że użytkownik wpisuje bezpieczne informacje w polu tekstowym, np. logując się w aplikacji bankowej lub wpisując tekst, który zawiera poufne i informacjami o nich. Złośliwa aplikacja może utworzyć wirtualny wyświetlacz poza ekranem, który ma wykonać działanie, oraz pole do wprowadzania tekstu. Uzasadnione złośliwe działania są skupione i obydwa z nich pokazują aktywny wskaźnik (kursor migający).

Ponieważ jednak dane wejściowe z klawiatury (sprzętu lub oprogramowania) są wprowadzane w tylko najwyższą aktywność (czyli uruchomioną ostatnio aplikację), według tworząc ukryty wirtualny wyświetlacz, szkodliwa aplikacja może pobierać dane wejściowe użytkownika, a nawet w przypadku korzystania z klawiatury programowej na głównym wyświetlaczu.

Użyj formatu: com.android.internal.R.bool.config_perDisplayFocusEnabled

Zgodność

Problem: w Androidzie 9 i starszych wersjach maksymalnie jedno okno w danym momencie.

Rozwiązanie: w rzadkim przypadku, gdy 2 okien z programu ten sam proces, system zaznacza tylko okno, który znajduje się wyżej w porządku warstw. To ograniczenie zostało usunięte w przypadku aplikacji kierowanych na Androida 10. W takiej sytuacji prawdopodobnie obsługują wiele okien jednocześnie.

Implementacja

WindowManagerService#mPerDisplayFocusEnabled kontroluje: i dostępności tej funkcji. W języku: ActivityManager Zamiast globalnego identyfikatora używany jest teraz ActivityDisplay#getFocusedStack() śledzenie w zmiennej. ActivityDisplay#getFocusedStack() określa fokus na podstawie kolejności osi (Z) zamiast zapisywania wartości w pamięci podręcznej. Dzięki temu tylko jedno źródło, WindowManager, potrzebuje śledzenia działań w kolejności na osi Z.

ActivityStackSupervisor#getTopDisplayFocusedStack() zajmuje podobne podejście w przypadkach, w których najbardziej skupiony stos w systemie musi być zidentyfikowana. Stosy są układane od góry do dołu w poszukiwaniu pierwszy odpowiedni stos.

InputDispatcher może teraz mieć wiele zaznaczonych okien (jedna na wyświetlacz). Jeśli zdarzenie wejściowe jest specyficzne dla wyświetlania, jest wysyłane do zaznaczonego okna na odpowiednim wyświetlaczu. W przeciwnym razie jest wysyłany do zaznaczonego okna, na którym użytkownik widzi użytkownik ostatnio kontaktował się z użytkownikiem.

Zobacz InputDispatcher::mFocusedWindowHandlesByDisplay i InputDispatcher::setFocusedDisplay() Aktualizowane są też wybrane aplikacje w). NativeInputManager::setFocusedApplication()

W systemie WindowManager zaznaczone okna są też śledzone oddzielnie. Zobacz DisplayContent#mCurrentFocus i DisplayContent#mFocusedApp i ich zastosowania. Powiązane elementy Metody śledzenia i aktualizacji zostały przeniesione z WindowManagerService do DisplayContent.