Jetpack Compose: задачи перетаскивания возвращаются в исходный столбец — как исправить?Android

Форум для тех, кто программирует под Android
Ответить
Anonymous
 Jetpack Compose: задачи перетаскивания возвращаются в исходный столбец — как исправить?

Сообщение Anonymous »

Я разрабатываю тестовое приложение с помощью Jetpack Compose, используя функции перетаскивания. У меня есть три задачи, которые указаны в каждом назначенном столбце: «Сделать», «В процессе» и «Готово». Когда я пытаюсь переместить любую задачу в другой столбец, она меняется, но затем возвращается в исходный столбец. В чем может быть проблема?
Вот мой код на GitHub: репозиторий GitHub
DragAndDrop.kt
internal val LocalDragTargetIfo = compositionLocalOf { DragTargetInfo() }

@Composable
fun DragableScreen(modifier: Modifier = Modifier, content: @Composable BoxScope.() -> Unit) {
val state = remember { DragTargetInfo() }
CompositionLocalProvider(LocalDragTargetIfo provides state) {
Box(modifier = Modifier.fillMaxSize()) {
content()
if (state.isDagging) {
var targetSize by remember { mutableStateOf(IntSize.Zero) }
Box(
modifier = Modifier
.graphicsLayer {
val offset = (state.dragPosition + state.dragOffset)
scaleX = 1.3f
scaleY = 1.3f
alpha = if (targetSize == IntSize.Zero) 0f else .9f
translationX = offset.x.minus(targetSize.width / 2)
translationY = offset.y.minus(targetSize.height / 2)
}
.onGloballyPositioned {
targetSize = it.size
}
) {
state.draggableComposable?.invoke()
}
}
}
}
}

MainViewModel.kt
class MainViewModel : ViewModel() {
var isCurrentlyDragging by mutableStateOf(false)
private set

val items = mutableStateListOf()

var addedTasks = mutableStateListOf()
private set
fun addExampleTasks() {
items.addAll(listOf(
Task(1, "Task 1","Description 1", TaskStatus.TO_DO),
Task(2, "Task 2","Description 2", TaskStatus.IN_PROGRESS),
Task(3, "Task 3","Description 3", TaskStatus.DONE)
))

}

fun startDragging() {
isCurrentlyDragging = true
}

fun stopDragging() {
isCurrentlyDragging = false
}

fun addTask(task: Task) {
items.add(task)
}

fun updateTaskStatus(task: Task, newStatus: TaskStatus) {
val index = items.indexOfFirst { it.id == task.id }
if (index != -1) {
val currentTask = items[index]
if (currentTask.status != newStatus) {
println("Updating task ${task.id} from ${currentTask.status} to $newStatus")
// Actualizar el estado directamente
items[index] = currentTask.copy(status = newStatus)
}
}
}

}

MainScreen.kt
@Composable
fun MainScreen(mainViewModel: MainViewModel = viewModel()) {
// Observar directamente el estado de items
val tasks = mainViewModel.items
// Llamar a un método para añadir tareas de ejemplo (solo si es necesario)
LaunchedEffect(Unit) {
if (tasks.isEmpty()) {
mainViewModel.addExampleTasks()
}
}
Row(modifier = Modifier.fillMaxSize()) {
TaskColumn(
title = "To Do",
tasks = tasks.filter { it.status == TaskStatus.TO_DO },
onTaskDropped = { task ->
mainViewModel.updateTaskStatus(task, TaskStatus.TO_DO)
},
viewModel = mainViewModel,
modifier = Modifier.weight(1f)
)
TaskColumn(
title = "In Progress",
tasks = tasks.filter { it.status == TaskStatus.IN_PROGRESS },
onTaskDropped = { task ->
mainViewModel.updateTaskStatus(task, TaskStatus.IN_PROGRESS)
},
viewModel = mainViewModel,
modifier = Modifier.weight(1f)
)
TaskColumn(
title = "Done",
tasks = tasks.filter { it.status == TaskStatus.DONE },
onTaskDropped = { task ->
mainViewModel.updateTaskStatus(task, TaskStatus.DONE)
},
viewModel = mainViewModel,
modifier = Modifier.weight(1f)
)
}
}
@Composable
fun TaskColumn(
title: String,
tasks: List,
onTaskDropped: (Task) -> Unit,
viewModel: MainViewModel, // Asegúrate de recibir el ViewModel
modifier: Modifier = Modifier
) {
Column(
modifier = modifier
.fillMaxHeight()
.padding(8.dp)
.border(1.dp, Color.Black, shape = RoundedCornerShape(8.dp))
) {
Text(title, style = MaterialTheme.typography.bodyMedium, modifier = Modifier.padding(8.dp))

tasks.forEach { task ->
DragTrarget(
modifier = Modifier.wrapContentWidth().padding(4.dp),
datatoDrop = task,
viewModel = viewModel // Pasar el ViewModel aquí
) {
TaskItem(task)
}
}

DropItem(
modifier = Modifier.fillMaxSize()
) { isInBound, droppedTask ->
if (isInBound && droppedTask != null) {
println("Task dropped: ${droppedTask.title} to $title")
onTaskDropped(droppedTask)
}
}
}
}

@Composable
fun TaskItem(task: Task) {
Box(
modifier = Modifier
.wrapContentWidth()
.padding(8.dp)
.background(Color.LightGray, shape = RoundedCornerShape(8.dp)) // Aquí se aplica el radio
.border(1.dp, Color.LightGray, shape = RoundedCornerShape(8.dp)) // Asegúrate de aplicar el mismo shape al borde
.padding(8.dp)
) {
Column {
Text("${task.title}:")
Text("${task.description}")
}
}
}

Task.kt
data class Task (val id: Int, val title: String, val description: String, var status: TaskStatus)

enum class TaskStatus{
TO_DO,IN_PROGRESS,DONE
}


Подробнее здесь: https://stackoverflow.com/questions/791 ... how-to-fix
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «Android»