How to achieve transparent background in ChoiceChip? - flutter

I am creating a set of selections using ChoiceChip widget. I wanted to make the chips to have transparent background under certain condition like this image
I tried putting backgroundColor: Colors.transparent, but it'll turn white instead of transparent.
Here is my codes:
String _selectedSize = "";
var sizes = ['XS', 'S', 'M', 'L', 'XL'];
_customChip(size) => InkWell(
child: Container(
width: 40.0,
height: 40.0,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(20.0),
color: Colors.white,
),
child: Stack(
children: <Widget>[
Center(child: Text(size, style: _chipTextStyle,)),
Center(
child: RotationTransition(
turns: AlwaysStoppedAnimation(315/360),
child: Container(height: 1.0, color: Colors.grey),
),
),
],
),
),
);
return Wrap(
alignment: WrapAlignment.center,
crossAxisAlignment: WrapCrossAlignment.center,
children: sizes.map((size) {
return ChoiceChip(
pressElevation: 1.0,
backgroundColor: Colors.transparent, // this doesn't work
label: _customChip(size),
labelPadding: EdgeInsets.symmetric(horizontal: 2.0),
padding: EdgeInsets.all(2.0),
materialTapTargetSize: MaterialTapTargetSize.padded,
shape: CircleBorder(),
selected: _selectedSize == size,
selectedColor: _themeColor,
onSelected: (isSelected) {
setState(() {
_selectedSize = size;
});
},
);
}).toList(),
);
Is there any idea how to make it transparent, or I should use widgets other than ChoiceChip? Thanks!

The Chip widget has a material which is colored according to the Theme. You can change that by changing the Theme.canvasColor, like this:
Theme(
data: ThemeData(canvasColor: Colors.transparent),
child: Chip(
label:Container(/*your widget*/),
backgroundColor: Colors.transparent, // or any other color
),
)
Or, you can keep your old Theme (except the canvasColor) by doing this:
Theme(
data: Theme.of(context).copyWith(canvasColor: Colors.transparent),
child: Chip(
label: Container(/*your widget*/),
backgroundColor: Colors.transparent, // or any other color
),
)

I have tried so many thigns with ChoiceChips for transparent background and not getting success then i decided to do it in another way as you also asked for alternate option, so i have created example for you where it similarly works same as ChoiceChips:
Note: For unselected background color i used
"Colors.grey.withOpacity(0.1)" but you can also use
"Colors.transparent"
import 'package:flutter/material.dart';
class MyChoiceChipsRadio extends StatefulWidget {
createState() {
return CustomRadioState();
}
}
class CustomRadioState extends State<MyChoiceChipsRadio> {
List<RadioModel> sampleData = List<RadioModel>();
#override
void initState() {
// TODO: implement initState
super.initState();
sampleData.add(RadioModel(false, 'XS'));
sampleData.add(RadioModel(false, 'S'));
sampleData.add(RadioModel(false, 'M'));
sampleData.add(RadioModel(false, 'L'));
sampleData.add(RadioModel(false, 'XL'));
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("ListItem"),
),
body: Stack(
children: <Widget>[
Container(
decoration: BoxDecoration(
image: DecorationImage(
image: AssetImage("assets/back_image.png"),
fit: BoxFit.cover,
),
)
),
ListView.builder(
itemCount: sampleData.length,
itemBuilder: (BuildContext context, int index) {
return InkWell(
//highlightColor: Colors.red,
splashColor: Colors.blueAccent,
onTap: () {
setState(() {
sampleData.forEach((element) => element.isSelected = false);
sampleData[index].isSelected = true;
});
},
child: RadioItem(sampleData[index]),
);
},
),
],
),
);
}
}
class RadioItem extends StatelessWidget {
final RadioModel _item;
RadioItem(this._item);
#override
Widget build(BuildContext context) {
return Container(
margin: EdgeInsets.all(15.0),
child: Row(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Container(
height: 50.0,
width: 50.0,
child: Center(
child: Text(_item.buttonText,
style: TextStyle(
color:
_item.isSelected ? Colors.red : Colors.grey,
//fontWeight: FontWeight.bold,
fontSize: 18.0)),
),
decoration: BoxDecoration(
color: _item.isSelected
? Colors.white
: Colors.grey.withOpacity(0.1),
shape: BoxShape.circle,
border: Border.all(color: _item.isSelected
? Colors.red
: Colors.grey, width: 1.0)
),
),
],
),
);
}
}
class RadioModel {
bool isSelected;
final String buttonText;
RadioModel(this.isSelected, this.buttonText);
}
Hope it helps :)

Related

Calling a page using a provider inside a bottom navigation bar in flutter

