Gdy aktywność przejmie kontrolę nad obsługą wszystkich elementów wstawianych, możesz użyć interfejsów API Compose, aby sprawdzić, czy treść nie jest zasłonięta, a elementy interaktywne nie nakładają się na interfejs systemu. Te interfejsy API synchronizują też układ aplikacji ze zmianami w marginesach.
Obsługa wcięć za pomocą dopełnienia lub modyfikatorów rozmiaru
Jest to na przykład najprostsza metoda zastosowania wcięć do treści całej aplikacji:
override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) enableEdgeToEdge() setContent { Box(Modifier.safeDrawingPadding()) { // the rest of the app } } }
Ten fragment kodu stosuje wcięcia okna safeDrawing jako dopełnienie wokół całej zawartości aplikacji. Zapewnia to, że elementy interaktywne nie będą nakładać się na interfejs systemu, ale oznacza też, że żadna część aplikacji nie będzie rysowana za interfejsem systemu, aby uzyskać efekt od krawędzi do krawędzi. Aby w pełni wykorzystać całe okno, musisz precyzyjnie dostosować miejsca, w których mają być stosowane wcięcia, w przypadku poszczególnych ekranów lub komponentów.
Wszystkie te typy wstawek są animowane automatycznie za pomocą animacji IME, które zostały przeniesione do API 21. W konsekwencji wszystkie układy korzystające z tych wcięć są automatycznie animowane w miarę zmiany wartości wcięć.
Aby dostosować układy funkcji kompozycyjnych, możesz użyć 3 sposobów obsługi wstawek:
Modyfikatory dopełnienia
Modifier.windowInsetsPadding(windowInsets: WindowInsets) stosuje podane wcięcia okna jako dopełnienie, działając tak samo jak Modifier.padding.
Na przykład Modifier.windowInsetsPadding(WindowInsets.safeDrawing) stosuje bezpieczne wstawki rysunkowe jako dopełnienie po wszystkich 4 stronach.
Dostępnych jest też kilka wbudowanych metod narzędziowych dla najpopularniejszych typów wcięć.
Modifier.safeDrawingPadding() to jedna z takich metod, która jest odpowiednikiem funkcji Modifier.windowInsetsPadding(WindowInsets.safeDrawing). Istnieją analogiczne modyfikatory dla innych typów wcięć.
Modyfikatory rozmiaru wstawki
Te modyfikatory stosują ilość odcięć okna, ustawiając rozmiar komponentu na rozmiar odcięć:
Stosuje początkową stronę elementu WindowInsets jako szerokość (np. |
|
Stosuje końcową stronę elementu WindowInsets jako szerokość (np. |
|
Stosuje górną krawędź windowInsets jako wysokość (np. |
|
|
Stosuje dolną krawędź elementu WindowInsets jako wysokość (np. |
Te modyfikatory są szczególnie przydatne do określania rozmiaru Spacer, który zajmuje miejsce wstawień:
LazyColumn( Modifier.imePadding() ) { // Other content item { Spacer( Modifier.windowInsetsBottomHeight( WindowInsets.systemBars ) ) } }
Zużycie w przypadku wstawki
Modyfikatory dopełnienia wewnętrznego (windowInsetsPadding i pomocnicze, np. safeDrawingPadding) automatycznie wykorzystują część wcięć, które są stosowane jako dopełnienie. Podczas zagłębiania się w drzewo kompozycji zagnieżdżone modyfikatory dopełnienia wewnątrz i modyfikatory rozmiaru wewnątrz wiedzą, że część wstawień została już wykorzystana przez zewnętrzne modyfikatory dopełnienia wewnątrz, i unikają używania tej samej części wstawień więcej niż raz, co spowodowałoby zbyt dużo dodatkowego miejsca.
Modyfikatory rozmiaru wstawki również unikają używania tej samej części wstawek więcej niż raz, jeśli wstawki zostały już wykorzystane. Ponieważ jednak zmieniają one swój rozmiar bezpośrednio, nie zużywają samych wstawek.
W rezultacie zagnieżdżone modyfikatory dopełnienia automatycznie zmieniają ilość dopełnienia zastosowanego do każdego komponentu.
Patrząc na ten sam LazyColumn przykład co wcześniej, widzimy, że LazyColumn jest zmieniany przez modyfikator imePadding. W sekcji LazyColumn ostatni element ma wysokość dolnej części pasków systemowych:
LazyColumn( Modifier.imePadding() ) { // Other content item { Spacer( Modifier.windowInsetsBottomHeight( WindowInsets.systemBars ) ) } }
Gdy edytor IME jest zamknięty, modyfikator imePadding() nie stosuje dopełnienia, ponieważ edytor IME nie ma wysokości. Modyfikator imePadding() nie stosuje dopełnienia, więc nie są używane żadne wcięcia, a wysokość elementu Spacer będzie równa rozmiarowi dolnej części paska systemowego.
Gdy otworzy się edytor IME, wstawki IME zostaną animowane, aby dopasować się do jego rozmiaru, a modyfikator imePadding() zacznie stosować dolne dopełnienie, aby zmienić rozmiar LazyColumn podczas otwierania edytora IME. Gdy modyfikator imePadding() zacznie stosować dopełnienie u dołu, zacznie też zużywać tę ilość wstawek. Dlatego wysokość Spacer zaczyna się zmniejszać, ponieważ część odstępu między paskami systemowymi została już zastosowana przez modyfikator imePadding(). Gdy modyfikator imePadding() stosuje dopełnienie u dołu większe niż paski systemowe, wysokość elementu Spacer wynosi zero.
Gdy IME się zamyka, zmiany zachodzą w odwrotnej kolejności: element Spacer zaczyna się rozszerzać od wysokości zera, gdy element imePadding() jest mniejszy niż dolna krawędź paska systemowego, aż w końcu element Spacer osiąga wysokość dolnej krawędzi paska systemowego, gdy IME jest całkowicie animowany.
TextField.Jest to możliwe dzięki komunikacji między wszystkimi modyfikatorami windowInsetsPadding. Można na to wpływać na kilka innych sposobów.
Modifier.consumeWindowInsets(insets: WindowInsets) też wykorzystuje wcięcia w taki sam sposób jak Modifier.windowInsetsPadding, ale nie stosuje wykorzystanych wcięć jako dopełnienia. Jest to przydatne w połączeniu z modyfikatorami rozmiaru wstawki, aby wskazać elementom równorzędnym, że określona liczba wstawek została już wykorzystana:
Column(Modifier.verticalScroll(rememberScrollState())) { Spacer(Modifier.windowInsetsTopHeight(WindowInsets.systemBars)) Column( Modifier.consumeWindowInsets( WindowInsets.systemBars.only(WindowInsetsSides.Vertical) ) ) { // content Spacer(Modifier.windowInsetsBottomHeight(WindowInsets.ime)) } Spacer(Modifier.windowInsetsBottomHeight(WindowInsets.systemBars)) }
Funkcja Modifier.consumeWindowInsets(paddingValues: PaddingValues) działa bardzo podobnie do wersji z argumentem WindowInsets, ale przyjmuje dowolny argument PaddingValues. Jest to przydatne, gdy chcesz poinformować dzieci, że dopełnienie lub odstępy są zapewniane przez inny mechanizm niż modyfikatory dopełnienia wstawki, np. zwykłe elementy Modifier.padding lub elementy odstępu o stałej wysokości:
Column(Modifier.padding(16.dp).consumeWindowInsets(PaddingValues(16.dp))) { // content Spacer(Modifier.windowInsetsBottomHeight(WindowInsets.ime)) }
Jeśli potrzebujesz surowych wartości wstawień okna bez ich wykorzystania, użyj bezpośrednio wartości WindowInsets lub użyj WindowInsets.asPaddingValues(), aby zwrócić PaddingValues wstawień, na które nie ma wpływu wykorzystanie.
Ze względu na poniższe zastrzeżenia w miarę możliwości używaj modyfikatorów dopełnienia odcięć okna i modyfikatorów rozmiaru odcięć okna.
Wstawki i fazy Jetpack Compose
Compose używa podstawowych interfejsów API AndroidX do aktualizowania i animowania wcięć, które korzystają z podstawowych interfejsów API platformy zarządzających wcięciami. Ze względu na to zachowanie platformy wcięcia mają specjalną relację z fazami Jetpack Compose.
Wartości wstawień są aktualizowane po fazie kompozycji, ale przed fazą układu. Oznacza to, że odczytywanie wartości wstawek w kompozycji zwykle używa wartości wstawek, która jest opóźniona o 1 klatkę. Wbudowane modyfikatory opisane na tej stronie są zaprojektowane tak, aby opóźniać używanie wartości wstawek do fazy układu, co zapewnia, że wartości wstawek są używane w tej samej ramce, w której są aktualizowane.