I have a list of items
List<String> items = [
"All",
"Jobs",
"Messages",
"Customers",
];
int current = 0;
And this list is directly responsible for my tab bar:
When i tap an item in the Tab bar i want to return a different container on each of them?
How do i go about this in flutter?
I tried returning an if statement just before the container but it seems i don't get the statement correctly.
this is the container i want to return if the item user select is All, and then put conditions in place for the rest items. this is how i put the condition but it gives me this error
My return statement and code -
current = 0 ??
Container(
margin: const EdgeInsets.only(top: 30),
height: MediaQuery.of(context).size.height * 1,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const SizedBox(
height: 10,
),
Text(
items[current],
style: GoogleFonts.laila(
fontWeight: FontWeight.w500,
fontSize: 30,
color: Colors.deepPurple),
),
],
),
),
current = 1 ?? Text('hello')
FULL WIDGET ADDED
class NotificationsView extends StatefulWidget {
@override
State<NotificationsView> createState() => _NotificationsViewState();
}
class _NotificationsViewState extends State<NotificationsView> {
final controller = Get.put(NotificationsController());
List<String> items = [
"All",
"Jobs",
"Messages",
"Customers",
];
int current = 0;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(
"Notifications".tr,
style: GoogleFonts.poppins(
color: Color(0xff000000),
fontSize: 16,
fontWeight: FontWeight.w600),
),
centerTitle: false,
backgroundColor: Colors.transparent,
elevation: 0,
automaticallyImplyLeading: false,
leadingWidth: 15,
leading: new IconButton(
icon: new Icon(Icons.arrow_back_ios, color: Color(0xff3498DB)),
onPressed: () => {Get.back()},
),
),
body: RefreshIndicator(
onRefresh: () async {
},
child: ListView(
primary: true,
children: <Widget>[
filter(),
],
),
),
);
}
Widget notificationsList() {
return Obx(() {
if (!controller.notifications.isNotEmpty) {
return CircularLoadingWidget(
height: 300,
onCompleteText: "Notification List is Empty".tr,
);
} else {
var _notifications = controller.notifications;
return ListView.separated(
itemCount: _notifications.length,
separatorBuilder: (context, index) {
return SizedBox(height: 7);
},
shrinkWrap: true,
primary: false,
itemBuilder: (context, index) {
var _notification = controller.notifications.elementAt(index);
if (_notification.data['message_id'] != null) {
return MessageNotificationItemWidget(
notification: _notification);
} else if (_notification.data['booking_id'] != null) {
return BookingNotificationItemWidget(
notification: _notification);
} else {
return NotificationItemWidget(
notification: _notification,
onDismissed: (notification) {
controller.removeNotification(notification);
},
onTap: (notification) async {
await controller.markAsReadNotification(notification);
},
);
}
});
}
});
}
Widget filter() {
return Container(
width: double.infinity,
margin: const EdgeInsets.all(5),
child: Column(
children: [
/// CUSTOM TABBAR
SizedBox(
width: double.infinity,
height: 60,
child: ListView.builder(
physics: const BouncingScrollPhysics(),
itemCount: items.length,
scrollDirection: Axis.horizontal,
itemBuilder: (ctx, index) {
return Column(
children: [
GestureDetector(
onTap: () {
setState(() {
current = index;
});
},
child: AnimatedContainer(
duration: const Duration(milliseconds: 300),
margin: const EdgeInsets.all(5),
decoration: BoxDecoration(
color: current == index
? Color(0xff34495E)
: Color(0xffF5F5F5),
borderRadius: BorderRadius.circular(11),
),
child: Center(
child: Padding(
padding: const EdgeInsets.only(
left: 10.0, right: 10.0, top: 5, bottom: 5),
child: Text(
items[index],
style: GoogleFonts.poppins(
fontSize: 12,
fontWeight: FontWeight.w500,
color: current == index
? Colors.white
: Colors.grey),
),
),
),
),
),
],
);
}),
),
/// MAIN BODY
current = 0 ??
Container(
margin: const EdgeInsets.only(top: 30),
height: MediaQuery.of(context).size.height * 1,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const SizedBox(
height: 10,
),
Text(
items[current],
style: GoogleFonts.laila(
fontWeight: FontWeight.w500,
fontSize: 30,
color: Colors.deepPurple),
),
Padding(
padding: const EdgeInsets.only(
left: 20.0, right: 20.0, top: 20.0, bottom: 20),
child: Column(
children: [
Stack(
children: [
Row(
children: [
Container(
decoration: BoxDecoration(
color: Color(0xffEFFAFF),
borderRadius:
BorderRadius.circular(20)),
child: Padding(
padding: const EdgeInsets.all(10.0),
child: Image.asset(
'assets/icon/suitcase.png'),
),
),
SizedBox(
width: 15,
),
Column(
crossAxisAlignment:
CrossAxisAlignment.start,
children: [
Text(
'New Job started ',
style: GoogleFonts.poppins(
fontSize: 14,
fontWeight: FontWeight.w500,
color: Color(0xff151515)),
),
Text(
'Tailoring for John Cletus ',
style: GoogleFonts.poppins(
fontSize: 10,
fontWeight: FontWeight.w400,
color: Color(0xff151515)),
),
],
),
Spacer(),
Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(2),
color: Color(0xffFFE8E8),
),
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Text(
'Urgent',
style: GoogleFonts.poppins(
color: Color(0xffC95E5E)),
),
),
),
],
),
],
),
Divider(
height: 5,
color: Color(0xffEFFAFF),
),
],
),
),
],
),
),
current = 1 ?? Text('hello')
],
),
);
}
}
CodePudding user response:
You can use Builder
if want to display different type of widget based on the current
index.
Builder(
builder: (context) {
switch (current) {
case 0:
return Container(
margin: const EdgeInsets.only(top: 30),
height: MediaQuery.of(context).size.height * 1,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const SizedBox(
height: 10,
),
Text(
items[current],
style: GoogleFonts.laila(
fontWeight: FontWeight.w500,
fontSize: 30,
color: Colors.deepPurple),
),
],
),
);
case 1:
return Text('Hello');
default:
return SizedBox.shrink();
}
},
);
CodePudding user response:
Below approach will solve your problem. If you need further assistance, please feel free to comment.
int _currentIndex = 0;
var _containers = <Widget>[
AllContainer(),
JobsContainer(),
MessagesContainer(),
CustomerContainer(),
];
Widget _bottomTab() {
return BottomNavigationBar(
currentIndex: _currentIndex,
onTap: _onItemTapped, //
type: BottomNavigationBarType.fixed,
selectedLabelStyle: const TextStyle(color: Colors.blue),
selectedItemColor: WAPrimaryColor,
unselectedLabelStyle: const TextStyle(color: Colors.blue),
unselectedItemColor: Colors.grey,
items: const <BottomNavigationBarItem>[
BottomNavigationBarItem(label: 'All'),
BottomNavigationBarItem(
label: 'Jobs'),
BottomNavigationBarItem(
label: 'Messages'),
BottomNavigationBarItem( label: 'Customer'),
],
);
}
void _onItemTapped(int index) async {
print('bottom index::: $index');
setState(() {
_currentIndex = index;
});
}
@override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
bottomNavigationBar: _bottomTab(),
body: Center(child: _containers.elementAt(_currentIndex)),
),
);
}
CodePudding user response:
You can use conditional if on widget level,
like
/// MAIN BODY
if (current == 0)
Container(
margin: const EdgeInsets.only(top: 30),
height: MediaQuery.of(context).size.height * 1,
...
),
if (current == 1) Text('hello')
Also can be use else if
if (current == 0)
Container(
margin: const EdgeInsets.only(top: 30),
height: MediaQuery.of(context).size.height * 1,
) //you shouldnt put coma
else if (current == 1) Text('hello')
],
),
);
But creating a separate method will be better instead of putting it here
Widget getWidget(int index) {
/// MAIN BODY
if (current == 0) // or switch case
return Container(
margin: const EdgeInsets.only(top: 30),
height: MediaQuery.of(context).size.height * 1,
); //you shouldnt put coma
else if (current == 1) return Text('hello');
return Text("default");
}
And call the method getWidget(current)
.
Also there are some widget like PageView
, IndexedStack
will help to organize the code structure