W: ConstraintLayout
wersji 2.1, dodaliśmy kilka funkcji, aby ułatwić
zarządzaj urządzeniami składanymi, w tym SharedValues
,
ReactiveGuide
i ulepszoną obsługę animacji w formatach MotionLayout
.
Wspólne wartości
Dodaliśmy nowy mechanizm do wstrzykiwania wartości środowiska wykonawczego w komponencie ConstraintLayout
:
powinien być używany w przypadku wartości systemowych, ponieważ wszystkie wystąpienia
ConstraintLayout
mają dostęp do tej wartości.
W kontekście urządzeń składanych możemy użyć tego mechanizmu, aby wstrzykiwać pozycja części strony widocznej na ekranie podczas działania:
Kotlin
ConstraintLayout.getSharedValues().fireNewValue(R.id.fold, fold)
Java
ConstraintLayout.getSharedValues().fireNewValue(R.id.fold, fold);
Możesz uzyskać dostęp do wspólnych wartości w niestandardowym pomocniku, dodając detektor dla wszelkie zmiany:
Kotlin
val sharedValues: SharedValues = ConstraintLayout.getSharedValues() sharedValues.addListener(mAttributeId, this)
Java
SharedValues sharedValues = ConstraintLayout.getSharedValues(); sharedValues.addListener(mAttributeId, this);
Spójrzmy na przykład FoldableExperiments.
by sprawdzić, jak określamy położenie części strony widocznej na ekranie
Biblioteka Jetpack WindowManager i wstrzykiwanie
położenie w: ConstraintLayout
.
Kotlin
inner class StateContainer : Consumer<WindowLayoutInfo> { override fun accept(newLayoutInfo: WindowLayoutInfo) { // Add views that represent display features for (displayFeature in newLayoutInfo.displayFeatures) { val foldFeature = displayFeature as? FoldingFeature if (foldFeature != null) { if (foldFeature.isSeparating && foldFeature.orientation == FoldingFeature.Orientation.HORIZONTAL ) { // The foldable device is in tabletop mode val fold = foldPosition(motionLayout, foldFeature) ConstraintLayout.getSharedValues().fireNewValue(R.id.fold, fold) } else { ConstraintLayout.getSharedValues().fireNewValue(R.id.fold, 0); } } } } }
Java
class StateContainer implements Consumer<WindowLayoutInfo> { @Override public void accept(WindowLayoutInfo newLayoutInfo) { // Add views that represent display features for (DisplayFeature displayFeature : newLayoutInfo.getDisplayFeatures()) { if (displayFeature instanceof FoldingFeature) { FoldingFeature foldFeature = (FoldingFeature)displayFeature; if (foldFeature.isSeparating() && foldFeature.getOrientation() == FoldingFeature.Orientation.HORIZONTAL ) { // The foldable device is in tabletop mode int fold = foldPosition(motionLayout, foldFeature); ConstraintLayout.getSharedValues().fireNewValue(R.id.fold, fold); } else { ConstraintLayout.getSharedValues().fireNewValue(R.id.fold, 0); } } } } }
fireNewValue()
przyjmuje identyfikator reprezentujący wartość jako pierwszy parametr, a
wartość do wstawienia jako drugi parametr.
ReactiveGuide
Jednym ze sposobów wykorzystania SharedValue
w układzie bez konieczności
do napisania dowolnego kodu, jest użycie funkcji ReactiveGuide
jako pomoc. Spowoduje to umieszczenie wskazów w poziomie lub pionie zgodnie z
połączono SharedValue
.
<androidx.constraintlayout.widget.ReactiveGuide
android:id="@+id/fold"
app:reactiveGuide_valueId="@id/fold"
android:orientation="horizontal" />
Można go następnie używać w taki sam sposób jak w przypadku normalnych wytycznych.
MotionLayout
dla urządzeń składanych
Dodaliśmy kilka funkcji w MotionLayout
w wersji 2.1, które ułatwiają przekształcanie
stanową. Jest to szczególnie przydatne w przypadku urządzeń składanych,
obsługiwać animacje między różnymi możliwymi układami.
Na urządzeniach składanych dostępne są 2 sposoby:
- W czasie działania zaktualizuj bieżący układ (
ConstraintSet
), aby wyświetlić lub ukryć strony. - W przypadku każdego stanu urządzenia składanego, który chcesz wybrać, użyj oddzielnego atrybutu
ConstraintSet
pomoc (closed
,folded
lubfully open
).
Animowanie elementu ConstraintSet
Funkcja updateStateAnimate()
w MotionLayout
została dodana w wersji 2.1
wersja:
Kotlin
fun updateStateAnimate(stateId: Int, set: ConstraintSet, duration: Int)
Java
void updateStateAnimate(int stateId, ConstraintSet set, int duration);
Ta funkcja automatycznie animuje zmiany przy
ConstraintSet
zamiast natychmiastowej aktualizacji (możesz to zrobić
updateState(stateId, constraintset)
). Dzięki temu możesz zaktualizować UI
w zależności od tego, jaki jest stan urządzenia składanego.
ReactiveGuide
w: MotionLayout
Atrybut ReactiveGuide
obsługuje też 2 przydatne atrybuty, gdy jest używany wewnątrz
MotionLayout
:
app:reactiveGuide_animateChange="true|false"
app:reactiveGuide_applyToAllConstraintSets="true|false"
Pierwsza z nich zmodyfikuje bieżący ConstraintSet
i animuje zmianę
automatycznie. Druga zastosuje nową wartość parametru ReactiveGuide
na wszystkie ConstraintSet
w MotionLayout
. Typowe podejście
w przypadku urządzeń składanych użyj ReactiveGuide
reprezentującego pozycję
i ustaw elementy układu względem ReactiveGuide
.
Używanie wielu elementów ConstraintSet
do reprezentowania stanu urządzenia złożonego
Zamiast aktualizować bieżący stan MotionLayout
– inny sposób tworzenia architektury
w interfejsie urządzeń składanych należy utworzyć określone stany (w tym
closed
, folded
i fully open
).
W takim przypadku nadal możesz używać zmiennej ReactiveGuide
do reprezentowania elementu
ale będziesz mieć znacznie większą kontrolę (w porównaniu do
animacji przy aktualizacji bieżącego ConstraintSet
), by dowiedzieć się, jak każdy stan
przejść do innego.
Przy takim podejściu w detektorze DeviceState
ustaw po prostu kierowanie
MotionLayout
, aby przejść do określonych stanów w
MotionLayout.transitionToState(stateId)
.
.