Utwórz responsywne UI za pomocą ConstraintLayout   Element Android Jetpack.

Wypróbuj tworzenie wiadomości
Jetpack Compose to zalecany zestaw narzędzi interfejsu na Androida. Dowiedz się, jak pracować z układami w Compose.

ConstraintLayout pozwala tworzyć duże, złożone układy z płaską hierarchią widoków – bez zagnieżdżonych grup widoków. Jest on podobny do RelativeLayout, ponieważ wszystkie widoki są rozmieszczone zgodnie z relacją między widokami siostrzanymi a ich układem nadrzędnym, ale jest bardziej elastyczny niż RelativeLayout i łatwiejszy w użyciu dzięki edytorowi układu w Android Studio.

Wszystkie możliwości interfejsu ConstraintLayout są dostępne bezpośrednio w narzędziach wizualnych w Edytorze układu, ponieważ interfejs API układu i Edytor układu są ze sobą specjalnie zintegrowane. Możesz tworzyć układy za pomocą ConstraintLayout, przeciągając elementy, zamiast edytować kod XML.

Na tej stronie dowiesz się, jak utworzyć układ za pomocą ConstraintLayout w Android Studio w wersji 3.0 lub nowszej. Więcej informacji o edytorze układu znajdziesz w artykule Tworzenie interfejsu użytkownika za pomocą edytora układu.

Aby zobaczyć różne układy, które możesz utworzyć za pomocą ConstraintLayout, zapoznaj się z projektem Przykłady układu ograniczeń na GitHubie.

Omówienie ograniczeń

Aby zdefiniować położenie widoku w ConstraintLayout, musisz dodać co najmniej 1 ograniczenie poziome i 1 ograniczenie pionowe. Każde ograniczenie reprezentuje połączenie lub dopasowanie do innego widoku, układu nadrzędnego lub niewidocznej linii pomocniczej. Każde ograniczenie określa położenie widoku wzdłuż osi pionowej lub poziomej. Każdy widok musi mieć co najmniej 1 ograniczenie dla każdej osi, ale często potrzebne jest więcej ograniczeń.

Gdy przeciągniesz widok do Edytora układu, pozostanie on w tym samym miejscu, nawet jeśli nie będzie miał żadnych ograniczeń. Ma to ułatwić edycję. Jeśli widok nie ma ograniczeń, gdy uruchomisz układ na urządzeniu, zostanie on narysowany w pozycji [0,0] (w lewym górnym rogu).

Na rysunku 1 układ wygląda dobrze w edytorze, ale w widoku C nie ma ograniczenia pionowego. Gdy ten układ jest wyświetlany na urządzeniu, widok C jest dopasowany poziomo do lewego i prawego brzegu widoku A, ale pojawia się u góry ekranu, ponieważ nie ma ograniczenia pionowego.

Rysunek 1. Edytor pokazuje widok C poniżej widoku A, ale nie ma ograniczenia pionowego.

Rysunek 2. Widok C jest teraz ograniczony pionowo poniżej widoku A.

Brakujące ograniczenia nie powodują błędów kompilacji, ale edytor układu wskazuje je jako błędy na pasku narzędzi. Aby wyświetlić błędy i inne ostrzeżenia, kliknij Pokaż ostrzeżenia i błędy. Aby pomóc Ci uniknąć braku ograniczeń, edytor układu automatycznie dodaje ograniczenia za pomocą funkcji Autołączanie i wyprowadzanie ograniczeń.

Dodawanie ConstraintLayout do projektu

Aby użyć ConstraintLayout w projekcie, wykonaj te czynności:

  1. Upewnij się, że repozytorium maven.google.com zostało zadeklarowane w pliku settings.gradle:

    Groovy

        dependencyResolutionManagement {
          ...
          repositories {
              google()
          }
        )
        

    Kotlin

        dependencyResolutionManagement {
          ...
          repositories {
              google()
          }
        }
        
  2. Dodaj bibliotekę jako zależność w pliku build.gradle na poziomie modułu, jak pokazano w tym przykładzie. Najnowsza wersja może się różnić od tej pokazanej w przykładzie.

    Odlotowe

    dependencies {
        implementation "androidx.constraintlayout:constraintlayout:2.2.0-beta01"
        // To use constraintlayout in compose
        implementation "androidx.constraintlayout:constraintlayout-compose:1.1.0-beta01"
    }
    

    Kotlin

    dependencies {
        implementation("androidx.constraintlayout:constraintlayout:2.2.0-beta01")
        // To use constraintlayout in compose
        implementation("androidx.constraintlayout:constraintlayout-compose:1.1.0-beta01")
    }
    
  3. Na pasku narzędzi lub w powiadomieniu o synchronizacji kliknij Synchronizuj projekt z plikami Gradle.

