Swipeable
est une API Compose Material qui vous aide à créer des composants qui peuvent passer d'un état distinct à un autre, tels que des bottom sheets, des panneaux ou le balayage pour ignorer. Pour mieux prendre en charge les cas d'utilisation avancés, tels que les ancres qui dépendent de la taille d'un composant, un successeur a été publié dans Compose-Foundation 1.6.0-alpha01: AnchoredDraggable
. AnchoredDraggable
est une API Foundation permettant de créer des composants déplaçables avec des états ancrés, tels que des bottom sheets, des panneaux ou des fonctionnalités de balayage pour ignorer.
Les API Swipeable
de Material ont été abandonnées au profit de AnchoredDraggable
de Foundation et seront supprimées dans une prochaine version. Ce guide explique comment migrer des API Swipeable
vers AnchoredDraggable
.
Migrer SwipeableState
vers AnchoredDraggableState
Commencez par identifier les modifications apportées à votre conteneur d'état. AnchoredDraggableState
ne peut pas être hérité et le décalage est représenté par Float.NaN
avant l'initialisation.
Mettre à jour votre conteneur d'état
AnchoredDraggableState
est une classe finale, ce qui signifie qu'elle ne peut pas être héritée. Si votre composant existant hérite de SwipeableState
, mettez à jour votre conteneur d'état pour qu'il contienne une référence à AnchoredDraggableState
au lieu de l'hériter:
À faire glisser
class MySwitchState: SwipeableState()
AnchoredDraggable
class MySwitchState {
private val anchoredDraggableState = AnchoredDraggableState(...)
}
Étant donné que votre conteneur d'état n'hérite plus de SwipeableState
, vous devrez peut-être exposer vous-même des API. Les API les plus courantes que vous pouvez utiliser sont offset
, progress
, currentValue
et targetValue
.
Accéder au décalage
Contrairement à Swipeable
, le offset
de AnchoredDraggableState
est Float.NaN
avant l'initialisation. Dans AnchoredDraggable
, les ancres peuvent être transmises au constructeur de AnchoredDraggableState
ou mises à jour via AnchoredDraggableState#updateAnchors
. La transmission des ancres au constructeur de AnchoredDraggableState
initialise immédiatement le décalage.
Si vos ancres dépendent de la mise en page ou peuvent changer, utilisez AnchoredDraggableState#updateAnchors
pour éviter de recréer l'état lorsque les ancres changent.
Si vous utilisez updateAnchors
, le décalage sera de Float.NaN
avant de transmettre les ancres à updateAnchors
. Pour éviter de transmettre accidentellement Float.NaN
à des composants, utilisez AnchoredDraggableState#requireOffset
pour exiger que le décalage ait été initialisé lors de sa lecture. Cela vous permet de détecter les incohérences ou les bugs éventuels dès le début.
@Composable
fun AnchoredDraggableBox() {
val state = remember { AnchoredDraggableState(...) }
val density = LocalDensity.current
val anchors = remember { DraggableAnchors { ... } }
SideEffect {
state.updateAnchors(anchors)
}
Box(
Modifier.offset { IntOffset(x = state.requireOffset(), y = 0) }
}
}
Migrer Modifier.swipeable
vers Modifier.anchoredDraggable
Modifier.anchoredDraggable()
remplace Modifier.swipeable
. Certains paramètres de Modifier.swipeable()
ont été déplacés directement vers AnchoredDraggableState
, comme décrit dans les sections suivantes.
Définir des ancrages
Définissez les ancrages à l'aide de la méthode de compilateur DraggableAnchors
. Transmettez-les ensuite au constructeur de AnchoredDraggableState#updateAnchors
ou AnchoredDraggableState
:
Constructeur
enum class DragValue { Start, Center, End }
@Composable
fun AnchoredDraggableBox() {
val anchors = DraggableAnchors {
Start at -100.dp.toPx()
Center at 0f
End at 100.dp.toPx()
}
val state = remember {
AnchoredDraggableState(anchors = anchors)
}
Box(
Modifier.offset { IntOffset(x = state.requireOffset(), y = 0) }
)
}
Mettre à jour les ancres
enum class DragValue { Start, Center, End }
@Composable
fun AnchoredDraggableBox() {
val state = remember { AnchoredDraggableState(...) }
val density = LocalDensity.current
val anchors = with (density) {
DraggableAnchors {
Start at -100.dp.toPx()
Center at 0f
End at 100.dp.toPx()
}
}
SideEffect {
state.updateAnchors(anchors)
}
Box(
Modifier.offset { IntOffset(x = state.requireOffset(), y = 0) }
)
}
Si les ancres sont statiques, transmettez-les au constructeur. S'ils dépendent de la mise en page ou s'ils ne sont pas statiques, utilisez updateAnchors
.
Définir des seuils positionnels
Le type et le nom du paramètre de seuils ont changé. Au lieu d'avoir une interface ThresholdConfig
distincte, AnchoredDraggableState
comporte un paramètre positionalThreshold
qui accepte une fonction lambda qui renvoie la position du seuil. Par exemple, un seuil de position de 50% peut être exprimé comme suit:
val anchoredDraggableState = AnchoredDraggableState(
positionalThreshold = { distance -> distance * 0.5f },
...
)
Un seuil de position de 56dp
peut être exprimé comme suit:
val density = LocalDensity.current
val anchoredDraggableState = AnchoredDraggableState(
positionalThreshold = { with(density) { 56.dp.toPx() } },
...
)
Définir des seuils de vitesse
Les seuils de vélocité sont également transmis au constructeur de AnchoredDraggableState
et exprimés sous la forme d'un lambda:
val density = LocalDensity.current
val anchoredDraggableState = AnchoredDraggableState(
velocityThreshold = { with(density) { 125.dp.toPx() } },
...
)
Modifications apportées à la surface de l'API
Vous trouverez ci-dessous un aperçu des modifications apportées à la surface de l'API.
AnchoredDraggableState
|
|
---|---|
|
|
|
|
|
|
|
|
|
|
|
N/A |
|
|
|
|
|
|
|
|
|
|
|
Modifier.anchoredDraggable
|
|
---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
Transmis au constructeur |
|
Pas encore compatible. Consultez b/288084801 pour connaître l'état le plus récent. |
|
Transmise au constructeur |