Am using a provider for each page in my flutter application like so :
class HolidayListState extends State<HolidayListView>{
#override
Widget build(BuildContext context) {
final vm = Provider.of<HolidayListViewModel>(context);
if(vm.holidaysviews == null){
return Align(child: CircularProgressIndicator());
}else if(vm.holidaysviews.isEmpty) {
return Align(child: Text("No holidays found."));
}else{
return Scaffold(
backgroundColor: Color(0xfff0f0f0),
body:SingleChildScrollView(
child: Container(
height: MediaQuery.of(context).size.height,
width: MediaQuery.of(context).size.width,
child: Stack(
children: [
Container(
padding: EdgeInsets.only(top: 145),
height: MediaQuery.of(context).size.height,
width: double.infinity,
child: ChangeNotifierProvider(
create: (_) => HolidayListViewModel(),
child: ListView.builder(
itemCount: vm.holidaysviews.length,
itemBuilder: (context, index) {
final holiday = vm.holidaysviews[index];
final item = holiday.toString();
return Dismissible(
key: UniqueKey(),
background: Container(
alignment: AlignmentDirectional.centerEnd,
color: Colors.red,
child: Icon(
Icons.delete,
color: Colors.white,
),
),
direction: DismissDirection.endToStart,
confirmDismiss:
(DismissDirection direction) async {
return await showDialog(
context: context,
builder: (BuildContext context) {
return AlertDialog(
title: const Text("Confirm"),
content: const Text(
"Are you sure you wish to delete this item?"),
actions: <Widget>[
FlatButton(
onPressed: () async {
await HolidayWebServices().deleteHoliday(holiday.id.toString());
Navigator.of(context).pop(true);
},
child: const Text("DELETE")),
FlatButton(
onPressed: () =>
Navigator.of(context).pop(false),
child: const Text("CANCEL"),
),
],
);
},
);
},
onDismissed: (direction) {
if (!mounted) {
setState(() {
vm.holidaysviews.removeAt(index);
});
}
},
child: Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(25),
color: Colors.white,
),
width: double.infinity,
height: 110,
margin: EdgeInsets.symmetric(
vertical: 10, horizontal: 20),
padding: EdgeInsets.symmetric(
vertical: 10, horizontal: 20),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Container(
width: 30,
height: 30,
margin: EdgeInsets.only(right: 15),
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(30),
border: Border.all(
width: 3, color: Colors.deepPurple),
),
child: Text(
holiday.duration
.toString(),
textAlign: TextAlign.center,
),
),
Expanded(
child: Column(
crossAxisAlignment:
CrossAxisAlignment.start,
children: <Widget>[
ConditionalBuilder(
condition:
holiday.status ==
"PENDING",
builder: (context) {
return Container(
decoration: BoxDecoration(
borderRadius:
BorderRadius.circular(25),
color: Colors.white,
),
foregroundDecoration:
BadgeDecoration(
badgeColor: Colors.orange,
badgeSize: 70,
textSpan: TextSpan(
text:holiday.status,
style: TextStyle(
color: Colors.white,
fontSize: 12),
),
),
);
},
),
ConditionalBuilder(
condition:
holiday.status ==
"ACCEPTED",
builder: (context) {
return Container(
decoration: BoxDecoration(
borderRadius:
BorderRadius.circular(25),
color: Colors.white,
),
foregroundDecoration:
BadgeDecoration(
badgeColor: Colors.green,
badgeSize: 70,
textSpan: TextSpan(
text: holiday.status,
style: TextStyle(
color: Colors.white,
fontSize: 12),
),
),
);
},
),
ConditionalBuilder(
condition:
holiday.status ==
"REFUSED",
builder: (context) {
return Container(
decoration: BoxDecoration(
borderRadius:
BorderRadius.circular(25),
color: Colors.white,
),
foregroundDecoration:
BadgeDecoration(
badgeColor: Colors.red,
badgeSize: 70,
textSpan: TextSpan(
text: holiday.status,
style: TextStyle(
color: Colors.white,
fontSize: 12),
),
),
);
},
),
Row(
children: <Widget>[
Icon(
Icons.calendar_today,
color: Colors.deepPurple,
size: 20,
),
Text(
holiday.startDate,
style: TextStyle(
color: primary,
fontSize: 13,
letterSpacing: .3)),
],
),
SizedBox(
height: 6,
),
Row(
children: <Widget>[
Icon(
Icons.calendar_today,
color: Colors.deepPurple,
size: 20,
),
Text(holiday.endDate,
style: TextStyle(
color: primary,
fontSize: 13,
letterSpacing: .3)),
],
),
SizedBox(
height: 6,
),
Row(
children: <Widget>[
Icon(
Icons.assignment,
color: Colors.deepPurple,
size: 20,
),
SizedBox(
width: 5,
),
Text(holiday.type,
style: TextStyle(
color: primary,
fontSize: 13,
letterSpacing: .3)),
],
),
],
),
)
],
),
),
);
},
),
),
),
Container(
height: 140,
width: double.infinity,
decoration: BoxDecoration(
color: primary,
borderRadius: BorderRadius.only(
bottomLeft: Radius.circular(30),
bottomRight: Radius.circular(30))),
child: Padding(
padding: const EdgeInsets.symmetric(horizontal: 30),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: <Widget>[
Text(
"Holidays",
textAlign: TextAlign.center,
style: TextStyle(color: Colors.white, fontSize: 24),
),
],
),
),
),
Container(
child: Column(
children: <Widget>[
SizedBox(
height: 110,
),
],
),
)
],
),
),
),
floatingActionButton: FloatingActionButton(
child: Icon(Icons.add),
backgroundColor: kPrimaryColor,
onPressed: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) {
return StepperDemo();
},
),
);
},
)
);
}}
}
class BadgeDecoration extends Decoration {
final Color badgeColor;
final double badgeSize;
final TextSpan textSpan;
const BadgeDecoration(
{#required this.badgeColor,
#required this.badgeSize,
#required this.textSpan});
#override
BoxPainter createBoxPainter([onChanged]) =>
_BadgePainter(badgeColor, badgeSize, textSpan);
}
class _BadgePainter extends BoxPainter {
static const double BASELINE_SHIFT = 1;
static const double CORNER_RADIUS = 4;
final Color badgeColor;
final double badgeSize;
final TextSpan textSpan;
_BadgePainter(this.badgeColor, this.badgeSize, this.textSpan);
#override
void paint(Canvas canvas, Offset offset, ImageConfiguration configuration) {
canvas.save();
canvas.translate(
offset.dx + configuration.size.width - badgeSize, offset.dy);
canvas.drawPath(buildBadgePath(), getBadgePaint());
// draw text
final hyp = math.sqrt(badgeSize * badgeSize + badgeSize * badgeSize);
final textPainter = TextPainter(
text: textSpan,
textDirection: TextDirection.ltr,
textAlign: TextAlign.center);
textPainter.layout(minWidth: hyp, maxWidth: hyp);
final halfHeight = textPainter.size.height / 2;
final v = math.sqrt(halfHeight * halfHeight + halfHeight * halfHeight) +
BASELINE_SHIFT;
canvas.translate(v, -v);
canvas.rotate(0.785398); // 45 degrees
textPainter.paint(canvas, Offset.zero);
canvas.restore();
}
Paint getBadgePaint() => Paint()
..isAntiAlias = true
..color = badgeColor;
Path buildBadgePath() => Path.combine(
PathOperation.difference,
Path()
..addRRect(RRect.fromLTRBAndCorners(0, 0, badgeSize, badgeSize,
topRight: Radius.circular(CORNER_RADIUS))),
Path()
..lineTo(0, badgeSize)
..lineTo(badgeSize, badgeSize)
..close());
}
and I want to call the page in a navigation bar , right now this is the navigation bar page :
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:helium/views/holiday/holidayList.dart';
import 'package:helium/views/login/login_screen.dart';
import 'package:helium/views/profile/profile_home.dart';
import 'package:helium/views/time_tracking/time_tracking_home.dart';
class MainMenu extends StatefulWidget {
#override
_MainMenuState createState() => _MainMenuState();
void signOut() {}
}
class _MainMenuState extends State<MainMenu> {
PageController _pageController;
int _page = 0;
List icons = [
Icons.home,
Icons.event,
Icons.beach_access_rounded
// Icons.ac_unit,
];
List<Widget> _widgetOptions = <Widget>[
Profile(),
MyCalendarPage(),
HolidayListView()
];
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
backgroundColor: Theme.of(context).primaryColor,
actions: <Widget>[
IconButton(
onPressed: () {
signOut();
},
icon: Icon(Icons.lock_open),
)
],
),
body: PageView(
physics: NeverScrollableScrollPhysics(),
controller: _pageController,
onPageChanged: onPageChanged,
children: _widgetOptions,
),
bottomNavigationBar: bottomMenu(),
floatingActionButtonAnimator: FloatingActionButtonAnimator.scaling,
floatingActionButtonLocation: FloatingActionButtonLocation.centerDocked,
);
}
Widget bottomMenu(){
return BottomAppBar(
child: Row(
mainAxisSize: MainAxisSize.max,
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: <Widget>[
SizedBox(width: 2),
buildTabIcon(0),
buildTabIcon(1),
buildTabIcon(2),
SizedBox(width: 2),
],
),
color: Theme.of(context).primaryColor,
shape: CircularNotchedRectangle(),
);
}
void navigationTapped(int page) {
_pageController.jumpToPage(page);
}
signOut() {
setState(() {
widget.signOut();
Navigator.pushReplacement(
context,
MaterialPageRoute(builder: (context) => LoginScreen()),
);
print("signed out");
});
}
#override
void initState() {
super.initState();
// getPref();
_pageController = PageController();
}
#override
void dispose() {
super.dispose();
_pageController.dispose();
}
void onPageChanged(int page) {
setState(() {
this._page = page;
});
}
buildTabIcon(int index) {
return IconButton(
icon: Icon(
icons[index],
size: 24.0,
),
color: Colors.grey,
//_page == index
//? Theme.of(context).accentColor
//: Theme.of(context).textTheme.caption.color,
onPressed: () => _pageController.jumpToPage(index),
);
}
}
apparently I have to call the provider somewhere in the bottom nav bar page but I don't know how to do it , right now am getting this error , so if anyone knows what seems to be wrong , I would appreciate so me help , here's the stack trace :
Error: Could not find the correct Provider<HolidayListViewModel> above this HolidayListView Widget
This happens because you used a `BuildContext` that does not include the provider
of your choice. There are a few common scenarios:
- You added a new provider in your `main.dart` and performed a hot-reload.
To fix, perform a hot-restart.
- The provider you are trying to read is in a different route.
Providers are "scoped". So if you insert of provider inside a route, then
other routes will not be able to access that provider.
- You used a `BuildContext` that is an ancestor of the provider you are trying to read.
Make sure that HolidayListView is under your MultiProvider/Provider<HolidayListViewModel>.
This usually happens when you are creating a provider and trying to read it immediately.
For example, instead of:
Widget build(BuildContext context) {
return Provider<Example>(
create: (_) => Example(),
// Will throw a ProviderNotFoundError, because `context` is associated
// to the widget that is the parent of `Provider<Example>`
child: Text(context.watch<Example>()),
),
}
consider using `builder` like so:
Widget build(BuildContext context) {
return Provider<Example>(
create: (_) => Example(),
// we use `builder` to obtain a new `BuildContext` that has access to the provider
builder: (context) {
// No longer throws
return Text(context.watch<Example>()),
}
),
}

