I need help to add button row in PaginatedDataTable but I don't know where to add it?
I try to add button in column test7 many time but it does not work
if you could help me where can I add button in table?
in data column or data cell?
like this
const kTableColumns = <DataColumn>[
DataColumn(
label: Expanded(
child: Text('test7',
textAlign: TextAlign.start,
style: TextStyle(fontSize: 12, fontWeight: FontWeight.bold)),
),
numeric: true,
),
];
class DetailstDataSource extends DataTableSource {
int selectedCount = 0;
List\<A\> myData = \<A\>\[
A(
'test',
3,
1,
'test',
'test',
'test',
'test',
),
\];
DataCell(
Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
SizedBox(
width: 100,
child: Text(dessert.test7,
maxLines: 3,
overflow: TextOverflow.visible,
textAlign: TextAlign.start,
style: const TextStyle(fontSize: 12)),
),
],
),
),
],
);
}
Related
body: Container(
padding: EdgeInsets.all(25),
child: Table(
border: TableBorder.all(),
columnWidths: {
0: FractionColumnWidth(0.14),
1: FractionColumnWidth(0.6),
2: FractionColumnWidth(0.3),
},
children: [
// here to add iconButton
buildRow(['No.','List of Books','Action'], isHeader: true),
buildRow(['1','Harry Potter Philosopher','Action']),
buildRow(['2','Sleeping Beauty','Action']),
buildRow(['3','Beauty and The Beast','Action']),
],
),
),
);
// here List<String>
TableRow buildRow(List<String> cells, {bool isHeader = false}) => TableRow(
children: cells.map((cell) {
final style = TextStyle(
fontWeight: isHeader? FontWeight.bold : FontWeight.normal,
fontSize: 18,
);
return Padding(
padding: const EdgeInsets.all(12),
child: Center(
child: Text(
(cell), //here error
style: TextStyle(
fontWeight: FontWeight.bold,
fontSize: 15,
),
),
),
);
}).toList(),
);
}
Here is i confused to declare icon button in the parameter buildRow cause it carry String but when i change to Widget it will appear the error at Text(cell). I want to add the iconButton in the third row of the table
Just declare List<Strings> cells to List<Widgets> cells like below code:
Use like this:
buildRow([Text('1'), IconButton(onPressed: (){}, icon: Icon(Icons.edit))], isHeader: true),
I have DataTable in flutter which is working fine until I got an empty list. In case the widget.detailDate.brands is empty, I get "Bad state: No element" error, now my question is, how can I handle the error, I've tried something like
widget.detailDate.brands.map((brand) => {
if (brand != ' '){
// do the DataRow stuff
}else{
print('brnad not found')
}
}).toList();
But it's not working. I wanna add something like "-", if the list is empty
My whole code looks like this:
DataTable buildBrandTable(context) {
return DataTable(
columnSpacing: 0,
showCheckboxColumn: false,
columns: const <DataColumn>[
DataColumn(
label: Text(
'Brand',
),
),
DataColumn(
label: Text(
'Mandant',
),
),
DataColumn(
label: Expanded(
child: Text(
'Januar',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'Februar',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'März',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'April',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'Mai',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'Juni',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'Juli',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'August',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'September',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'Oktober',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'November',
textAlign: TextAlign.end,
),
)),
DataColumn(
label: Expanded(
child: Text(
'Dezember',
textAlign: TextAlign.end,
),
),
),
],
rows: [
...widget.detailData.brands!
.map(
(brand) => DataRow(
onSelectChanged: (bool) {
Navigator.of(context)
.pushNamed(DetailScreen.routeName, arguments: {
'pageType': 'Brand',
'id': brand['brand_slug'].toString(),
});
},
color: (brand['brand'] == 'Gesamt')
? MaterialStateProperty.resolveWith(
(Set<MaterialState> states) => Colors.grey[300])
: null,
cells: [
DataCell(Text(brand['brand'])),
DataCell(Text(brand['mandant'])),
..._month
.map(
(month) => DataCell(
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
Text(formatter.format(brand[month])),
],
),
),
)
.toList(),
DataCell(
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
Text(
formatter.format(
_month
.map((month) => brand[month])
.toList()
.reduce((a, b) => a + b),
),
),
],
),
),
DataCell(
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
Text((brand['rate'] != null)
? formatterPercent.format(brand['rate'] / 100)
: 'N/A'),
],
),
),
DataCell(
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
Text((brand['rate_letztes_jahr'] != null)
? formatterPercent
.format(brand['rate_letztes_jahr'] / 100)
: 'N/A')
],
),
),
],
),
)
.toList(),
],
);
}
I think your problem is caused by
rows: [
...widget.detailData.brands!
.map( // rest of your mapping function
...
maybe you should
widget.detailData.brands.length>0 ?
...widget.detailData.brands.map( // rest of your mapping function
:
[]
in your widget tree
Update
for example
Using the spread operator(...), adds the items individually not as a list
Column(
children: [
...values.map((value) {
return Text(value);
}),
],
),
I'm trying to show a widget onFinished countdown timer but I can't seem to make it work.
I've added var reqPIN = false;
And here is my code:
children [
Countdown(
seconds: 3,
build: (_, double time) =>
RichText(
text: TextSpan(
text: 'Reset PIN in ',
style: TextStyle(
color: Theme.of(context).inputDecorationTheme.labelStyle?.color
),
children: <TextSpan>[
TextSpan(
text: time.toString(),
style: TextStyle(
color: Color(0xFF2481CF),
fontWeight: FontWeight.bold
)),
TextSpan(text: ' sec',
style: TextStyle(
color: Theme.of(context).inputDecorationTheme.labelStyle?.color
))
]
),
),
onFinished: () {
setState(() {
reqPIN = true;
});
},
),
SizedBox(
child: Visibility(
visible: reqPIN,
child: Text('Resend PIN',
style: TextStyle(
color: Colors.black
),),
),
)
]
Is there any solution?
onlySelectedBorderPinPut() is not getting called on setState...
to fix this, you can wrap your RichText with a Column, and add your Resend button there, you won't need to have a reqPin bool for managing the state, simply handle it with the remaining time like below
Countdown(
seconds: 3,
build: (_, double time) => Column(
children: [
RichText(
...
),
Visibility(
visible: time == 0,
child: SizedBox(
child: Text('Resend PIN',
style: TextStyle(color: Colors.black
)
),
),
),
],
),
),
Try this one.
if (reqPIN)
SizedBox(
child: Text('Resend PIN', style: TextStyle(color: Colors.black)),
),
I have created a DataTable widget with several columns. I have a list of map elements that I want to render inside each row of DataTable sequentially. I have two columns as ID and Name inside DataTable. I want to display each of the elements inside the row i.e. element with ID 1 is displayed in the first row and then the next element in the 2nd row. How to do the rendering so that I have something like a loop which iterates over the whole list and renders the elements one by one?
List<Map<String,dynamic>> myList = [
{
'id':1,
'name':'Ahmad'
},
{
'id':2,
'name':'Usama'
},
{
'id':3,
'name':'Habib'
}
];
DataTable widget is:
SingleChildScrollView(
scrollDirection: Axis.vertical,
child: SingleChildScrollView(
scrollDirection: Axis.horizontal,
child: DataTable(
columns: [
DataColumn(label: Text('ID')),
DataColumn(label: Text('Name')),
],
rows: [
DataRow(
cells: [
// How to render here ?
]
),
]
),
),
),
It is working for you.
DataTable(
columnSpacing: 50,
columns: const <DataColumn>[
DataColumn(
label: Text(
'ID',
style: TextStyle(
fontStyle: FontStyle.italic,
),
),
),
DataColumn(
label: Text(
'Name',
style: TextStyle(
fontStyle: FontStyle.italic,
),
),
),
],
rows: myList
.map(
(e) => DataRow(
cells: [
DataCell(
Text(
e['id'],
style: TextStyle(
fontStyle: FontStyle.italic,
),
),
),
DataCell(
Text(
e['name'],
style: TextStyle(
fontStyle: FontStyle.italic,
),
),
),
],
),
)
.toList(),
),
I have the following code that renders a ListTile with a TextFormField and a ListTitle with a DropdownButton.
Row(
mainAxisSize: MainAxisSize.max,
mainAxisAlignment: MainAxisAlignment.spaceBetween,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
new Expanded(
child: ListTile(
dense: true,
title: Text(
"Property Name",
style: TextStyle(fontWeight: FontWeight.bold),
),
subtitle: TextFormField(
decoration: InputDecoration(
labelText: 'Enter the property name'
),
),
isThreeLine: true,
)
),
new Expanded(
child: ListTile(
dense: true,
title: Text(
"Contact Name",
style: TextStyle(fontWeight: FontWeight.bold),
),
subtitle: DropdownButton<int>(
items: [
DropdownMenuItem<int>(
value: 1,
child: Text(
"John Smith",
),
),
DropdownMenuItem<int>(
value: 2,
child: Text(
"Jon Doe",
),
),
],
onChanged: (value) {
setState(() {
_value = value;
});
},
value: _value,
hint: Text(
"Select Contact Name",
style: TextStyle(
color: Colors.black,
),
),
),
isThreeLine: true,
)
),
],
),
but it produces the following:
Is there a way to align the Contact Name's DropdownButton bottom line to the Property Name's ListTile? Any ideas?
1. Use DropdownButtonFormField
As for me, I rather choose to replace Dropdown widget with DropdownButtonFormField
change this
child: ListTile(
dense: true,
title: Text(
"Contact Name",
style: TextStyle(fontWeight: FontWeight.bold),
),
subtitle: DropdownButton<int>( // change this
items: [
...
into this
child: ListTile(
dense: true,
title: Text(
"Contact Name",
style: TextStyle(
fontWeight: FontWeight.bold,
),
),
subtitle: DropdownButtonFormField<int>( // into this
decoration: InputDecoration(
isDense: true,
hasFloatingPlaceholder: true,
labelText: 'Select Contact Name',
contentPadding: EdgeInsets.symmetric(vertical: 9),
),
items: [
...
2. Remove hint params
secondly, as we move 'Select Contact name' to label Text inside InputDecoration, we can remove these lines :
hint: Text(
"Select Contact Name",
style: TextStyle(
color: Colors.black,
),
),
3. Comparison
We can discover three options that we already have in image below.
at the first row, it is solution proposed by KeykoYume
at the second row, it is solution proposed by Abhilash Chandran
at the last row, it is new solution proposed by me
Take note, that the third row also automatically handle overflows nicely
Padding your dropdown button with top inset could help as shown below.
subtitle: Padding(
padding: const EdgeInsets.only(top: 19.0),
child: DropdownButton<int>(
items: [
DropdownMenuItem<int>(
value: 1,
child: Text(
"John Smith",
),
),
DropdownMenuItem<int>(
value: 2,
child: Text(
"Jon Doe",
),
),
],
onChanged: (value) {
// setState(() {
// _value = value;
// });
},
value: 1,
hint: Text(
"Select Contact Name",
style: TextStyle(
color: Colors.black,
),
),
),
),