I'm wondering if there's a way to disable the shadow/overlay affect a dialog has? Basically so I can get a dialog looking like it does on the right side of this image:
My best attempt at this was to use a stack containing my custom dialog which are then toggled to be displayed or not but then I had trouble being able to scroll each custom dialog's own ListView without it messing up another. I know this goes against the Material Design guidelines but I'm trying to replicate a UI from dribble.com.
Thanks!
Edit:
I've managed to almost achieve this affect by editing the showGeneralDialog method but there's still an elevation shadow:
await showGeneralDialog(
context: context,
pageBuilder: (BuildContext buildContext,
Animation<double> animation,
Animation<double> secondaryAnimation) {
return SafeArea(
child: Builder(builder: (context) {
return AlertDialog(
content: Container(
color: Colors.white,
width: 150.0,
height: 150.0,
child: Center(child: Text("Testing"))));
}),
);
},
barrierDismissible: true,
barrierLabel: MaterialLocalizations.of(context)
.modalBarrierDismissLabel,
barrierColor: null,
transitionDuration:
const Duration(milliseconds: 150));
Edit 2: Just an image to illustrate the change on the above code showing that I've so far been able to disable the dark overlay but there's still elevation on the dialog which I can't seem to get rid of:
Edit 3: I think if I'm able to change the AlertDialog in the showGeneralDialog's Builder then I can get it to work but I'm having trouble putting in something which is Material but doesn't take up the whole screen.
Got it to work! You have to create your own dialog like Widget within the Builder of the showGeneralDialog method along with setting the barrierColor to null:
await showGeneralDialog(
context: context,
pageBuilder: (BuildContext buildContext,
Animation<double> animation,
Animation<double> secondaryAnimation) {
return SafeArea(
child: Builder(builder: (context) {
return Material(
color: Colors.transparent,
child: Align(
alignment: Alignment.center,
child: Container(
height: 200.0,
width: 250.0,
color: Colors.white,
child:
Center(child: Text('Testing')))));
}),
);
},
barrierDismissible: true,
barrierLabel: MaterialLocalizations.of(context)
.modalBarrierDismissLabel,
barrierColor: null,
transitionDuration: const Duration(milliseconds: 150));
Friend, set the parameter "elevation" = 0. It's work.
AlertDialog(
elevation: 0,
),
I have achieved the result using below code. Trick is barrierColor property in showDialog method which I set white color with opacity value zero and barrier shadow is vanished
AlertDialog alert = AlertDialog(
backgroundColor: Colors.transparent,
elevation: 0,
content: new Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Loader(),
],
),
);
showDialog(
barrierColor: Colors.white.withOpacity(0),
barrierDismissible: false,
context: context,
builder: (BuildContext context) {
return WillPopScope(
onWillPop: (){},
child: alert);
},
);
Just set in showDialog the barrierColor parameter to Colors.transparent.
Example:
showDialog(
context: context,
barrierColor: Colors.transparent, // Here the solution
builder: (context) => myDialog(),
);
Related
default switch button in flutter have padding, I want reduce padding, I tried everything I know but I still can't do it
default
I want
I made it
Switch(
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
value: !state,
activeTrackColor: PrimaryColor.value,
onChanged: (value)=> context.read<SettingRo>().change(value),
),
You can use Material Button or Inkwell or Button theme for this.
Solution 1:MaterialButton/RawMaterialButton:
MaterialButton(
onPressed: () {},
color: Colors.red,
minWidth: 0,
height: 0,
padding: EdgeInsets.zero,
child: Text('Material Button'),
)
Solution 2 Inkwell:
InkWell(
child: Center(child: Container(child: Text("Inkwell"))),
onTap: () => onPressed()
);
Solution 3: wrap the button in a ButtonTheme.
give maxWith and height (set to zero to wrap the child) and then pass your button as the child.
ButtonTheme(
padding: EdgeInsets.symmetric(vertical: 2.0, horizontal: 6.0), //adds padding inside the button
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap, //limits the touch area to the button area
minWidth: 0, //wraps child's width
height: 0, //wraps child's height
child: RaisedButton(onPressed: (){}, child: Text('ButtonTheme')), //your original button
);
I can't put icon and text at the same time for floatbuttom?
The error in the title.
return new Scaffold(
appBar: new AppBar(
title: new Text('Hello'),
backgroundColor: Colors.blue,
),
body: new Container(
padding: new EdgeInsets.all(22.0),
child: new Column(
children: <Widget>[
new Text("it's working, $name"),
new FlatButton(onPressed:()=> onClick('test'), child: new Icon(Icons.accessibility),child : new Text('data'))
],
)));
}
}
Your problem is inside the FlatButton widget, you are using child attribute two times.
You can put text and icon, this way:
FlatButton.icon(
icon: Icon(Icons.accessibility),
label: Text('data'),
onPressed: () {
//Code to execute when Button is clicked
},
)
I believe wrapping both children in either a row or column would solve your problem.
FlatButton can only take one widget as the child parameter.
FlatButton(
onPressed:()=> onClick('test')},
child: Row(
children: <Widget>[
new Icon(Icons.accessibility),
new Text('data'),
],
),
),
I am trying in vain to add onLongPress to an image button along with onPressed. I get error: The named parameter 'onDoubleTap' isn't defined.
I have multiple rows of 2 horizontal image buttons using rows and expanded. Everything works except onLongPress (or onDoubleTap). What am I doing wrong, do I have to rebuild the entire code in a different format, or am I overcomplicating this?
I also tried to add a new child (error: already defined), GestureDetector, InkWell, with no success.
body: SingleChildScrollView(
child: Container(
child: Column(
children: <Widget>[
Center(
child: Row(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: <Widget>[
Expanded(
child: FlatButton(
onPressed: () {
setState(() {
launchURL();
});
},
//Trying to add onLongPress , error: "onLongPress not defined
//If I try add a new child it says child already defined
onLongPress: () => _showAlertMessage(context, "message"),
padding: EdgeInsets.all(6.0),
child: Image.asset(
'images/image1.png',
))),
Expanded(
child: FlatButton(
onPressed: () {
setState(() {
launchURL();
});
},
padding: EdgeInsets.all(6.0),
child: Image.asset(
'images/image2.png',
)
)//flat button
),//expanded
])), //row-center
//Repeat above for rows of 2 more image buttons
The code runs with a single onPressed for each button and does not display any errors, but adding any second click event displays errors.
Flatbutton only supports the onPressed callback, not onLongpressed, etc. Suggest you re-look at using gesture detector or other widgets that support long press.
I would try using two containers, each wrapped in a gesture detector widget, as children in the row. Each container having a text and/or image content. You can then pick up onTap, double tap, long press, etc on each container. Not tested this as I am on my phone but should work. They are probably more elegant widgets to use than container.
Thanks for the feedback, really appreciated. I replaced flatButton with Gesture detector inside a column, used onTap instead of onPressed, put image in new Column, added onLongPress. The code runs. When I added the second Expanded I got this error:
E/InputMethodManager( 7133): prepareNavigationBarInfo() rootView is null
I read here that "RootView is the View in which all the other views are placed. It is like the root node in a tree structure which is the parent to all the children.", but I can't see my mistake here. I did a full restart and that error is gone.
Container(
child: Row(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: <Widget>[
Expanded(
child: GestureDetector(
onLongPress: () {
setState(() {
_showAlertMessage(context, "message");
});
},
onTap: () {
setState(() {
_launchUrl;
});
},
child: Container(
padding: EdgeInsets.all(6.0),
child: Image.asset(
'images/image1.png',
)
)),
), //Expanded
Expanded(
child: GestureDetector(
on: () {
setState(() {
_showAlertMessage(context, "message");
});
},
onTap: () {
setState(() {
_launchUrl;
});
},
child: Container(
padding: EdgeInsets.all(6.0),
child: Image.asset(
'images/image2.png',
)
)),
),
])),
NOTE: As version 2 of flutter FlatButton is deprecated. You should use TextButton instead.
I don't know how you are using the GestureDetector but it's the best solution fit for your question and supports different aspects of user press Gestures. So I prepared the sample code below to see how it works.
body: SingleChildScrollView(
child: Container(
child: Column(children: <Widget>[
Center(
child: Row(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: <Widget>[
Expanded(
child: GestureDetector(
onTap: () => print('onTap'),
onLongPress: () => print('onLongPress'),
onDoubleTap: () => print('onDoubleTap'),
child: Image.network(
'https://lp-cms-production.imgix.net/image_browser/social-beast-GettyRF_136327669.jpg?auto=format&fit=crop&sharp=10&vib=20&ixlib=react-8.6.4&w=850&q=50&dpr=2'),
) //flat button
),
Expanded(
child: GestureDetector(
onTap: () => print('onTap'),
onLongPress: () => print('onLongPress'),
onDoubleTap: () => print('onDoubleTap'),
child: Image.network(
'https://lp-cms-production.imgix.net/image_browser/lions-hunting-500pxRF_7416880.jpg?auto=format&fit=crop&sharp=10&vib=20&ixlib=react-8.6.4&w=850&q=50&dpr=2'),
)
), //expanded
])
), //row-center
]
)
)
)
There are yet so many other gestures for GestureDetector that can be found here.
You can use InkWell widget
child: InkWell(
onLongPress: () {
setState(() {
tip++;
});
},
child: FloatingActionButton(
heroTag: "btn+",
onPressed: () {
setState(() {
tip++;
});
},
backgroundColor: Colors.grey.shade400,
child: Icon(
Icons.add,
color: Colors.black,
),
),
),
I am developing an app that includes GridView, here is the simplest form of code:
return OrientationBuilder(builder: (context, orientation) {
return RefreshIndicator(
onRefresh: refreshList,
child: new GridView.builder(
itemCount: dergiler.length,
gridDelegate: new SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: 2,
mainAxisSpacing: 1.0,
crossAxisSpacing: 1.0,
childAspectRatio: 0.7),
itemBuilder: (BuildContext context, int index) {
return Container(
alignment: Alignment.center,
child: Dergielemet(dergiler[index], index),
);
},
),
);
});
When I use the as childAspectRatio as 0.7 I am getting what I want. Here is the image:
)
However, when I try the same code on another device with slightly different screen size, there would be overflow errors because elements of GridView are overflowing each other. Example:
use the as childAspectRatio some thing like this
MediaQuery.of(context).size.height/980
I just have a simple Card like new Card(child: new Text('My cool card')) and I want to be able to click anywhere on it to run some function, except there's no onPressed method for a Card. I could add a button to the bottom, but that's not ideal for this situation.
Anyone know how to make the whole card clickable?
Flutter use composition over properties.
Wrap the desired widget into a clickable one to achieve what you need.
Some clickable widgets : GestureDetector, InkWell, InkResponse.
GestureDetector(
onTap: () => ......,
child: Card(...),
);
Flutter provides the InkWell Widget. by registering a callback you can decide what happens when user clicks on the card (called tap in flutter). InkWell also implements Material Design ripple effect
Card(
child: new InkWell(
onTap: () {
print("tapped");
},
child: Container(
width: 100.0,
height: 100.0,
),
),
),
I think you can also use InkWell apart from GestureDetector just wrap the card inside InkWell() Widget
InkWell(
onTap: (){ print("Card Clicked"); }
child: new Card(),
);
You can use Inkwell and insert splashColor which, at the click of the user, creates the rebound effect with the chosen color, on the card ..
This is mainly used in material design.
return Card(
color: item.completed ? Colors.white70 : Colors.white,
elevation: 8,
child: InkWell(
splashColor: "Insert color when user tap on card",
onTap: () async {
},
),
);
Wrap a card in GestureDetector Widget like a below:
GestureDetector(
onTap: () {
// To do
},
child: Card(
),
),
Another way is as follows:
InkWell(
onTap: () {
// To do
},
child: Card(),
),
In Flutter, InkWell is a material widget that responds to touch action.
InkWell(
child: Card(......),
onTap: () {
print("Click event on Container");
},
);
GestureDetector is a widget that detects the gestures.
GestureDetector(
onTap: () {
print("Click event on Container");
},
child: Card(.......),
)
Difference
InkWell is a material widget and it can show you a Ripple Effect whenever a touch was received.
GestureDetector is more general-purpose, not only for touch but also for other gestures.
The most preferred way is to add ListTile as Card child. Not only does ListTile contain the method onTap it also helps you in making Card interesting.
Card(
child: ListTile(
title: Text('Title')
leading: CircleAvatar(
backgroundImage: AssetImage('assets/images/test.jpg'),
),
onTap: () {
print('Card Clicked');
},
),
),
You also can insert a card into a TextButton:
TextButton clickableCard = TextButton(child: card, onPressed: onCardClick, style: [...]);
This brings the advantage, that you get some features for free. For example in Flutter Web, you get a mousover effect and the cursor changes to the hand so that ths user knows, he can click there. Other additional features can be customised using the style.
Do something on tap/click of 'child' in Flutter:-
Code:-your code looks like:
child: Card(------
------------
--------),
Step1:- Put your mouse cursor on Card then, press- Alt+Enter(in windows) select wrap with widget.
Step2:- Change your default widget into GestureDetector.
final code:-
child: GestureDetector(
onTap: YourOnClickCode(),
child: Card(------
------------
--------),
),
Most of the answers are brilliant but I just want to share mine for the one who wants to make/show a ripple effect on Tap of card or list tile.
Card(
child: TextButton(
onPressed: ()=> ...,
child: ListTile(
title: Text('title'),
),
),
);