How to generate new route to the new stfull widget when user created new container?

I am currently developing an app which people can save their receipt in it, I shared home screen below,initial time It will be empty, as soon as user add new menu, it will get full with menu, After user added new menu, the should be able to click the menu container, and access to new screen for example, İn home screen I created container which called "CAKES", the cakes screen should be created, if I created another menu in my home screen It should also created too, I currently menu extanded screen as a statefull widget already, you can see below, but my question is How can I create this page for spesific menu's , How can I store them, in list, in map etc, Lastly, I dont want user information dissapear, I know I have to use database, but I want to use local database, How can I handle with that, Have a nice day...
import 'package:flutter/material.dart';
import 'package:lezzet_kitabi/add_menu_screen.dart';
import 'package:lezzet_kitabi/constants.dart';
import 'package:lezzet_kitabi/widgets.dart';
class HomeScreen extends StatefulWidget {
HomeScreen({this.newMenuName,this.imagePath});
final imagePath;
final newMenuName;
static String id="homeScreen";
#override
_HomeScreenState createState() => _HomeScreenState();
}
class _HomeScreenState extends State<HomeScreen> {
Widget buildBottomSheet(BuildContext context)=>AddMenuScreen(buttonText: "Menü Ekle",route: HomeScreen,);
void initState(){
super.initState();
if (widget.newMenuName!=null && widget.imagePath!=null){
Widget newMenu=MenuCard(newMenuName: widget.newMenuName,imagePath: widget.imagePath);
menuCards.insert(0,newMenu);
}
}
#override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
backgroundColor: kColorTheme1,
appBar: AppBar(
centerTitle: true,
automaticallyImplyLeading: false,
elevation: 5,
backgroundColor: Color(0xFFF2C3D4).withOpacity(1),
title:TitleBorderedText(title:"SEVIMLI YEMEKLER", textColor: Color(0xFFFFFB00)),
actions: [
CircleAvatar(
radius: 27,
backgroundColor: Colors.transparent,
backgroundImage: AssetImage(kCuttedLogoPath),
),
],
),
body: Container(
decoration: BoxDecoration(
image: DecorationImage(
image: AssetImage(kBGWithLogoOpacity),
fit: BoxFit.cover,
),
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Expanded(
child: GridView.count(
crossAxisCount: 2,
children:menuCards,
),
),
Column(
mainAxisAlignment: MainAxisAlignment.end,
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Padding(
padding: EdgeInsets.all(10),
child: Container(
decoration: BoxDecoration(
boxShadow:[
BoxShadow(
color: Colors.black.withOpacity(1),
spreadRadius: 2,
blurRadius: 7,
offset: Offset(0,4),
),
],
color: kColorTheme7,
borderRadius: BorderRadius.circular(40),
),
child: FlatButton(
onPressed: (){
showModalBottomSheet(
context: context,
builder: (BuildContext context)=> AddMenuScreen(buttonText: "Menü Ekle",route: "homeScreen",),
);
},
child: TitleBorderedText(title: "LEZZET GRUBU EKLE",textColor: Colors.white,)
),
),
),
],
)
],
),
),
),
);
}
}
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'package:lezzet_kitabi/screens/home_screen.dart';
import 'package:lezzet_kitabi/widgets.dart';
import 'constants.dart';
import 'dart:math';
class AddMenuScreen extends StatefulWidget {
AddMenuScreen({#required this.buttonText, #required this.route});
final route;
final String buttonText;
static String id="addMenuScreen";
#override
_AddMenuScreenState createState() => _AddMenuScreenState();
}
class _AddMenuScreenState extends State<AddMenuScreen> {
int selectedIndex=-1;
Color _containerForStickersInactiveColor=Colors.white;
Color _containerForStickersActiveColor=Colors.black12;
final stickerList= List<String>.generate(23, (index) => "images/sticker$index");
String chosenImagePath;
String menuName;
int addScreenImageNum;
void initState(){
super.initState();
createAddScreenImageNum();
}
void createAddScreenImageNum(){
Random random =Random();
addScreenImageNum = random.nextInt(3)+1;
}
#override
Widget build(BuildContext context) {
return Material(
child: Container(
color: kColorTheme9,
child: Container(
height: 400,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.only(topRight: Radius.circular(40),topLeft: Radius.circular(40)),
),
child:Padding(
padding:EdgeInsets.all(20.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
mainAxisAlignment: MainAxisAlignment.start,
children: [
Container(
decoration: BoxDecoration(
color: kColorTheme2,
borderRadius: BorderRadius.circular(90)
),
child: TextField(
style: TextStyle(
color: Colors.black,
fontFamily:"Graduate",
fontSize: 20,
),
textAlign: TextAlign.center,
onChanged: (value){
menuName=value;
},
decoration: InputDecoration(
border:OutlineInputBorder(
borderRadius: BorderRadius.circular(90),
borderSide: BorderSide(
color: Colors.teal,
),
),
hintText: "Menü ismi belirleyin",
hintStyle: TextStyle(
color: Colors.black.withOpacity(0.2),
fontFamily: "Graduate",
),
),
),
),
SizedBox(height: 20,),
Text(" yana kadırarak menünüz icin bir resim secin",textAlign: TextAlign.center,
style: TextStyle(fontFamily: "Graduate", fontSize: 12),),
SizedBox(height: 20,),
Expanded(
child: ListView.builder(
scrollDirection: Axis.horizontal,
itemCount: stickerList.length,
itemBuilder: (context,index){
return Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(30),
color: index == selectedIndex ?
_containerForStickersActiveColor :
_containerForStickersInactiveColor,
),
child:FlatButton(
child: Image(
image: AssetImage("images/sticker$index.png"),
),
onPressed: (){
setState(() {
selectedIndex = index;
});
},
),
);
}
),
),
SizedBox(height: 20,),
Container(
decoration: BoxDecoration(
border: Border.all(style: BorderStyle.solid),
color: kColorTheme7,
borderRadius: BorderRadius.circular(90),
),
child: FlatButton(
onPressed: (){
widget.route=="homeScreen"?Navigator.push(context, MaterialPageRoute(builder: (context)=>HomeScreen(newMenuName: menuName,imagePath: "images/sticker$selectedIndex.png")))
:Navigator.push(context, MaterialPageRoute(builder: (context)=>MenuExtension(menuExtensionName: menuName)),
);
},
child: Text(widget.buttonText, style: TextStyle(fontSize: 20, color: Colors.white,
fontFamily: "Graduate", fontWeight: FontWeight.bold),),
),
),
],
),
),
),
),
);
}
}
import 'package:flutter/material.dart';
import 'dart:math';
import 'add_menu_screen.dart';
import 'package:bordered_text/bordered_text.dart';
import 'package:lezzet_kitabi/screens/meal_screen.dart';
import 'constants.dart';
List<Widget> menuExtensionCards=[EmptyMenu()];
List<Widget> menuCards=[EmptyMenu()];
class MenuCard extends StatelessWidget {
MenuCard({this.newMenuName, this.imagePath});
final newMenuName;
final imagePath;
#override
Widget build(BuildContext context) {
return Padding(
padding: EdgeInsets.only(top:15.0),
child: FlatButton(
onPressed: (){
Navigator.push(context, MaterialPageRoute(builder: (context)=>MenuExtension(menuExtensionName: newMenuName,)));
},
child: Container(
height: 180,
width: 180,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(30),
color: Color((Random().nextDouble() * 0xFFFFFF).toInt()).withOpacity(0.5),
),
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
SizedBox(height: 10,),
Container(
decoration: BoxDecoration(
color: Colors.white.withOpacity(0.5),
borderRadius: BorderRadius.circular(90),
),
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Text(
newMenuName,
style: TextStyle(
color: Colors.black,
fontSize: 20,
fontFamily: 'Graduate',
fontWeight: FontWeight.bold),
),
),
),
Expanded(
child: Padding(
padding:EdgeInsets.all(5),
child: Image(
image: AssetImage(
imagePath
),
),
),
),
],
),
),
),
);
}
}
class EmptyMenu extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Padding(
padding: EdgeInsets.only(top:15.0),
child: FlatButton(
onPressed: (){
showModalBottomSheet(
context: context,
builder: (BuildContext context)=> AddMenuScreen(buttonText: "Menü Ekle",route:"homeScreen"),
);
},
child: Container(
height: 180,
width: 180,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(30),
color: Colors.black12.withOpacity(0.1),
),
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Icon(Icons.add_circle_outline_outlined,size: 100,color: Colors.grey.shade400,),
],
),
),
),
);
}
}
class MenuExtension extends StatefulWidget {
MenuExtension({this.menuExtensionName});
final String menuExtensionName;
#override
_MenuExtensionState createState() => _MenuExtensionState();
}
class _MenuExtensionState extends State<MenuExtension> {
Widget buildBottomSheet(BuildContext context)=>AddMenuScreen(buttonText: "Tarif Ekle",route: MealScreen,);
#override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
appBar: AppBar(
centerTitle: true,
automaticallyImplyLeading: false,
elevation: 5,
backgroundColor: Color(0xFFF2C3D4).withOpacity(1),
title:BorderedText(
child:Text(
widget.menuExtensionName,
style: TextStyle(
color: Color(0XFFFFFB00),
fontSize: 30,
fontFamily: "Graduate"
),
),
strokeWidth: 5,
strokeColor: Colors.black,
),
actions: [
CircleAvatar(
radius: 27,
backgroundColor: Colors.transparent,
backgroundImage: AssetImage("images/cuttedlogo.PNG"),
),
],
),
body: Container(
decoration: BoxDecoration(
image: DecorationImage(
image: AssetImage("images/logoBGopacity.png"),
fit: BoxFit.cover,
),
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Expanded(
child: GridView.count(
crossAxisCount: 2,
children:menuExtensionCards,
),
),
Column(
mainAxisAlignment: MainAxisAlignment.end,
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Padding(
padding: EdgeInsets.all(10),
child: Container(
decoration: BoxDecoration(
boxShadow:[
BoxShadow(
color: Colors.black.withOpacity(1),
spreadRadius: 2,
blurRadius: 7,
offset: Offset(0,4),
),
],
color: kColorTheme7,
borderRadius: BorderRadius.circular(40),
),
child: FlatButton(
onPressed: (){
showModalBottomSheet(
context: context,
builder: (BuildContext context)=> AddMenuScreen(buttonText: "Tarif Ekle", route:"mealScreen"),
);
},
child: BorderedText(
strokeWidth: 5,
strokeColor: Colors.black,
child:Text("Tarif Ekle",style: TextStyle(
color: Colors.white,
fontFamily:'Graduate',
fontSize:30,
),
),
),
),
),
),
],
)
],
),
),
),
);
}
}
class TitleBorderedText extends StatelessWidget {
TitleBorderedText({this.title, this.textColor});
final Color textColor;
final String title;
#override
Widget build(BuildContext context) {
return BorderedText(
strokeWidth: 5,
strokeColor: Colors.black,
child:Text(title,style: TextStyle(
color: textColor,
fontFamily:'Graduate',
fontSize:30,
),
),
);
}
}

