Виджет DragTarget
Виджет DragTarget рисует область через builder
и меняет вид, когда над ней держат drag.
При успешном бросе вызывают onAcceptWithDetails
с данными из
Draggable.
Отказ до броса проверяют в onWillAcceptWithDetails.
Синтаксис
DragTarget<String>(
onAcceptWithDetails: (details) {},
builder: (context, candidateData, rejectedData) {
return child;
},
)
Параметры
| Параметр | Описание |
|---|---|
builder |
Строит дочерний виджет. Получает списки candidate и rejected данных над зоной. |
onAcceptWithDetails |
Вызывается, когда данные приняли после отпускания. |
onWillAcceptWithDetails |
Решает, принимать ли данные, пока drag над зоной. |
onMove |
Drag движется над зоной. |
onLeave |
Drag покинул зону без броса. |
Пример
Давайте примем строку из Draggable:
import 'package:flutter/material.dart';
class DropZone extends StatefulWidget
{
const DropZone({super.key});
@override
State<DropZone> createState() => _DropZoneState();
}
class _DropZoneState extends State<DropZone>
{
var stored = 'abcde';
@override
Widget build(BuildContext context)
{
return Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
Draggable<String>(
data: '12345',
feedback: const Text('12345'),
child: const Text('drag me'),
),
DragTarget<String>(
onAcceptWithDetails: (details) {
setState(() {
stored = details.data;
});
},
builder: (context, candidate, rejected) {
return Container(
width: 140,
height: 90,
color: candidate.isNotEmpty
? Colors.lightGreen
: Colors.grey.shade300,
alignment: Alignment.center,
child: Text(stored),
);
},
),
],
);
}
}
void main()
{
runApp(
MaterialApp(
home: Scaffold(
body: Center(
child: DropZone(),
),
),
),
);
}
На экране зона слева подсветится зелёным, когда над ней тащат; после броса в ней будет '12345'.
Пример
Давайте примем только строку '12345':
import 'package:flutter/material.dart';
class FilterTarget extends StatefulWidget
{
const FilterTarget({super.key});
@override
State<FilterTarget> createState() => _FilterTargetState();
}
class _FilterTargetState extends State<FilterTarget>
{
var message = 'abcde';
@override
Widget build(BuildContext context)
{
return DragTarget<String>(
onWillAcceptWithDetails: (details) {
return details.data == '12345';
},
onAcceptWithDetails: (details) {
setState(() {
message = 'ok';
});
},
builder: (context, candidate, rejected) {
return Container(
width: 160,
height: 80,
color: rejected.isNotEmpty
? Colors.red.shade100
: Colors.blue.shade100,
alignment: Alignment.center,
child: Text(message),
);
},
);
}
}
void main()
{
runApp(
MaterialApp(
home: Scaffold(
body: Center(
child: FilterTarget(),
),
),
),
);
}
На экране синяя зона; чужие данные подсветят её красным, а '12345' после броса покажет 'ok'.
Смотрите также
-
виджет
Draggable,
который отдаёт data в DragTarget -
виджет
LongPressDraggable,
который начинает drag после долгого нажатия -
виджет
Dismissible,
который убирает элемент смахиванием -
виджет
GestureDetector,
который двигает виджет без приёма данных