A Swipeable
é uma API Compose Material que ajuda a criar componentes que
podem ser deslizados entre estados distintos, como páginas inferiores, gavetas ou
deslizar para dispensar. Para oferecer melhor suporte a casos de uso avançados, como âncoras que
dependem do tamanho de um componente, um sucessor foi publicado no
Compose-Foundation 1.6.0-alpha01: AnchoredDraggable
. A AnchoredDraggable
é uma API Foundation para criar componentes arrastáveis com estados ancorados, como
páginas inferiores, gavetas ou deslizar para dispensar.
As APIs Swipeable
do Material Design foram descontinuadas e substituídas por AnchoredDraggable
do Foundation, e elas vão ser removidas em uma versão futura Este guia
descreve como migrar das APIs Swipeable
para o AnchoredDraggable
.
Migrar SwipeableState
para AnchoredDraggableState
Comece identificando as mudanças no detentor de estado. AnchoredDraggableState
não pode ser herdado, e o deslocamento é representado como Float.NaN
antes de ser inicializado.
Atualizar o detentor de estado
AnchoredDraggableState
é uma classe final, o que significa que ela não pode ser herdada. Se o componente existente herdar de SwipeableState
, atualize
o detentor de estado para manter uma referência ao AnchoredDraggableState
em vez de
herdar dele:
Deslizante
class MySwitchState: SwipeableState()
AnchoredDraggable
class MySwitchState {
private val anchoredDraggableState = AnchoredDraggableState(...)
}
Como o detentor de estado não herda mais de SwipeableState
, talvez
seja necessário expor APIs por conta própria. As APIs mais comuns que você pode usar são
offset
, progress
, currentValue
e targetValue
.
Acessar o deslocamento
Ao contrário de Swipeable
, o offset
do AnchoredDraggableState
é Float.NaN
antes de ser inicializado. Em AnchoredDraggable
, as âncoras podem ser transmitidas para o
construtor do AnchoredDraggableState
ou atualizadas usando
AnchoredDraggableState#updateAnchors
. A transmissão das âncoras para o
construtor do AnchoredDraggableState
inicializa o deslocamento imediatamente.
Caso suas âncoras dependam do layout ou possam mudar, use
AnchoredDraggableState#updateAnchors
para evitar recriar o estado quando
as âncoras mudarem.
Se você usar updateAnchors
, o deslocamento será Float.NaN
antes de transmitir as
Âncoras para updateAnchors
. Para evitar a transmissão acidental de Float.NaN
a
componentes, use AnchoredDraggableState#requireOffset
para exigir que o
deslocamento tenha sido inicializado durante a leitura. Isso ajuda você a detectar
inconsistências ou possíveis bugs logo no início.
@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) }
}
}
Migrar Modifier.swipeable
para Modifier.anchoredDraggable
Modifier.anchoredDraggable()
substitui Modifier.swipeable
. Alguns
parâmetros de Modifier.swipeable()
foram movidos diretamente para AnchoredDraggableState
, conforme descrito nas seções a seguir.
Definir âncoras
Defina as âncoras usando o método do builder DraggableAnchors
. Em seguida, transmita-os
para o construtor de AnchoredDraggableState#updateAnchors
ou
AnchoredDraggableState
:
Construtor
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) }
)
}
updateAnchors
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) }
)
}
Se as âncoras forem estáticas, transmita-as para o construtor. Se elas dependerem do
layout ou não forem estáticas, use updateAnchors
.
Definir limites de posicionamento
O tipo e o nome do parâmetro de limites foram alterados. Em vez de ter uma
interface ThresholdConfig
separada, o AnchoredDraggableState
tem um
parâmetro positionalThreshold
que usa uma função lambda que retorna a
posição do limite. Por exemplo, um limite posicional de 50% pode ser expresso como:
val anchoredDraggableState = AnchoredDraggableState(
positionalThreshold = { distance -> distance * 0.5f },
...
)
Um limite de posição de 56dp
pode ser expresso assim:
val density = LocalDensity.current
val anchoredDraggableState = AnchoredDraggableState(
positionalThreshold = { with(density) { 56.dp.toPx() } },
...
)
Definir limites de velocidade
Os limites de velocidade também são transmitidos para o construtor de AnchoredDraggableState
e também expressos como um lambda:
val density = LocalDensity.current
val anchoredDraggableState = AnchoredDraggableState(
velocityThreshold = { with(density) { 125.dp.toPx() } },
...
)
Mudanças na superfície da API
Confira abaixo uma visão geral das mudanças na plataforma da API.
AnchoredDraggableState
|
|
---|---|
|
|
|
|
|
|
|
|
|
|
|
N/A |
|
|
|
|
|
|
|
|
|
|
|
Modifier.anchoredDraggable
|
|
---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
Passado para o construtor |
|
Sem suporte no momento. Consulte b/288084801 para ver o status mais recente. |
|
Passado para o construtor |