Reputation: 29468
I show dialog with list inside it.
showDialog(
context: context,
builder: (context) {
return AlertDialog(
title: Text(select_conference),
content: ListView.separated(
itemCount: selected.length,
separatorBuilder: (context, index) => CommonDivider(),
itemBuilder: (context, index) => ListTile(...),
),
);
});
But no matter how many elements is has - dialog fills all available height. Is there any solution to solve this without calculating height of list elements?
Upvotes: 16
Views: 22572
Reputation: 11
Wrapping the AlertDialog with a ConstrainedBox widget didn't work for me on its own (perhaps due to changes to Flutter since Rémi Rousselet's answer or because my use case doesn't involve scrolling or because I have other widgets nested in between showDialog and AlertDialog).
As far as I can tell the ConstrainedBox widget needs to be surrounded by a widget that allows it to be smaller than the screen, otherwise ConstrainedBox will just fill the whole screen.
The solution is to wrap ConstrainedBox with another widget that tells it how to layout, e.g., you can simply use Center for this.
Additionally, by default AlertDialog has a padding around it so that it doesn't go all the way to the screen's edges. While this is desirable in many cases, it also means that the actual dialog will be smaller than the maximum size you set in ConstraintBox due to this padding. To account for this, you can set the AlertDialog's insetPadding attribute to zero and then use a Padding widget around the ConstrainedBox widget to add this padding manually (see code below).
My full code is as follows:
await showDialog<void>(
context: context,
builder: (context) {
/* ... */
return Center(
child: Padding(
padding: EdgeInsets.symmetric(horizontal: 40.0, vertical: 24.0), // <- this is the default padding used by AlertDialog if insetPadding isn't set
child: ConstrainedBox(
constraints: BoxConstraints.loose(Size(300, 300)),
child: AlertDialog(
insetPadding: EdgeInsets.zero,
title: /* ... */,
content: /* ...*/
),
),
),
);
},
);
Upvotes: 0
Reputation: 418
wrap content with column and add widget like container set that width
showDialog(
context: context,
builder: (context) {
return AlertDialog(
title: const Text("Bookmark"),
insetPadding: const EdgeInsets.all(0),
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(10)),
content: Column(
mainAxisSize: MainAxisSize.min,
children: [
Container(
color: Colors.red,
width: screen.width * 0.70,
)
],
),
);
});
Upvotes: 0
Reputation: 651
A Dialog
's insetPadding property controls the padding around the dialog so you could set values to effectively reduce the height / width of the dialog, e.g.
showDialog(
context: context,
builder: (context) {
return AlertDialog(
insetPadding: EdgeInsets.symmetric(
horizontal: 50.0,
vertical: 100.0,
),
title: Text('...'),
content: Text('...'),
);
});
Upvotes: 3
Reputation: 277697
You can wrap it inside a SizedBox
or ConstrainedBox
ConstrainedBox(
constraints: BoxConstraints(maxHeight: 100.0),
child: AlertDialog(
...
),
);
Alternatively, you can set shrinkWrap
to true
in your ListView
so that it takes the least amount of vertical space necessary.
ListView(
shrinkWrap: true,
...
)
Upvotes: 11
Reputation: 32559
Wrap your content with a Column
and set mainAxisSize
to MainAxisSize.min
:
AlertDialog(
content: Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
//your content
],
),
Upvotes: 47