How to reduce the white space beside the drawer icon in Flutter?

In my flutter project, I have set one custom drawer.
Here's code for custom drawer-
class AppDrawer extends StatelessWidget {
#override
Widget build(BuildContext context) {
double defaultScreenWidth = 400.0;
double defaultScreenHeight = 810.0;
ScreenUtil.instance = ScreenUtil(
width: defaultScreenWidth,
height: defaultScreenHeight,
allowFontScaling: true,
)..init(context);
return SizedBox(
width: MediaQuery.of(context).size.width * 0.70,
child: Drawer(
child: Container(
color: Colors.black87,
child: ListView(
padding: EdgeInsets.zero,
children: <Widget>[
SizedBox(height: ScreenUtil.instance.setHeight(30),),
_createDrawerItem(
icon: Icons.keyboard_arrow_right,
text: 'English to Bangla',
onTap: () =>
Navigator.pushReplacementNamed(context, Routes.englishToBangla)),
Padding(
padding: EdgeInsets.only(left:ScreenUtil.instance.setWidth(20), right: ScreenUtil.instance.setWidth(20)),
child: Divider(
height: ScreenUtil.instance.setHeight(10),
color: Colors.grey,
),
),
],
),
),
),
);
}
Widget _createHeader() {
return DrawerHeader(
margin: EdgeInsets.zero,
padding: EdgeInsets.zero,
decoration: BoxDecoration(
image: DecorationImage(
fit: BoxFit.fill,
image: AssetImage('path/to/header_background.png'))),
child: Stack(children: <Widget>[
Positioned(
bottom: 12.0,
left: 16.0,
child: Text("Flutter Step-by-Step",
style: TextStyle(
color: Colors.white,
fontSize: 20.0,
fontWeight: FontWeight.w500))),
]));
}
Widget _createDrawerItem(
{IconData icon, String text, GestureTapCallback onTap}) {
return ListTile(
title: Padding(
padding: EdgeInsets.only(left: ScreenUtil.instance.setWidth(10)),
child: Row(
children: <Widget>[
Container(
decoration: BoxDecoration(
shape: BoxShape.circle,
color: Colors.teal
),
child: Icon(icon, color: Colors.white,)
),
Padding(
padding: EdgeInsets.only(left: ScreenUtil.instance.setWidth(10)),
child: Text(text, style: TextStyle(color: Colors.white, fontWeight: FontWeight.bold, fontSize: ScreenUtil.instance.setSp(14) ),),
)
],
),
),
onTap: onTap,
);
}
}
Here's code for the toolBar which is shown beside the drawer icon-
class SearchAppBar extends StatefulWidget implements PreferredSizeWidget {
final PatternCallback onPatternSelected;
SearchAppBar(this.onPatternSelected, {Key key})
: preferredSize = Size.fromHeight(90),
super(key: key);
#override
final Size preferredSize; // default is 56.0
#override
_SearchAppBarState createState() => _SearchAppBarState();
}
class _SearchAppBarState extends State<SearchAppBar> {
TextEditingController _searchTextController = TextEditingController();
#override
Widget build(BuildContext context) {
double defaultScreenWidth = 400.0;
double defaultScreenHeight = 810.0;
ScreenUtil.instance = ScreenUtil(
width: defaultScreenWidth,
height: defaultScreenHeight,
allowFontScaling: true,
)..init(context);
return Container(
color: Colors.white,
child: Row(
children: <Widget>[
Expanded(
child: Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(3),
),
child: Theme(
data:
Theme.of(context).copyWith(primaryColor: Color(0xFFff9900)),
child: TextFormField(
autofocus: false,
style: TextStyle(fontSize: ScreenUtil.instance.setSp(18)),
keyboardType: TextInputType.text,
controller: _searchTextController,
decoration: InputDecoration(
border: InputBorder.none,
hintText: 'Search for any word you want',
hintStyle:
TextStyle(fontSize: ScreenUtil.instance.setSp(16)),
contentPadding: EdgeInsets.symmetric(
vertical: 14,
horizontal: 10),
),
onChanged: (String value) {
widget.onPatternSelected(value);
},
),
),
),
),
Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(0),
),
child: InkWell(onTap: (){
if(_searchTextController.text.isNotEmpty) {
Navigator.of(context).push(MaterialPageRoute(builder: (context)=>WordDetailScreen(_searchTextController.text.toLowerCase())));
}
},
child: Icon(Icons.search, color: Colors.blue,))),
SizedBox(width: 15)
],
),
);
}
}
And then, in the class where I want to use this drawer, I have called inside Scaffold like below-
drawer: AppDrawer()
But the problem is this causing a white space beside the drawer icon like below image-
And I am having no idea from where this extra padding or margin is happening. So, I need a solution to reduce this extra white space beside the drawer icon.
You can use Transform.translate to move the search bar to the left:
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
leading: Builder(builder: (context) {
return IconButton(
icon: Icon(Icons.menu),
onPressed: () => Scaffold.of(context).openDrawer(),
);
}),
title: Transform.translate(
offset: Offset(-30.0, 0.0),
child: Text('this is the title') // here you can put the search bar
),
),
drawer: Drawer(
),
);
}
Just add a property called "titleSpacing" in your AppBar Tag,
Sample
appBar: AppBar(
titleSpacing: 0, //Add this line to your code
title: Text(widget.title),
leading: Icon(Icons.android),
),