Teraz możesz utworzyć układ za pomocą ConstraintLayout.

Konwertowanie układu

Rysunek 3. Menu do konwertowania układu na ConstraintLayout.

Aby przekonwertować dotychczasowy układ na układ z ograniczeniami:

  1. Otwórz układ w Android Studio i kliknij kartę Projekt na dole okna edytora.
  2. W oknie Drzewo komponentów kliknij prawym przyciskiem myszy układ i kliknij Przekształc układ LinearLayout w ConstraintLayout.

Tworzenie nowego układu

Aby utworzyć nowy plik układu ograniczeń:

  1. W oknie Projekt kliknij folder modułu i wybierz Plik > Nowy > XML > XML układu.
  2. Wpisz nazwę pliku układu, a w polu RootTag wpisz „androidx.constraintlayout.widget.ConstraintLayout”.
  3. Kliknij Zakończ.

Dodawanie i usuwanie ograniczeń

Aby dodać ograniczenie:

Film 1. Lewa strona widoku jest ograniczona do lewej strony elementu nadrzędnego.

  1. Przeciągnij widok z okna Paleta do edytora.

    Gdy dodasz widok do ConstraintLayout, pojawi się on w ramce z kwadratowymi uchwytami do zmiany rozmiaru w każdym rogu oraz okrągłym uchwytami ograniczającymi po każdej stronie.

  2. Kliknij widok, aby go wybrać.
  3. Wykonaj jedną z tych czynności:
    • Kliknij uchwyt ograniczenia i przeciągnij go do dostępnego punktu zakotwiczenia. Punkt ten może być krawędzią innego widoku, krawędzią układu lub wskazówką. Gdy przeciągasz uchwyt ograniczenia, edytor układu wyświetla potencjalne uchwyty połączenia i niebieskie nakładki.
    • Kliknij jeden z przycisków Utwórz połączenie w sekcji Układ w oknie Atrybuty, jak pokazano na rysunku 4.

      Rysunek 4. W sekcji Układ w oknie Atrybuty możesz tworzyć połączenia.

Po utworzeniu ograniczenia edytor nadaje mu domyślny margines, aby oddzielić 2 widoki.

Podczas tworzenia ograniczeń pamiętaj o tych zasadach:

  • Każdy widok musi mieć co najmniej 2 ograniczenia: jedno poziome i jedno pionowe.
  • Ograniczenia możesz tworzyć tylko między uchwytem ograniczenia a punktem zakotwiczenia, które znajdują się na tej samej płaszczyźnie. Płaszczyzna pionowa (czyli lewy i prawy bok) widoku może być ograniczona tylko do innej płaszczyzny pionowej, a linie bazowe mogą być ograniczone tylko do innych linii bazowych.
  • Każdy uchwyt ograniczenia może być używany tylko do jednego ograniczenia, ale możesz tworzyć wiele ograniczeń z różnych widoków do tego samego punktu kotwiczenia.

Ograniczenie możesz usunąć, wykonując jedną z tych czynności:

  • Kliknij ograniczenie, aby je zaznaczyć, a potem kliknij Usuń.
  • Kliknij Control (Command w systemie macOS) kotwicę ogranicznika. Ograniczenie zmienia kolor na czerwony, aby wskazać, że można je usunąć, klikając je (jak pokazano na rysunku 5).

    Rysunek 5. Czerwony ogranicznik oznacza, że możesz go kliknąć, aby go usunąć.

  • W sekcji Układ w oknie Atrybuty kliknij kotwicę ograniczeń, jak pokazano na rysunku 6.

    Rysunek 6. Kliknij ograniczenie, aby je usunąć.

Film 2. dodanie ograniczenia, które jest przeciwstawne do istniejącego;

