I need to implement a long press selection on a row element of Flutter for Android and iOS. Any help please?
My code so far:
class ListElement extends StatelessWidget {
ListElement({this.text, this.name, this.mId, this.animationController});
final String text;
final String name;
final String mId;
final AnimationController animationController;
@override
Widget build(BuildContext context) {
return new GestureDetector(
onTap: () {
Navigator.of(context).push(
new MaterialPageRoute(builder: (BuildContext context) => new DrugProfile(drugmId))
);
},
onLongPress: () {
//HERE I NEED TO SELECT MULTIPLE ROWS IF IT FIRES
},
child: new SizeTransition(
sizeFactor: new CurvedAnimation(
parent: animationController, curve: Curves.easeOut),
axisAlignment: 0.0,
child: new Container(
margin: const EdgeInsets.symmetric(vertical: 10.0),
child: new Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
new Container(
margin: const EdgeInsets.only(right: 16.0),
child: new CircleAvatar(child: new Text(name[0].toUpperCase())),
),
new Expanded(
child: new Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
new Text(name, style: Theme.of(context).textTheme.subhead),
new Container(
margin: const EdgeInsets.only(top: 5.0),
child: new Text(
text,
textAlign: TextAlign.left,
style: new TextStyle(
fontSize: 13.0,),
),
),
],
),
),
],
),
)
)
);
}
}
Maybe I am wrong starting from the onLongPress event, but I need to do the following: If longPress on a row element then provide the ability to select many rows. And after selection then perform custom operation on the rows (this is not part of the question :) ) After selection I imagine a array of indexes that I can pass into a function for further processes. I only need help with multiple selection of elements.
You can use a HashMap to track the selected items in the List and update its values depending on the gesture that you'd like.
Here's a sample that you can try. In this sample, multi-select mode will start on long press of an item. Multi-select mode will stop when there's no selected items left.
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
@override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
var selectMode = false;
Map<String, bool> listItemSelected = {
'List 1': false,
'List 2': false,
'List 3': false,
'List 4': false,
'List 5': false,
'List 6': false,
'List 7': false,
'List 8': false,
'List 9': false,
};
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: ListView(
children: listItemSelected.keys.map((key) {
return Card(
child: GestureDetector(
onTap: () {
// if multi-select mode is true, tap should select List item
if (selectMode && listItemSelected.containsValue(true)) {
debugPrint('onTap on $key');
setState(() {
listItemSelected[key] = !listItemSelected[key];
});
} else {
// Stop multi-select mode when there's no more selected List item
debugPrint('selectMode STOP');
selectMode = false;
}
},
// Start List multi-select mode on long press
onLongPress: () {
debugPrint('onLongPress on $key');
if (!selectMode) {
debugPrint('selectMode START');
selectMode = true;
}
setState(() {
listItemSelected[key] = !listItemSelected[key];
});
},
child: Container(
// Change List item color if selected
color: (listItemSelected[key])
? Colors.lightBlueAccent
: Colors.white,
padding: EdgeInsets.all(16.0),
child: Text(key),
),
),
);
}).toList(),
),
),
);
}
}
Demo