Loop to generate a list of 2 columns with Flutter

I'm a beginner with Flutter and I need to make a loop and generate a widget that contains rows with just 2 columns.
I tried too many different ways to do that but nothing works :/
when I put a loop to my code such as for (var i = 0; i < p1.length-1; i+2) .. nothing shows in the screen and its became all in white.
Here is the code I'm using:
class _MapPageState extends State<MapPage> {
var p1= [
"A0",
"A1",
"A2",
"A3",
];
List<Widget> getWidgets()
{
List<Widget> list = new List<Widget>();
for(var i = 0; i < p1.length-1; i+2){
list.add(new Container(
decoration: BoxDecoration(
color: Colors.green,
borderRadius:BorderRadius.circular(20.0)
),
child: FlatButton(
child: Text(p1[i].toString(),style: TextStyle(color: Colors.white),),
onPressed:()=>print('hii1'),
),
),);
list.add(new Container(
decoration: BoxDecoration(
color: Colors.green,
borderRadius:BorderRadius.circular(20.0)
),
child: FlatButton(
child: Text(p1[i+1].toString(),style: TextStyle(color: Colors.white),),
onPressed:()=>print('hii2'),
),
),);
}
return list;
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
backgroundColor: Colors.transparent,
centerTitle: true,
title: Text("Votre SMARTY PARK"),
),
body:Container(
decoration: BoxDecoration(
image: DecorationImage(
image: NetworkImage('https://images.wallpaperscraft.com/image/parking_cars_underground_131454_240x320.jpg'),
fit: BoxFit.cover,
),),
child: ListView(
scrollDirection: Axis.vertical,
children: <Widget>[
Padding(
padding: const EdgeInsets.only(top: 80),
child: new Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: getWidgets()
),
),
],
),
)
);
}
}
Hope anybody can help cuz i'm trying to that for 3 days..
Thanks
Instead of adding two Container's to list, add a Row containing two Container's to the list.
Also, you should probably change the Row in ListView to Column
Refer to the following code:
(I just copy pasted a few things from your code, there are a lot of changes so go through it carefully. You will have to make changes to make it look neater and have the correct name etc.)
import 'package:flutter/material.dart';
void main() {
runApp(MainApp());
}
class MainApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
backgroundColor: Colors.transparent,
centerTitle: true,
title: Text("Votre SMARTY PARK"),
),
body: MapPage(),
),
);
}
}
class MapPage extends StatefulWidget {
#override
State<StatefulWidget> createState() {
return MapPageState();
}
}
class MapPageState extends State<MapPage> {
var p1 = ["A0", "A1", "A2", "A3"];
List<Widget> widgetlist = List();
MapPageState() {
getWidgets(widgetlist);
}
#override
Widget build(BuildContext context) {
double scwidth = MediaQuery.of(context).size.width;
double scheight = MediaQuery.of(context).size.height;
return Column(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Container(
height: scheight - kToolbarHeight - 24,
decoration: BoxDecoration(
image: DecorationImage(
image: NetworkImage(
'https://images.wallpaperscraft.com/image/parking_cars_underground_131454_240x320.jpg'),
fit: BoxFit.cover,
),
),
child: ListView(
children: widgetlist.map((element) {
return element;
}).toList(),
),
)
],
);
}
void getWidgets(List<Widget> wlist) {
for (int i = 0; i < p1.length-1; i++) {
wlist.add(Row(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Container(
decoration: BoxDecoration(
color: Colors.green, borderRadius: BorderRadius.circular(20.0)),
child: FlatButton(
child: Text(
p1[i].toString(),
style: TextStyle(color: Colors.white),
),
onPressed: () => print('hii1'),
),
),
Container(
decoration: BoxDecoration(
color: Colors.green, borderRadius: BorderRadius.circular(20.0)),
child: FlatButton(
child: Text(
p1[i + 1].toString(),
style: TextStyle(color: Colors.white),
),
onPressed: () => print('hii2'),
),
)
],
));
}
}
}
Output:
Your method should return a list of row.You can use this method
List<Row> getWidgets()
{
List<Row> list = new List<Row>();
for(var i = 0; i < p1.length-1; i+=2){
list.add(Row(
mainAxisAlignment:MainAxisAlignment.spaceAround,
children:[
Container(
decoration: BoxDecoration(
color: Colors.green,
borderRadius:BorderRadius.circular(20.0)
),
child: FlatButton(
child: Text(p1[i].toString(),
style: TextStyle(
color: Colors.white
),
),
onPressed:()=>print('hii1'),
),
),
Container(
decoration: BoxDecoration(
color: Colors.green,
borderRadius:BorderRadius.circular(20.0)
),
child: FlatButton(
child: Text(p1[i+1].toString(),
style: TextStyle(
color: Colors.white
),
),
onPressed:()=>print('hii2'),
),
),
]
);
);
}
return list;
}
Then you can call this from your build() with a ListView.
ListView(
scrollDirection: Axis.vertical,
children:getWidgets()
),