Jeśli dodasz do widoku przeciwstawne ograniczenia, linie ograniczeń zwiną się jak sprężyna, aby wskazać przeciwstawne siły, jak pokazano w filmie 2. Efekt jest najbardziej widoczny, gdy rozmiar widoku jest ustawiony na „stały” lub „Zawijaj treść”. W tym przypadku widok jest wyśrodkowany między ograniczeniami. Jeśli chcesz, aby widok rozciągał się, aby spełniać ograniczenia, zamiast tego zmień rozmiar na „dopasuj do ograniczeń”. Jeśli chcesz zachować bieżący rozmiar, ale przesunąć widok, aby nie był wyśrodkowany, zmień ograniczenie ograniczające.

Za pomocą ograniczeń możesz uzyskać różne typy zachowania układu, jak opisano w następnych sekcjach.

Pozycja nadrzędna

ograniczenie strony widoku do odpowiedniej krawędzi układu;

Na rysunku 7 lewa strona widoku jest połączona z lewym marginesem głównego układu. Odległość od krawędzi możesz określić za pomocą marginesu.

Rysunek 7. Ograniczenie poziome do elementu nadrzędnego.

Pozycja zamówienia

Określ kolejność wyświetlania 2 widoków: pionowo lub poziomo.

Na rysunku 8 element B jest zawsze po prawej stronie elementu A, a element C jest zawsze poniżej elementu A. Te ograniczenia nie oznaczają jednak wyrównania, więc element B może się nadal przesuwać w górę i w dół.

Rysunek 8. Ograniczenie w poziomie i w pionie.

Wyrównanie

wyrównać krawędź widoku do krawędzi innego widoku;

Na rysunku 9 lewa strona elementu B jest wyrównana do lewej strony elementu A. Jeśli chcesz wyrównać środki widoku, utwórz ograniczenie po obu stronach.

Możesz przesunąć wyrównanie, przeciągając widok do wewnątrz ograniczenia. Na przykład rysunek 10 przedstawia element B z wyrównaniem przesuniętym o 24 piksele. Odsunięcie jest zdefiniowane przez margines widoku ograniczonego.

Możesz też zaznaczyć wszystkie widoki, które chcesz wyrównać, a potem na pasku narzędzi kliknąć Wyrównaj , aby wybrać typ wyrównania.

Rysunek 9. ograniczenie wyrównania w poziomie.

Rysunek 10. Ograniczenie wyrównania w poziomie z odstępem.

Wyrównanie do linii bazowej

Wyrównaj linię bazową tekstu w widoku do linii bazowej tekstu w innym widoku.

Na rysunku 11 pierwszy wiersz tekstu w B jest wyrównany do tekstu w A.

Aby utworzyć ograniczenie wartości bazowej, kliknij prawym przyciskiem widok tekstu, który chcesz ograniczyć, a następnie kliknij Pokaż wartość bazową. Następnie kliknij tekst na linii bazowej i przeciągnij ją do innej linii bazowej.

Rysunek 11. Ograniczenie wyrównania do wartości podstawowej.

Ograniczenie do wytycznych

Możesz dodać linię pomocniczą pionową lub poziomą, która ograniczy widok, a która jest niewidoczna dla użytkowników aplikacji. Możesz ustawić położenie linii pomocniczej w ramach układu na podstawie jednostek dp lub procenta w stosunku do krawędzi układu.

Aby utworzyć wytyczne, na pasku narzędzi kliknij Wytyczne , a następnie Dodaj wytyczne pionowe lub Dodaj wytyczne poziome.

Przeciągnij przerywaną linię, aby zmienić jej położenie, i kliknij kółko na jej krawędzi, aby przełączyć tryb pomiaru.

Rysunek 12. Widok ograniczony do wytycznych.

Ograniczenie do bariery

Podobnie jak w przypadku wytycznych, bariera to niewidoczna linia, którą możesz ograniczyć widok, ale nie określa ona swojej pozycji. Zamiast tego pozycja bariery zmienia się w zależności od pozycji widoków, które zawiera. Jest to przydatne, gdy chcesz ograniczyć widok do zbioru widoków, a nie do jednego konkretnego widoku.

Na przykład na rysunku 13 widok C jest ograniczony do prawej strony bariery. Barierę ustawiono na „końcu” (czyli po prawej stronie w układzie od lewej do prawej) zarówno w widoku A, jak i w widoku B. Barierę przesuwa się w zależności od tego, czy prawa strona widoku A czy widoku B jest najdalej po prawej stronie.

