Swipeable
é uma API do Material Design do Compose que ajuda a criar componentes que
podem ser deslizados entre estados discretos, como páginas inferiores, gavetas ou
deslize para fechar. 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
. AnchoredDraggable
é uma API do Foundation para criar componentes arrastáveis com estados fixados, como
folhas de fundo, gavetas ou deslize para fechar.
As APIs Swipeable
do Material foram descontinuadas em favor da AnchoredDraggable
do Foundation e serão removidas em uma versão futura. Este guia
descreve como migrar das APIs Swipeable
para AnchoredDraggable
.
Migre SwipeableState
para AnchoredDraggableState
Comece identificando as mudanças no titular do 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 atual 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 do estado não herda mais de SwipeableState
, talvez seja necessário
expor as 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
de AnchoredDraggableState
é Float.NaN
antes
de ser inicializado. No AnchoredDraggable
, as âncoras podem ser transmitidas para
o construtor da AnchoredDraggableState
ou atualizadas pelo
AnchoredDraggableState#updateAnchors
. A transmissão das âncoras para
o construtor de AnchoredDraggableState
inicializa o deslocamento imediatamente.
Se as âncoras dependem do layout ou podem 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
para
componentes, use AnchoredDraggableState#requireOffset
para exigir que o
offset tenha sido inicializado ao ser lido. Isso ajuda 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) }
}
}
Migre Modifier.swipeable
para Modifier.anchoredDraggable
Modifier.anchoredDraggable()
substitui Modifier.swipeable
. Alguns
dos parâmetros de Modifier.swipeable()
foram movidos para AnchoredDraggableState
diretamente, conforme descrito nas seções a seguir.
Definir âncoras
Defina as âncoras usando o método de builder DraggableAnchors
. Em seguida, transmita
elas para o AnchoredDraggableState#updateAnchors
ou o AnchoredDraggableState
do construtor:
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 ao construtor. Se eles dependem do
layout ou não são estáticos, use updateAnchors
.
Definir limites de posição
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 posicional de 56dp
pode ser expresso como:
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 ao construtor de AnchoredDraggableState
e expressos como uma lambda:
val density = LocalDensity.current
val anchoredDraggableState = AnchoredDraggableState(
velocityThreshold = { with(density) { 125.dp.toPx() } },
...
)
Mudanças na plataforma da API
Confira uma visão geral das mudanças na API abaixo.
AnchoredDraggableState
|
|
---|---|
|
|
|
|
|
|
|
|
|
|
|
N/A |
|
|
|
|
|
|
|
|
|
|
|
Modifier.anchoredDraggable
|
|
---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
Transmitido para o construtor |
|
Sem suporte no momento. Consulte o status mais recente em b/288084801. |
|
Transmitido para o construtor |