Flutter - Button Group style and position

I am trying to create something like the attached image. I got this far ...
Expanded(
child: Container(
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.only(
topLeft: Radius.circular(32),
topRight: Radius.circular(32),
),
),
child: ButtonTheme(
child: ButtonBar(
alignment: MainAxisAlignment.center,
children: <Widget>[
RaisedButton(
onPressed: () => print('hi'),
child: Text('Referals'),
color: Color(0xff2FBBF0),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.only(
bottomLeft: Radius.circular(15.0),
topLeft: Radius.circular(15.0)),
),
),
RaisedButton(
onPressed: () => print('hii'),
child: Text('Stats'),
color: Color(0xff2FBBF0),
),
RaisedButton(
onPressed: () => print('hiii'),
child: Text('Edit Profile'),
color: Color(0xff2FBBF0),
// color: Colors.white,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.only(
bottomRight: Radius.circular(15.0),
topRight: Radius.circular(15.0)),
),
),
],
),
),
),
),
But I don't really feel like it will look like the image.
I would also like the button group to be at the top of the Container. Now they're in the absolute center. Just like they would be if wrapped in a Center widget.
Here's the complete code. I have just used Container and Row because I find it more suitable and easy to achieve without any headache. :P
If you want with RaisedButton, figure it out.
Source:
import 'package:flutter/material.dart';
class Demo extends StatefulWidget {
#override
_DemoState createState() => new _DemoState();
}
class _DemoState extends State<Demo> {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text("DEMO")),
body: Padding( // used padding just for demo purpose to separate from the appbar and the main content
padding: EdgeInsets.all(10),
child: Container(
alignment: Alignment.topCenter,
child: Container(
height: 60,
padding: EdgeInsets.all(3.5),
width: MediaQuery.of(context).size.width * 0.9,
decoration: BoxDecoration(
color: Colors.blue,
borderRadius: BorderRadius.all(Radius.circular(15)),
),
child: Row(
children: <Widget>[
Expanded(
child: InkWell(
onTap: () {},
child: Container(
alignment: Alignment.center,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.only(
bottomLeft: Radius.circular(12),
topLeft: Radius.circular(12))),
child: Text("Referrals",
style: TextStyle(
color: Colors.blue,
fontSize: 17,
)),
))),
Expanded(
child: InkWell(
onTap: () {},
child: Container(
alignment: Alignment.center,
child: Text("Stats",
style: TextStyle(
color: Colors.white, fontSize: 17)),
))),
Padding(
padding: EdgeInsets.symmetric(vertical: 5),
child: Container(color: Colors.white, width: 2)),
Expanded(
child: InkWell(
onTap: () {},
child: Container(
alignment: Alignment.center,
child: Text("Edit Profile",
style: TextStyle(
color: Colors.white, fontSize: 17)),
)))
],
)),
)));
}
}
Output Screenshot:
Check my ButtonGroup widget that I created
import 'package:flutter/material.dart';
class ButtonGroup extends StatelessWidget {
static const double _radius = 10.0;
static const double _outerPadding = 2.0;
final int current;
final List<String> titles;
final ValueChanged<int> onTab;
final Color color;
final Color secondaryColor;
const ButtonGroup({
Key key,
this.titles,
this.onTab,
int current,
Color color,
Color secondaryColor,
}) : assert(titles != null),
current = current ?? 0,
color = color ?? Colors.blue,
secondaryColor = secondaryColor ?? Colors.white,
super(key: key);
#override
Widget build(BuildContext context) {
return Material(
color: color,
borderRadius: BorderRadius.circular(_radius),
child: Padding(
padding: const EdgeInsets.all(_outerPadding),
child: ClipRRect(
borderRadius: BorderRadius.circular(_radius - _outerPadding),
child: IntrinsicHeight(
child: Row(
mainAxisSize: MainAxisSize.min,
children: _buttonList(),
),
),
),
),
);
}
List<Widget> _buttonList() {
final buttons = <Widget>[];
for (int i = 0; i < titles.length; i++) {
buttons.add(_button(titles[i], i));
buttons.add(
VerticalDivider(
width: 1.0,
color: (i == current || i + 1 == current) ? color : secondaryColor,
thickness: 1.5,
indent: 5.0,
endIndent: 5.0,
),
);
}
buttons.removeLast();
return buttons;
}
Widget _button(String title, int index) {
if (index == this.current)
return _activeButton(title);
else
return _inActiveButton(title, index);
}
Widget _activeButton(String title) => FlatButton(
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
disabledColor: secondaryColor,
disabledTextColor: color,
shape: const RoundedRectangleBorder(
borderRadius: BorderRadius.zero,
),
child: Text(title),
onPressed: null,
);
Widget _inActiveButton(String title, int index) => FlatButton(
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
color: Colors.transparent,
textColor: Colors.white,
shape: const RoundedRectangleBorder(
borderRadius: BorderRadius.zero,
),
child: Text(title),
onPressed: () {
if (onTab != null) onTab(index);
},
);
}
You can use it like this
ButtonGroup(
titles: ["Button1", "Button2", "Button3"],
current: index,
color: Colors.blue,
secondaryColor: Colors.white,
onTab: (selected) {
setState(() {
index = selected;
});
},
)
Example:
import 'package:flutter/material.dart';
import 'package:flutter_app_test2/btn_grp.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
home: MainPage(),
);
}
}
class MainPage extends StatefulWidget {
#override
_MainPageState createState() => _MainPageState();
}
class _MainPageState extends State<MainPage> {
int current = 0;
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: ButtonGroup(
titles: ["Button1", "Button2", "Button3", "Button3"],
current: current,
onTab: (selected) {
print(selected);
setState(() {
current = selected;
});
},
),
),
);
}
}
try adding following in all RaisedButton widgets:
materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
and buttonPadding: EdgeInsets.all(1), in ButtonBar
Source: https://api.flutter.dev/flutter/material/MaterialTapTargetSize-class.html