Aby utworzyć barierę:

  1. Na pasku narzędzi kliknij Wytyczne , a następnie Dodaj barierę pionową lub Dodaj barierę poziomą.
  2. W oknie Drzewo komponentów wybierz widoki, które chcesz umieścić w bariery, i przeciągnij je do komponentu bariery.
  3. Wybierz barierę w drzewie komponentów, otwórz okno Atrybuty i ustaw opcję kierunekBariery.

Teraz możesz utworzyć ograniczenie z innego widoku do bariery.

Możesz też ograniczyć widoczność do tych widoków, które znajdują się w obrębie bariery. Dzięki temu możesz dopasować wszystkie widoki w barierze do siebie nawzajem, nawet jeśli nie wiesz, który z nich jest najdłuższy lub najwyższy.

Możesz też umieścić w barierze wskazówkę, aby zapewnić jej „minimalną” pozycję.

Rysunek 13. Widok C jest ograniczony do bariery, która przesuwa się w zależności od położenia i rozmiaru widoku A oraz widoku B.

Dostosowywanie wartości domyślnej ograniczeń

Gdy dodasz ograniczenie po obu stronach widoku, a jego rozmiar w tym samym wymiarze jest ustawiony na „stały” lub „Zawijanie treści”, widok zostanie wyśrodkowany między tymi dwoma ograniczeniami, a domyślnie będzie przesunięty o 50%. Możesz dostosować 偏差 (bias) przez przeciąganie suwaka w oknie Atrybuty lub przez przeciąganie widoku, jak pokazano w filmie 3.

Jeśli zamiast tego chcesz, aby widok rozciągał się, aby spełniać ograniczenia, zmien rozmiar na „dopasuj do ograniczeń”.

Film 3. Dostosowywanie wartości domyślnej ograniczeń.

Dostosowywanie rozmiaru widoku

Rysunek 14. Po wybraniu widoku w oknie Atrybuty znajdziesz opcje dotyczące 1 współczynnika rozmiaru, 2 usuwania ograniczeń, 3 trybu wysokości lub szerokości, 4 marginesów oraz 5 biasu ograniczeń. Możesz też wyróżnić poszczególne ograniczenia w Edytorze układu, klikając je na liście 6 ograniczeń.

Za pomocą uchwytów w rogu możesz zmienić rozmiar widoku, ale spowoduje to zakodowanie rozmiaru. Widok nie będzie się zmieniał w zależności od treści lub rozmiaru ekranu. Aby wybrać inny tryb zmiany rozmiaru, kliknij widok i otwórz okno Atrybuty po prawej stronie edytora.

U góry okna Atrybuty znajduje się kontroler widoku, który zawiera opcje dotyczące kilku atrybutów układu, jak pokazano na rysunku 14. Jest to możliwe tylko w przypadku widoków w układzie z ograniczeniami.

Aby zmienić sposób obliczania wysokości i szerokości, kliknij symbole wskazane strzałką 3 na rysunku 14. Te symbole oznaczają tryb rozmiaru w następujący sposób. Kliknij symbol, aby przełączać się między tymi ustawieniami:

  • Stały: w tym celu wskaż konkretny wymiar w polu tekstowym poniżej lub zmień rozmiar widoku w edytorze.
  • Zawijanie treści: widok rozszerza się tylko do tego stopnia, aby zmieścić zawartość.
    • layout_constrainedWidth
    • Ustaw tę wartość na true, aby wymiar poziomy mógł się zmieniać w celu zachowania ograniczeń. Domyślnie widget ustawiony na WRAP_CONTENTnie jest ograniczony przez ograniczenia.

  • Ograniczenia dopasowania: widok rozszerza się w jak największym stopniu, aby spełniać ograniczenia po obu stronach, uwzględniając marginesy widoku. Możesz jednak zmodyfikować to zachowanie za pomocą tych atrybutów i wartości. Te atrybuty działają tylko wtedy, gdy ustawisz szerokość widoku na „dopasuj do ograniczeń”:
    • layout_constraintWidth_min

      W przypadku widoku o minimalnej szerokości używany jest wymiar dp.

    • layout_constraintWidth_max

      W przypadku maksymalnej szerokości widoku używa się wymiaru dp.

    Jeśli jednak dany wymiar ma tylko 1 ograniczenie, widok rozszerza się, aby dopasować zawartość. Użycie tego trybu w przypadku wysokości lub szerokości pozwala też ustawić współczynnik rozmiaru.

