Replace button-triggered collapse with vertical drag gesture
ViewModel now exposes onDrag/onDragEnd so BottomCard drives the collapse animation via detectVerticalDragGestures instead of a discrete collapse() call. Drag maps to 0–1 progress over 200dp; on release the animatable snaps to the nearest end with spring. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
parent
35cbcaf430
commit
b734e26645
@ -1,6 +1,7 @@
|
||||
package plus.rua.project
|
||||
|
||||
import androidx.compose.animation.core.Animatable
|
||||
import androidx.compose.animation.core.spring
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.setValue
|
||||
@ -42,31 +43,27 @@ class CalendarViewModel(private val coroutineScope: CoroutineScope) {
|
||||
selectedDate = date
|
||||
}
|
||||
|
||||
fun collapse() {
|
||||
if (isCollapsed) return
|
||||
fun onDrag(delta: Float) {
|
||||
coroutineScope.launch {
|
||||
_collapseAnimatable.animateTo(
|
||||
targetValue = 1f,
|
||||
animationSpec = androidx.compose.animation.core.spring(
|
||||
dampingRatio = 0.8f,
|
||||
stiffness = 400f
|
||||
)
|
||||
)
|
||||
isCollapsed = true
|
||||
val new = (_collapseAnimatable.value + delta).coerceIn(0f, 1f)
|
||||
_collapseAnimatable.snapTo(new)
|
||||
}
|
||||
}
|
||||
|
||||
fun expand() {
|
||||
if (!isCollapsed) return
|
||||
isCollapsed = false
|
||||
fun onDragEnd() {
|
||||
coroutineScope.launch {
|
||||
_collapseAnimatable.animateTo(
|
||||
targetValue = 0f,
|
||||
animationSpec = androidx.compose.animation.core.spring(
|
||||
dampingRatio = 0.8f,
|
||||
stiffness = 400f
|
||||
if (_collapseAnimatable.value > 0.5f) {
|
||||
_collapseAnimatable.animateTo(
|
||||
targetValue = 1f,
|
||||
animationSpec = spring(dampingRatio = 0.8f, stiffness = 400f)
|
||||
)
|
||||
)
|
||||
isCollapsed = true
|
||||
} else {
|
||||
_collapseAnimatable.animateTo(
|
||||
targetValue = 0f,
|
||||
animationSpec = spring(dampingRatio = 0.8f, stiffness = 400f)
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1,6 +1,5 @@
|
||||
package plus.rua.project.ui
|
||||
|
||||
import androidx.compose.animation.core.animate
|
||||
import androidx.compose.foundation.background
|
||||
import androidx.compose.foundation.gestures.detectVerticalDragGestures
|
||||
import androidx.compose.foundation.layout.Box
|
||||
@ -12,14 +11,13 @@ import androidx.compose.foundation.shape.RoundedCornerShape
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Surface
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.rememberCoroutineScope
|
||||
import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.draw.clip
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.input.pointer.pointerInput
|
||||
import androidx.compose.ui.platform.LocalDensity
|
||||
import androidx.compose.ui.unit.dp
|
||||
import kotlinx.coroutines.launch
|
||||
import plus.rua.project.CalendarViewModel
|
||||
|
||||
@Composable
|
||||
@ -27,16 +25,20 @@ fun BottomCard(
|
||||
viewModel: CalendarViewModel,
|
||||
modifier: Modifier = Modifier
|
||||
) {
|
||||
val coroutineScope = rememberCoroutineScope()
|
||||
val density = LocalDensity.current
|
||||
val dragRange = with(density) { 200.dp.toPx() }
|
||||
|
||||
Surface(
|
||||
modifier = modifier
|
||||
.fillMaxWidth()
|
||||
.pointerInput(Unit) {
|
||||
detectVerticalDragGestures { _, dragAmount ->
|
||||
if (dragAmount < 0 && !viewModel.isCollapsed) {
|
||||
viewModel.collapse()
|
||||
}
|
||||
.pointerInput(viewModel.isCollapsed) {
|
||||
if (viewModel.isCollapsed) return@pointerInput
|
||||
detectVerticalDragGestures(
|
||||
onDragEnd = { viewModel.onDragEnd() },
|
||||
onDragCancel = { viewModel.onDragEnd() }
|
||||
) { _, dragAmount ->
|
||||
val delta = -dragAmount / dragRange
|
||||
viewModel.onDrag(delta)
|
||||
}
|
||||
},
|
||||
shape = RoundedCornerShape(topStart = 16.dp, topEnd = 16.dp),
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user