Related
i made a code which opens bottomSheet. Inside the bottomSheet there are inputs that can be added and subtracted by pressing a button.
but the changes that occur are not in accordance with what I expected. changes are delayed not directly.
Widget buildBottomSheet(BuildContext context) => makeDismissible(
child: DraggableScrollableSheet(
initialChildSize: 0.6,
minChildSize: 0.5,
maxChildSize: 0.6,
builder: (_, controller) => Container(
decoration: const BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.vertical(top: Radius.circular(20)),
),
padding: const EdgeInsets.only(top: 10),
child: Column(
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const Center(child: Icon(Icons.horizontal_rule)),
ListTile(
title: Container(
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.start,
children: [
Row(
children: [
ClipRRect(
borderRadius:
const BorderRadius.all(Radius.circular(20)),
child: Image.network(
widget.productList.image,
width: 125,
height: 125,
fit: BoxFit.cover,
),
),
SizedBox(
height: 125,
child: Padding(
padding:
const EdgeInsets.symmetric(horizontal: 15),
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
if (widget.productList.discount == 0)
Text(
CurrencyFormat.convertToIdr(
widget.productList.price, 0),
style: const TextStyle(
fontWeight: FontWeight.w600,
fontSize: 18),
),
if (widget.productList.discount >= 1)
Text(
CurrencyFormat.convertToIdr(
widget.productList.price -
(widget.productList.discount /
100) *
widget.productList.price,
0),
style: const TextStyle(
fontWeight: FontWeight.w600,
fontSize: 18),
),
if (widget.productList.discount >= 1)
Row(
children: [
Text(
"${widget.productList.discount}% ",
style: const TextStyle(
color: Colors.red,
fontWeight: FontWeight.w600),
),
Text(
CurrencyFormat.convertToIdr(
widget.productList.price, 0),
style: const TextStyle(
color: Colors.black38,
fontWeight: FontWeight.w600,
decoration:
TextDecoration.lineThrough),
)
],
),
Text("Stock : ${widget.productList.stock}")
],
),
),
),
],
),
],
),
),
// minLeadingWidth: 125,
trailing: SizedBox(
child: IconButton(
onPressed: () => Navigator.pop(context),
icon: const Icon(Icons.close)),
),
),
const SizedBox(
height: 10,
),
const Divider(
indent: 15,
endIndent: 15,
color: Colors.black,
),
const SizedBox(
height: 10,
),
Padding(
padding: const EdgeInsets.symmetric(horizontal: 15),
child: Column(
children: const [
Text(
"Pilihan Varian :",
style: TextStyle(fontWeight: FontWeight.w800),
),
],
),
),
const Spacer(),
SizedBox(
child: Padding(
padding: const EdgeInsets.symmetric(
vertical: 15, horizontal: 10),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
ElevatedButton(
onPressed: _minCounter,
clipBehavior: Clip.antiAlias,
style: ElevatedButton.styleFrom(
shadowColor: Colors.white,
primary: Colors.black,
padding: const EdgeInsets.symmetric(
horizontal: 0, vertical: 0),
),
child: const Icon(Icons.remove),
),
Text('${widget.productList.minbuy + counter} '),
// const SizedBox(
// width: 50,
// height: 35,
// child: TextField(
// textAlign: TextAlign.center,
// decoration: InputDecoration(
// border: OutlineInputBorder(
// borderSide:
// BorderSide(color: Colors.black)),
// ),
// ),
// ),
ElevatedButton(
onPressed: _incrementCounter,
clipBehavior: Clip.antiAlias,
style: ElevatedButton.styleFrom(
shadowColor: Colors.white,
primary: Colors.black,
padding: const EdgeInsets.symmetric(
horizontal: 0, vertical: 0),
),
child: const Icon(Icons.add),
),
],
),
ElevatedButton.icon(
icon: const Icon(
Icons.add,
color: Colors.amber,
size: 14,
),
label: const Text(
"Keranjang",
style: TextStyle(color: Colors.amber),
),
clipBehavior: Clip.antiAlias,
onPressed: () {},
style: ElevatedButton.styleFrom(
side: const BorderSide(color: Colors.amber),
shadowColor: Colors.white,
primary: Colors.white,
padding: const EdgeInsets.symmetric(
horizontal: 15, vertical: 10),
),
),
],
),
),
),
],
),
),
),
);
for full code : https://github.com/nazhoir/travel-app/blob/main/lib/views/shop/product_detail.dart
So I'm new to flutter, and I'm trying to make a card. But I can't seem to get my desired output.
I tried to separate the different widgets, by using rows and columns, but I kept messing it up.
This is my target output
Target output
This is my current progressCurrent progress
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: buildhomePageAppBar(),
body: buildExhibitorBody(),
);
}
Widget buildExhibitorBody() {
return Container(
child: SingleChildScrollView(
child: Column(
mainAxisAlignment: MainAxisAlignment.start,
children: [
buildExhibitorText(),
SizedBox(
height: 10,
),
buildExhibitorCards(),
SizedBox(height: 10),
],
),
),
);
}
Widget buildhomePageAppBar() {
double profileDimension = 35;
return AppBar(
backgroundColor: Colors.white,
titleSpacing: 0,
title: Padding(
padding: EdgeInsets.only(
left: 20,
),
child: Row(
children: [
Padding(
padding: EdgeInsets.only(
top: 5,
bottom: 5,
),
child: Image(
image: AssetImage('assets/images/plain_logo.png'),
height: 30,
),
),
SizedBox(width: 5),
Text(
'Virtex',
style: TextStyle(
color: Colors.black87,
fontFamily: 'Poppins',
fontSize: 16,
fontWeight: FontWeight.bold,
),
)
],
),
),
actions: [
Padding(
padding: EdgeInsets.only(
top: 10,
bottom: 10,
),
child: Container(
height: profileDimension,
width: profileDimension,
alignment: Alignment.center,
decoration: BoxDecoration(
color: Colors.white,
border: Border.all(
color: Colors.black54,
width: 2,
),
borderRadius: BorderRadius.circular(50),
),
child: ClipRRect(
borderRadius: BorderRadius.circular(50),
child: Image(
width: profileDimension,
height: profileDimension,
image: AssetImage(
'assets/images/profile-image.jpeg',
),
fit: BoxFit.cover,
),
),
),
),
SizedBox(width: 20),
],
);
}
Widget buildExhibitorText() {
return Padding(
padding: EdgeInsets.only(
left: 20,
right: 20,
top: 20,
bottom: 10,
),
child: Container(
child: new Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
Expanded(
child: Text(
"Exhibitors",
textAlign: TextAlign.justify,
style: TextStyle(
fontFamily: "DMSans",
letterSpacing: -0.2,
fontSize: 20.0,
color: Colors.black,
fontWeight: FontWeight.w400,
),
),
),
],
),
),
);
}
Widget buildExhibitorCards() { // I think my problem is I don't know how to do the layout here
return Container(
width: 400,
height: 150,
child: Column(children: <Widget>[
Card(
elevation: 1,
child: Padding(
padding: const EdgeInsets.only(),
child: Row(children: [
buildCardImage(),
buildCardExhibitor(),
buildCardIndustry(),
buildCardGo(),
])),
),
]),
);
}
Widget buildCardExhibitor() {
return Row(mainAxisAlignment: MainAxisAlignment.center, children: [
Container(
padding: EdgeInsets.all(10),
width: 40,
height: 40,
child: Center(
child: Row(
children: <Widget>[
Text(
"EN",
style: TextStyle(
fontSize: 15.0,
color: Colors.white,
fontWeight: FontWeight.bold,
),
textAlign: TextAlign.center,
),
Text('Exhibitor Name')
],
),
),
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(200),
),
color: Colors.red,
),
),
]);
}
Widget buildCardImage() {
return Container(
height: 100,
width: 100,
child: Image(
image: AssetImage('assets/images/onboarding-2.jpg'),
height: 100,
),
);
}
Widget buildCardIndustry() {
return Padding(
padding: EdgeInsets.only(
left: 40,
right: 40,
),
child: Container(
child: new Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
Text(
"Industry 1",
style: TextStyle(
fontFamily: "DMSans",
color: Colors.grey,
letterSpacing: 0.3,
fontSize: 12,
),
),
Text(
"Industry 2",
style: TextStyle(
fontFamily: "DMSans",
letterSpacing: -0.3,
fontSize: 12,
color: Colors.grey,
fontWeight: FontWeight.w500,
),
),
],
),
),
);
}
Widget buildCardGo() {
return Row(mainAxisAlignment: MainAxisAlignment.end, children: [
Text(
'Go to Booth',
style: TextStyle(
color: Colors.blue,
fontFamily: 'Poppins',
fontSize: 16,
fontWeight: FontWeight.bold,
),
),
SizedBox(width: 5),
IconButton(
icon: Icon(
MdiIcons.fromString('arrow-right'),
size: 30,
color: Colors.black,
),
onPressed: () {
Navigator.of(context).pop();
},
),
]);
}
}
I would greatly appreciate any kind of help.
Look:
My own Code
import 'package:flutter/material.dart';
class CardLayout extends StatelessWidget {
Widget buildCardImage = Container(
margin: EdgeInsets.only(right: 10.0),
width: 150,
height: 150,
decoration: BoxDecoration(
image: DecorationImage(
fit: BoxFit.fill,
image: NetworkImage("https://picsum.photos/250?image=9"),
),
),
);
Widget buildCardExhibitor =
Row(mainAxisAlignment: MainAxisAlignment.start, children: [
Container(
padding: EdgeInsets.all(10.0),
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(200),
),
color: Colors.red,
),
child: Text(
"EN",
style: TextStyle(
fontSize: 15.0,
color: Colors.white,
fontWeight: FontWeight.bold,
),
textAlign: TextAlign.center,
),
),
SizedBox(
width: 10.0,
),
Text(
'Exhibitor Name',
style: TextStyle(
fontSize: 15.0,
color: Colors.black,
fontWeight: FontWeight.bold,
),
textAlign: TextAlign.center,
),
]);
Widget buildCardIndustry = Padding(
padding: EdgeInsets.all(8.0),
child: Container(
child: new Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
Container(
padding:
EdgeInsets.only(left: 10.0, right: 10.0, top: 5, bottom: 5),
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(100),
),
color: Colors.blueGrey.shade400,
),
child: Text(
'Industry 1',
style: TextStyle(
fontFamily: "DMSans",
color: Colors.white,
letterSpacing: 0.3,
fontSize: 12,
),
),
),
SizedBox(
width: 10.0,
),
Container(
padding:
EdgeInsets.only(left: 10.0, right: 10.0, top: 5, bottom: 5),
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(100),
),
color: Colors.blueGrey.shade400,
),
child: Text(
'Industry 2',
style: TextStyle(
fontFamily: "DMSans",
color: Colors.white,
letterSpacing: 0.3,
fontSize: 12,
),
),
),
],
),
),
);
Widget buildCardGo = Row(mainAxisAlignment: MainAxisAlignment.end, children: [
Text(
'Go to Booth',
style: TextStyle(
color: Colors.blue,
fontFamily: 'Poppins',
fontSize: 16,
fontWeight: FontWeight.bold,
),
),
SizedBox(width: 3),
IconButton(
icon: Icon(
Icons.arrow_forward_rounded,
size: 30,
color: Colors.blue,
),
onPressed: () {
//Navigator.pop(context);
},
),
]);
#override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
appBar: AppBar(
title: Text('Exhibitor'),
actions: [
IconButton(
icon: Icon(Icons.filter_list_rounded),
onPressed: () {
Navigator.pop(context);
})
],
),
body: Container(
margin: EdgeInsets.only(top: 10.0),
width: MediaQuery.of(context).size.width,
//height: 150.0, // remove this line -------------- (1) [EDIT]
child: Column(
// wrap card with column and add listtile as children -------------- (2) [EDIT]
children: [
ListTile(
leading: Text('Exhibitor'),
trailing: IconButton(
icon: Icon(Icons.filter_list_rounded),
onPressed: () {
Navigator.pop(context);
}),
),
Card(
elevation: 5.0,
color: Colors.white,
child: Padding(
padding: EdgeInsets.all(5.0),
child: Row(
children: <Widget>[
buildCardImage,
Expanded(
child: Column(
children: <Widget>[
buildCardExhibitor,
buildCardIndustry,
buildCardGo
],
))
],
),
),
),
],
),
),
));
}
}
Column(
children: [
Padding(
padding: const EdgeInsets.only(
left: 15, bottom: 8, top: 1),
child: Row(
//crossAxisAlignment: CrossAxisAlignment.start,
//mainAxisAlignment: MainAxisAlignment.start,
children: [
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
// ITEM NAME
Padding(
padding: const EdgeInsets.only(
left: 10, top: 10),
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
children: [
Text(
'${restaurantItems[i].name}',
style: TextStyle(
fontSize: 17,
color: kTextColor,
fontWeight: FontWeight.w700),
),
SizedBox(
width: width / 2,
),
// 'ADD' BUTTON CONTAINER
Container(
decoration: BoxDecoration(
borderRadius:
BorderRadius.circular(8),
color: Colors.black87,
),
child: Padding(
padding: const EdgeInsets.only(
left: 9,
top: 3,
right: 5,
bottom: 3),
child: InkWell(
splashColor: Colors.white,
onTap: () {
// print(restaurantItems[i].name);
cart.addItem(
restaurantItems[i].id,
restaurantItems[i].name,
restaurantItems[i].price,
restaurant,
);
},
child: Row(
children: [
Text(
'ADD',
style: TextStyle(
color: Colors.white,
),
),
Icon(
Icons.add,
color: Colors.white,
size: 17,
),
],
),
),
),
),
],
),
),
Padding(
padding: const EdgeInsets.only(
left: 10, top: 10, bottom: 11),
child: Text(
'₹${restaurantItems[i].price}',
style: TextStyle(
fontSize: 15,
color: kTextColor,
fontWeight: FontWeight.w500),
),
),
// Padding(
// padding: const EdgeInsets.only(
// left: 17, top: 17),
// child: InkWell(
// onTap: () {
// // Add to Cart
// },
// child: Row(
// children: [
// Padding(
// padding:
// const EdgeInsets.only(left: 15),
// child: Text(
// '${restaurantItems[i].quantity} Left',
// style: TextStyle(
// color: kTextLightColor,
// fontSize: 13,
// fontWeight: FontWeight.w700),
// ),
// )
// ],
// ),
// ),
// )
],
),
],
),
),
],
),
How can I fill the space between 'ITEM NAME' and 'ADD CONTAINER'? I have tried spacer(), but it doesn't work. Also, I have seen Expanded() widget but since I am new to flutter, I can't seem to get a hang of it. I have also added the Column widget, because of which the Spacer() widget is not working I guess.
Any help would be appreciated, thanks.
Use SizedBox widget between 'ITEM NAME' and 'ADD CONTAINER'. for example:
Widget build(BuildContext context) {
double height = MediaQuery.of(context).size.height;
double width = MediaQuery.of(context).size.width;
return Scaffold(
body: SafeArea(
child: Padding(
padding: const EdgeInsets.only(left: 10, top: 10),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text(
'test',
style: TextStyle(
fontSize: 17,
color: Colors.black,
fontWeight: FontWeight.w700),
),
// Spacer()
SizedBox(width: width/2,)
// 'ADD' BUTTON CONTAINER
Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(8),
color: Colors.black87,
),
child: Padding(
padding:
const EdgeInsets.only(left: 9, top: 3, right: 5, bottom: 3),
child: InkWell(
splashColor: Colors.white,
onTap: () {
// print(restaurantItems[i].name);
// cart.addItem(
// restaurantItems[i].id,
// restaurantItems[i].name,
// restaurantItems[i].price,
// restaurant,
// );
},
child: Row(
children: [
Text(
'ADD',
style: TextStyle(
color: Colors.white,
),
),
Icon(
Icons.add,
color: Colors.white,
size: 17,
),
],
),
),
),
),
],
),
),));
}
For providing space between widgets you can use SizedBox(width:10)
Use Spacer() to fill the space if you don't want to define size of width
Wrap your Column with ConstrainedBox and set the constraints value to BoxConstraints.expand(). The idea:
body: ConstrainedBox(
constraints: const BoxConstraints.expand(),
child: Column(children: [
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [const Text('ITEM NAME='), ElevatedButton(onPressed: () {}, child: const Text('ADD'))])
]))
Try this:
Text(
'${restaurantItems[i].name}',
style: TextStyle(
fontSize: 17,
color: kTextColor,
fontWeight: FontWeight.w700,
),
),
Spacer(flex: 1),
// 'ADD' BUTTON CONTAINER
Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(8),
color: Colors.black87,
),
child: Padding(
padding: const EdgeInsets.only(
left: 9,
top: 3,
right: 5,
bottom: 3,
),
child: InkWell(
splashColor: Colors.white,
onTap: () {
// print(restaurantItems[i].name);
cart.addItem(
restaurantItems[i].id,
restaurantItems[i].name,
restaurantItems[i].price,
restaurant,
);
},
child: Row(
children: [
Text(
'ADD',
style: TextStyle(
color: Colors.white,
),
),
Icon(
Icons.add,
color: Colors.white,
size: 17,
), // Icon
], // <Widget>[]
), // Row
), // InkWell
), // Padding
), // Container
Spacer(flex: 4),
How to add circular border for dialog box in a flutter?,I tried the below code but I can't able to get the desired output, I already added circular border but it's not working, I need circular border for dialog,Refer the expected output for details, please guide
My code :
`
class CustomDialog extends StatelessWidget {
#override
Widget build(BuildContext context) {
const double padding = 1.0;
return Dialog(
backgroundColor: Colors.green,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(8.0),
),
child: Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.all(Radius.circular(20.0))),
child: Column(mainAxisSize: MainAxisSize.min, children: [
Container(
margin: EdgeInsets.all(1),
width: double.infinity,
child: Text('title',
style: TextStyle(fontSize: 30, color: Colors.white)),
color: Colors.green,
),
Container(
color: Colors.white,
padding: EdgeInsets.all(10),
child: ListView(
shrinkWrap: true,
children: [
Container(
margin: EdgeInsets.only(left: 10, bottom: 10),
height: 30,
child: Text('one',
style: TextStyle(
fontSize: 20,
))),
Container(
margin: EdgeInsets.only(left: 10, bottom: 10),
height: 30,
child: Text('one',
style: TextStyle(
fontSize: 20,
))),
Container(
margin: EdgeInsets.only(left: 10, bottom: 10),
height: 30,
child: Text('one',
style: TextStyle(
fontSize: 20,
))),
],
),
),
Divider(
color: Colors.white,
),
Container(
color: Colors.white,
height: 50,
padding: EdgeInsets.all(5),
alignment: Alignment.centerRight,
child: Text(
'CANCEL',
style: TextStyle(fontSize: 20),
)),
])));
}
}
`
My expectation:
current output:
Just need to add ClipBehavior to Dialog.
import 'package:flutter/material.dart';
class CustomDialog extends StatelessWidget {
#override
Widget build(BuildContext context) {
const double padding = 1.0;
return Dialog(
backgroundColor: Colors.green,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(20.0),
),
clipBehavior: Clip.antiAlias, // add clipBehavior
child: Column(mainAxisSize: MainAxisSize.min, children: [
Container(
margin: EdgeInsets.all(1),
width: double.infinity,
child: Text('title',
style: TextStyle(fontSize: 30, color: Colors.white)),
color: Colors.green,
),
Container(
color: Colors.white,
padding: EdgeInsets.all(10),
child: ListView(
shrinkWrap: true,
children: [
Container(
margin: EdgeInsets.only(left: 10, bottom: 10),
height: 30,
child: Text('one',
style: TextStyle(
fontSize: 20,
))),
Container(
margin: EdgeInsets.only(left: 10, bottom: 10),
height: 30,
child: Text('one',
style: TextStyle(
fontSize: 20,
))),
Container(
margin: EdgeInsets.only(left: 10, bottom: 10),
height: 30,
child: Text('one',
style: TextStyle(
fontSize: 20,
))),
],
),
),
Divider(
color: Colors.white,
),
Container(
color: Colors.white,
height: 50,
padding: EdgeInsets.all(5),
alignment: Alignment.centerRight,
child: Text(
'CANCEL',
style: TextStyle(fontSize: 20),
)),
]),
);
}
}
The issue was with the Container you used to wrap the other widgets, you can add specific border radius to each container to fix.
I added a demo and code to get what you wanted your output to look like:
class CustomDialog extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Dialog(
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(15.0),
),
child: Container(
height: 340,
child: Column(
children: [
Container(
height: 60,
width: double.infinity,
padding: EdgeInsets.all(
15.0,
),
decoration: BoxDecoration(
color: Colors.green,
borderRadius: BorderRadius.only(
topLeft: Radius.circular(
15.0,
),
topRight: Radius.circular(
15.0,
),
),
),
child: Text(
'Baby Names',
style: TextStyle(
fontSize: 20,
color: Colors.white,
),
),
),
...List.generate(
5,
(index) => Padding(
padding: const EdgeInsets.all(10.0),
child: Align(
alignment: Alignment.centerLeft,
child: Text(
'List Names',
style: TextStyle(
fontSize: 18,
),
),
),
),
),
Divider(
color: Colors.grey[200],
thickness: 1.5,
),
Padding(
padding: const EdgeInsets.all(10.0),
child: Align(
alignment: Alignment.centerRight,
child: Text(
'CANCEL',
style: TextStyle(
fontSize: 18,
color: Colors.green,
),
),
),
),
],
),
),
);
}
}
RESULT:
You added RoundedRectangleBorder(),
import 'package:flutter/material.dart';
void main() {
runApp(
MaterialApp(
home: MyWidget(),
),
);
}
class MyWidget extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Dialog(
backgroundColor: Colors.green,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(8.0),
),
child: Container(
padding: EdgeInsets.only(
top: 10.0,
bottom: 5,
left: 5,
right: 5,
),
margin: EdgeInsets.only(top: 5),
decoration: new BoxDecoration(
color: Colors.white,
shape: BoxShape.rectangle,
borderRadius: BorderRadius.circular(5),
boxShadow: [
BoxShadow(
color: Colors.black26,
blurRadius: 10.0,
offset: const Offset(0.0, 10.0),
),
],
),
child: Column(
mainAxisSize: MainAxisSize.min, // To make the card compact
children: <Widget>[
Text(
"Baby",
style: TextStyle(
fontSize: 24.0,
fontWeight: FontWeight.w700,
),
),
Divider(color: Colors.grey,),
SizedBox(height: 16.0),
Text(
"text",
textAlign: TextAlign.center,
style: TextStyle(
fontSize: 16.0,
),
),
SizedBox(height: 24.0),
Align(
alignment: Alignment.bottomRight,
child: FlatButton(
onPressed: () {
Navigator.of(context).pop(); // To close the dialog
},
child: Text("buttonText"),
),
),
],
),
),
);
}
}
I am building a row of toggle buttons (on/off selectors) which is basically a row of containers and each container is a category and is clickable.
Q: How to make it so in a way when one category is selected all the others get deselected?
This is the categories widget I've build:
Widget header(){
return Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Container(
padding: EdgeInsets.only(top: 4.0, left: 0.0, right: 0.0, bottom: 6.0),
child: Container(
child: Center(
child: Column(
children: <Widget>[
SizedBox(height: 4.0,),
Container(
margin: EdgeInsets.only(left: 10.0, right: 10.0),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
InkWell(
splashColor: Colors.blue[100],
onTap: (){},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.blueAccent[100],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('All',
style: TextStyle(color: Colors.white, fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 1',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 2',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 3',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 4',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
],
),
),
SizedBox(height: 6.0,)
],
),
),
),
),
],
);
}`
The best way would be to use ListView.builder to build your items and save the selected indexes but you can also modify your existing code to save selected items in a list and check to see if the item is in the list and if it is then add selection format and refresh the page. You can implement that as shown below,
class MyApp extends StatefulWidget {
#override
MyAppState createState() => MyAppState();
}
class MyAppState extends State<MyApp> {
List<String> selectedCategory = new List<String>();
String all = 'All';
String category1 = 'category 1';
String category2 = 'category 2';
String category3 = 'category 3';
String category4 = 'category 4';
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text('Test'),
),
body: Container(
padding: const EdgeInsets.all(20.0),
child: header()
)));
}
Widget header(){
return Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Container(
padding: EdgeInsets.only(top: 4.0, left: 0.0, right: 0.0, bottom: 6.0),
child: Container(
child: Center(
child: Column(
children: <Widget>[
SizedBox(height: 4.0,),
Container(
margin: EdgeInsets.only(left: 10.0, right: 10.0),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
InkWell(
splashColor: Colors.blue[100],
onTap: (){
selectedCategory.add(all);
selectedCategory.add(category1);
selectedCategory.add(category2);
selectedCategory.add(category3);
selectedCategory.add(category4);
setState(() {});
},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: selectedCategory.contains(all) ? Colors.blueAccent[100] : Colors.grey[500],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('All',
style: TextStyle(color: Colors.white, fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){
selectedCategory = new List<String>();
selectedCategory.add(category1);
setState(() {});
},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: selectedCategory.contains(category1) ? Colors.blue[100] : Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 1',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){
selectedCategory = new List<String>();
selectedCategory.add(category2);
setState(() {});
},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: selectedCategory.contains(category2) ? Colors.blue[100] : Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 2',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){
selectedCategory = new List<String>();
selectedCategory.add(category3);
setState(() {});
},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: selectedCategory.contains(category3) ? Colors.blue[100] : Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 3',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
SizedBox(width: 2.0,),
InkWell(
splashColor: Colors.blue[100],
onTap: (){
selectedCategory = new List<String>();
selectedCategory.add(category4);
setState(() {});
},
child: Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: selectedCategory.contains(category4) ? Colors.blue[100] : Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('category 4',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
),
),
],
),
),
SizedBox(height: 6.0,)
],
),
),
),
),
],
);
}
}
Hope this helps.
Well, this piece of code can be optimized, but so far this worked just fine:
class Header extends StatefulWidget {
#override
_HeaderState createState() => _HeaderState();
}
class _HeaderState extends State<Header> {
List<bool> isSelected;
#override
void initState() {
isSelected = [true, false, false, false, false];
super.initState();
}
#override
Widget build(BuildContext context) {
return Column(
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: <Widget>[
ToggleButtons(
borderColor: Colors.transparent,
fillColor: Colors.transparent,
borderWidth: null,
selectedBorderColor: Colors.transparent,
selectedColor: Colors.transparent,
splashColor: Colors.transparent,
children: <Widget>[
!isSelected[0] ?
Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
margin: EdgeInsets.only(right: 3.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 1',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
)
:Container(
margin: EdgeInsets.only(right: 3.0),
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.blueAccent[100],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 1',
style: TextStyle(color: Colors.white, fontSize: 10.0, fontWeight: FontWeight.w700),),
),
!isSelected[1] ?
Container(
margin: EdgeInsets.only(right: 3.0),
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 2',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
)
:Container(
margin: EdgeInsets.only(right: 3.0),
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.blueAccent[100],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 2',
style: TextStyle(color: Colors.white, fontSize: 10.0, fontWeight: FontWeight.w700),),
),
!isSelected[2] ?
Container(
margin: EdgeInsets.only(right: 3.0),
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 3',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
)
:Container(
margin: EdgeInsets.only(right: 3.0),
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.blueAccent[100],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 3',
style: TextStyle(color: Colors.white, fontSize: 10.0, fontWeight: FontWeight.w700),),
),
!isSelected[3] ?
Container(
margin: EdgeInsets.only(right: 3.0),
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 4',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
)
:Container(
margin: EdgeInsets.only(right: 3.0),
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.blueAccent[100],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 4',
style: TextStyle(color: Colors.white, fontSize: 10.0, fontWeight: FontWeight.w700),),
),
!isSelected[4] ?
Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 5',
style: TextStyle(color: Colors.grey[900], fontSize: 10.0, fontWeight: FontWeight.w500),),
)
:Container(
padding: EdgeInsets.symmetric(vertical: 10.0, horizontal: 12.0),
decoration: BoxDecoration(
color: Colors.blueAccent[100],
borderRadius: BorderRadius.all(Radius.circular(48.0)),
),
child: Text('cat 5',
style: TextStyle(color: Colors.white, fontSize: 10.0, fontWeight: FontWeight.w700),),
),
],
onPressed: (int index) {
setState(() {
for (int i = 0; i < isSelected.length; i++) {
isSelected[i] = i == index;
}
});
},
isSelected: isSelected,
),
],
);
}
}