Ustaw rozmiar jako współczynnik

Rysunek 15. Widok jest ustawiony na format 16:9 ze szerokością na podstawie współczynnika wysokości.

Rozmiar widoku możesz ustawić na proporcje, np. 16:9, jeśli co najmniej jeden z wymiarów widoku ma ustawienie „dopasuj ograniczenia” (0dp). Aby włączyć proporcje, kliknij Przełącz ograniczenie formatu obrazu (wyróżnienie 1 na rysunku 14) i wprowadź format width:height w polu, które się pojawi.

Jeśli zarówno szerokość, jak i wysokość mają ustawiony parametr „Dopasuj do ograniczeń”, możesz kliknąć Przełącz ograniczenie współczynnika proporcji, aby wybrać, który wymiar ma być dostosowywany do współczynnika drugiego. W inspektorze widoku możesz sprawdzić, który wymiar jest ustawiony jako współczynnik, łącząc odpowiadające mu krawędzie ciągłą linią.

Jeśli np. dla obu stron ustawisz „Dopasuj do ograniczeń”, kliknij Przełącz ograniczenie współczynnika proporcji dwukrotnie, aby ustawić szerokość jako współczynnik wysokości. Cały rozmiar jest określony przez wysokość widoku, którą można zdefiniować dowolnie, jak pokazano na rysunku 15.

Dostosowywanie marginesów widoku

Aby wyrównać widoki, na pasku narzędzi kliknij Margines , aby wybrać domyślne marginesy dla każdego widoku, który dodajesz do układu. Wszelkie zmiany domyślnej marży mają zastosowanie tylko do widoków dodanych od tego momentu.

Możesz kontrolować marżę dla każdego widoku w oknie Atrybuty, klikając liczbę w wierszu, który reprezentuje poszczególne ograniczenia. Na rysunku 14 w wyjaśnieniu 4 widać, że dolny margines ma wartość 16 dp.

Rysunek 16. Przycisk Margin na pasku narzędzi.

Wszystkie marginesy oferowane przez narzędzie są wielokrotnością 8 dp, aby ułatwić dopasowanie widoków do zaleceń dotyczących siatki kwadratowej o wymiarach 8 dp w ramach Material Design.

Sterowanie grupami liniowymi za pomocą łańcucha

Rysunek 17. Łańcuch poziomy z 2 widokami.

Łańcuch to grupa widoków połączonych ze sobą dwukierunkowymi ograniczeniami pozycji. Widoki w łańcuchu mogą być rozmieszczone pionowo lub poziomo.

Rysunek 18. Przykłady każdego stylu łańcucha.

Łańcuchy można stylizować na jeden z tych sposobów:

  1. Spread: widoki są równomiernie rozłożone po uwzględnieniu marż. Jest to ustawienie domyślne.
  2. Rozprowadź wewnątrz: pierwsze i ostatnie wyświetlenia są przypisane do ograniczeń po obu stronach łańcucha, a pozostałe są równomiernie rozłożone.
  3. Z wagą: gdy łańcuch jest ustawiony na rozprowadź lub rozprowadź wewnątrz, możesz wypełnić pozostałą przestrzeń, ustawiając co najmniej jeden widok na „dopasuj do ograniczeń” (0dp). Domyślnie przestrzeń jest równomiernie rozłożona między widokami ustawionymi na „dopasuj do ograniczeń”, ale możesz przypisać wagę dla każdego widoku, używając atrybutów layout_constraintHorizontal_weight i layout_constraintVertical_weight. Działa to tak samo jak layout_weightukładzie liniowym: widok o najwyższej wartości wagi zajmuje najwięcej miejsca, a widoki o tej samej wadze zajmują taką samą ilość miejsca.
  4. Zpakowane: widoki są pakowane po uwzględnieniu marż. Możesz dostosować ustawienie całego łańcucha – w lewo lub w prawo, w górę lub w dół – przez zmianę ustawienia widoku „głowy” łańcucha.

Widok „głowy” łańcucha – widok lewy w łańcuchu poziomym (w układzie od lewej do prawej) i widok górny w łańcuchu pionowym – definiuje styl łańcucha w pliku XML. Możesz jednak przełączać się między opcjami rozproszenie, rozproszenie wewnątrz i zbiornicze, wybierając dowolny widok w łańcuchu i klikając przycisk , który pojawi się pod widokiem.

Aby utworzyć łańcuch, wykonaj te czynności, jak pokazano w filmie 4:

  1. Wybierz wszystkie widoki, które mają być uwzględnione w łańcuchu.
  2. Kliknij prawym przyciskiem myszy jeden z widoków.
  3. Wybierz Sieć.
  4. Wybierz Centrum poziome lub Centrum pionowe.

Film 4. Tworzenie łańcucha poziomego.

Oto kilka kwestii, które warto wziąć pod uwagę podczas tworzenia łańcuchów:

  • Widok może być częścią łańcucha poziomego i pionowego, dzięki czemu możesz tworzyć elastyczne układy siatki.
  • Łańcuch działa prawidłowo tylko wtedy, gdy każdy jego koniec jest ograniczony do innego obiektu na tej samej osi, jak pokazano na rysunku 14.
  • Chociaż orientacja łańcucha jest pionowa lub pozioma, korzystanie z niego nie powoduje wyrównywania widoków w tym kierunku. Aby uzyskać odpowiednią pozycję dla każdego widoku w łańcuchu, uwzględnij inne ograniczenia, takie jak ograniczenia wyrównania.

Automatyczne tworzenie ograniczeń

Zamiast dodawać ograniczenia do każdego widoku podczas umieszczania go w układzie, możesz przenieść każdy widok w wybrane miejsca w Edytorze układu, a potem kliknąć Wnioskowanie ograniczeń , aby automatycznie utworzyć ograniczenia.

Wnioskowanie ograniczeń skanuje układ, aby określić najskuteczniejszy zestaw ograniczeń dla wszystkich widoków. Ogranicza ona widoki do ich bieżących pozycji, zapewniając jednocześnie elastyczność. Może być konieczne wprowadzenie poprawek, aby układ działał elastycznie zgodnie z zamierzeniami na różnych rozmiarach i orientacjach ekranu.

Automatyczne połączenie z urządzeniem rodzica to osobna funkcja, którą możesz włączyć. Gdy ta funkcja jest włączona i dodasz widoki podrzędne do widoku nadrzędnego, automatycznie utworzy ona co najmniej 2 ograniczenia dla każdego z nich, gdy tylko będzie to możliwe. Autoconnect nie tworzy ograniczeń dla innych widoków w schemacie.

Automatyczne łączenie jest domyślnie wyłączone. Aby go włączyć, na pasku narzędzi Edytora układu kliknij Włącz automatyczne połączenie z elementem nadrzędnym .

Animacje klatek kluczowych

W ramach ConstraintLayout możesz animować zmiany rozmiaru i pozycji elementów za pomocą elementów ConstraintSetTransitionManager.

ConstraintSet to lekki obiekt, który reprezentuje ograniczenia, marginesy i wypełnienie wszystkich elementów podrzędnych w ConstraintLayout. Gdy zastosujesz ConstraintSet do wyświetlanego ConstraintLayout, układ zaktualizuje ograniczenia wszystkich jego elementów podrzędnych.

Aby utworzyć animację za pomocą ConstraintSet, określ 2 pliki układu, które będą pełnić funkcję początkowej i końcowej klatki kluczowej animacji. Następnie możesz załadować ConstraintSet z drugiego pliku klatki kluczowej i zastosować go do wyświetlanego ConstraintLayout.

Ten przykład kodu pokazuje, jak animować przenoszenie pojedynczego przycisku na dół ekranu.

// MainActivity.kt

fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.keyframe_one)
    constraintLayout = findViewById(R.id.constraint_layout) // member variable
}

fun animateToKeyframeTwo() {
    val constraintSet = ConstraintSet()
    constraintSet.load(this, R.layout.keyframe_two)
    TransitionManager.beginDelayedTransition()
    constraintSet.applyTo(constraintLayout)
}
// layout/keyframe1.xml
// Keyframe 1 contains the starting position for all elements in the animation
// as well as final colors and text sizes.

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <Button
        android:id="@+id/button2"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:text="Button"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
// layout/keyframe2.xml
// Keyframe 2 contains another ConstraintLayout with the final positions.

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <Button
        android:id="@+id/button2"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:text="Button"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintBottom_toBottomOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>

Dodatkowe materiały

ConstraintLayout jest używany w aplikacji demonstracyjnej Sunflower.