BorderSide Color to BottomNavigationBar? - flutter

I want to add a colored BorderSide to the top of my BottomNavigationBar.
I can achieve it using a Custom BottomAppBar, but it is not convenient for my design as it misplaces my floatingActionButtonLocation.centerDocked, so I need to stick with BottomNavigationBar.
Any help to find a workaround is appreciated.
import 'package:flutter/material.dart';
class BottomNavTest extends StatefulWidget {
#override
_BottomNavTestState createState() => _BottomNavTestState();
}
class _BottomNavTestState extends State<BottomNavTest> {
#override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Colors.grey,
bottomNavigationBar: BottomNavigationBar(
type: BottomNavigationBarType.fixed,
backgroundColor: Colors.grey,
selectedItemColor: Colors.white,
unselectedItemColor: Colors.black, //
currentIndex: 0,
onTap: (index) {
switch (index) {
case 0:
break;
case 1:
break;
}
},
items: [
BottomNavigationBarItem(
icon: Icon(Icons.thumb_up),
title: Text('good'),
),
BottomNavigationBarItem(
icon: Icon(Icons.thumb_down),
title: Text('bad'),
),
],
),
);
}
}
Current output:
My goal:

Add it inside the container and give border
Scaffold(
backgroundColor: Colors.grey,
bottomNavigationBar: Container(
decoration: BoxDecoration(
border: Border.all(color: Colors.white, width: 2)
),
child: BottomNavigationBar(
type: BottomNavigationBarType.fixed,
backgroundColor: Colors.grey,
selectedItemColor: Colors.white,
unselectedItemColor: Colors.black,
currentIndex: 0,
onTap: (index) {
switch (index) {
case 0:
break;
case 1:
break;
}
},
items: [
BottomNavigationBarItem(
icon: Icon(Icons.thumb_up),
title: Text('good'),
),
BottomNavigationBarItem(
icon: Icon(Icons.thumb_down),
title: Text('bad'),
),
],
),
),
);
Output:

You can make BottomNavigationBar as a child to the Container..
And add topBorder to Container like this..
decoration: BoxDecoration( border: Border( top: BorderSide( color: Colors.blue, // width: 3.0 --> you can set a custom width too! ), ), ),
hope it solves your issue

Related

In meterial 3, the background color of the BottomAppBar does not change. Pink shades appear in the background of the BottomAppBar

I Upgrade flutter 3.3.10 to 3.7.3.In material 3, the background colour of the BottomAppBar does not change.Pink shades appear in the background of the BottomAppBar .enter image description here.and BottomAppBar and BottomNavigationBar do not merge, they act separately
import 'package:bottom_navbar/constants/app_assets.dart';
import 'package:bottom_navbar/constants/app_colors.dart';
import 'package:bottom_navbar/constants/app_labels.dart';
import 'package:bottom_navbar/constants/app_styles.dart';
import 'package:bottom_navbar/size_config.dart';
import 'package:flutter/material.dart';
class MainScreen extends StatefulWidget {
const MainScreen({super.key});
#override
State<MainScreen> createState() => _MainScreenState();
}
class _MainScreenState extends State<MainScreen> {
#override
Widget build(BuildContext context) {
int ci = 0;
return Scaffold(
backgroundColor: Colors.white,
floatingActionButtonLocation: FloatingActionButtonLocation.centerDocked,
floatingActionButton: FloatingActionButton(
heroTag: AppLabels.addOrEditHero,
shape:
RoundedRectangleBorder(borderRadius: BorderRadius.circular(30.0)),
onPressed: () {},
backgroundColor: AppColors.colorWhite,
child: Container(
decoration: BoxDecoration(
shape: BoxShape.circle,
border: Border.all(width: 3, color: AppColors.colorWhite)),
child: Image.asset(
AppAssets.add,
fit: BoxFit.cover,
),
)),
bottomNavigationBar: BottomAppBar(
color: Colors.white,
surfaceTintColor: Colors.white,
shape: const CircularNotchedRectangle(),
notchMargin: 8,
clipBehavior: Clip.antiAlias,
child: SizedBox(
height: 8 * SizeConfig.textMultiplier!,
child: BottomNavigationBar(
backgroundColor: Colors.white,
elevation: 0,
selectedFontSize: 1.4 * SizeConfig.textMultiplier!,
selectedItemColor: AppColors.primary,
selectedIconTheme: const IconThemeData(color: AppColors.primary),
currentIndex: ci,
unselectedLabelStyle: AppStyles.bottomNavButtonStyle,
selectedLabelStyle: AppStyles.bottomNavButtonStyle,
unselectedItemColor: AppColors.menuButton,
onTap: (i) {
setState(() {
ci = i;
});
},
showUnselectedLabels: false,
type: BottomNavigationBarType.fixed,
items: const [
BottomNavigationBarItem(icon: Icon(Icons.home), label: 'Home'),
BottomNavigationBarItem(
icon: Icon(Icons.local_activity), label: 'Activity'),
BottomNavigationBarItem(
icon: Icon(Icons.notifications), label: 'Notifications'),
BottomNavigationBarItem(
icon: Icon(Icons.shopping_bag), label: 'Cart'),
],
),
),
),
body: const Center(child: Text('Main Screen')),
);
}
}
Don't know why this happening, but you can fix this issue by setting canvas color in MaterialApp's ThemeData like this,
MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
useMaterial3: true,
canvasColor: Colors.white,///here
),
),
There must be some issue with colorScheme in ThemeData
You can also use this,
ThemeData(
useMaterial3: true,
// canvasColor: Colors.white,
colorScheme: ColorScheme.highContrastLight(),
),

navigation bar issue after clicking on card flutter

[![When I click on any card the navigation bar doesn't work anymore ][2]][2]
the 1st image shows my navigation bar which works very well. The moment I click on a card the navigation bar doesn't work anymore and I didn't find out what is the reason
**This is my navigation bar Widget code that I'm using after clicking on the card **
class MenuBarWidget extends StatefulWidget {
#override
_State createState() => _State();
}
class _State extends State<MenuBarWidget> {
int _index = 0;
#override
Widget build(BuildContext context) {
return Container(
height: 70,
decoration: BoxDecoration(
gradient: AppGradients.linear,
),
child: BottomNavigationBar(
onTap: (newIndex) => setState(() => _index = newIndex),
currentIndex: _index,
unselectedItemColor: Colors.white70,
selectedItemColor: Colors.white,
elevation: 0,
items: const <BottomNavigationBarItem>[
BottomNavigationBarItem(
icon: Icon(Icons.home_outlined),
label: 'Principal',
backgroundColor: Colors.transparent,
),
BottomNavigationBarItem(
icon: Icon(Icons.assignment_outlined),
label: 'Pedidos',
backgroundColor: Colors.transparent,
),
BottomNavigationBarItem(
icon: Icon(Icons.chat_outlined),
label: 'Chat',
backgroundColor: Colors.transparent,
),
BottomNavigationBarItem(
icon: Icon(Icons.person_outline),
label: 'Perfil',
backgroundColor: Colors.transparent,
),
],
),
);
}
}
this is my code after clicking on the card
#override
Widget build(BuildContext context) {
return Scaffold(
bottomNavigationBar: MenuBarWidget(),
appBar: PreferredSize(
preferredSize: Size.fromHeight(100),
child: Stack(children: [
Container(
height: 128,
decoration: BoxDecoration(
color: AppColors.green,
border: Border(
bottom: BorderSide(
color: AppColors.blueButton,
width: 2,
),
),
image: DecorationImage(
image: AssetImage(AppImages.dots),
fit: BoxFit.cover,
),
),
),
Align(
alignment: Alignment(-0.7, -0.3),
child: RichText(
text: TextSpan(
text: serviceName,
style: TextStyle(
color: AppColors.white,
fontSize: 25,
fontWeight: FontWeight.bold,
),
),
),
),
Align(
alignment: Alignment(-0.6, 0.4),
child: RichText(
text: TextSpan(
text: 'Confira abaixo todos os profissionais desta categoria',
style: TextStyle(
color: AppColors.white,
fontSize: 9,
fontWeight: FontWeight.bold,
),
),
),
),
]),
),
**Any help is appreciated thanks **
create a new list of screens and add the screens you created as the list items
List screens = [
HomeScreen();
CarpentryScreen();
...
...
];
then make the body of your MenuBarWidget() return screens[_index]
class MenuBarWidget extends StatefulWidget {
#override
_State createState() => _State();
}
class _State extends State<MenuBarWidget> {
int _index = 0;
// new list of your screens
List<Widget> screens = [
PrincipalScreen(),
PedidosScreen(),
Chatscreen(),
Perfilscreen(),
];
#override
Widget build(BuildContext context) {
// return the screens
return Scaffold(
body: screens[_index],
bottomNavigationBar: BottomNavigationBar(
onTap: (newIndex) => setState(() => _index = newIndex),
currentIndex: _index,
unselectedItemColor: Colors.white70,
selectedItemColor: Colors.white,
elevation: 0,
items: const <BottomNavigationBarItem>[
BottomNavigationBarItem(
icon: Icon(Icons.home_outlined),
label: 'Principal',
backgroundColor: Colors.transparent,
),
BottomNavigationBarItem(
icon: Icon(Icons.assignment_outlined),
label: 'Pedidos',
backgroundColor: Colors.transparent,
),
BottomNavigationBarItem(
icon: Icon(Icons.chat_outlined),
label: 'Chat',
backgroundColor: Colors.transparent,
),
BottomNavigationBarItem(
icon: Icon(Icons.person_outline),
label: 'Perfil',
backgroundColor: Colors.transparent,
),
],
),
);
}
}
then you don't have to add bottomNavigationBar to the screens individually, this way, the screen is persistent across all screens

Where is the black behind my navigation bar coming from?

After rounding the corners of my navigation bar I noticed there's still something there. When I set the scaffolds background color to transparent, what's behind my navigation bar is black.. if I change it to blue, it's blue.. So is it the scaffold? How do I get it to show my home page behind it? I'm new at this...
class Navigation extends StatefulWidget {
#override
_NavigationState createState() => _NavigationState();
}
class _NavigationState extends State<Navigation> {
int _selectedIndex = 0;
List<Widget> _widgetOptions = <Widget>[
Home(),
Options(),
Menu(),
Search (),
Text ('Profile')
];
void _onItemTap(int index) {
setState(() {
_selectedIndex = index;
});
}
#override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Colors.transparent,
body: Stack (
children: [_widgetOptions.elementAt(_selectedIndex)],
),
bottomNavigationBar: Container(
margin: EdgeInsets.zero,
decoration: BoxDecoration(
color: Color (0xFF213359),
borderRadius: BorderRadius.only(
topLeft: Radius.circular(30.0),
topRight: Radius.circular(30.0),),),
child: Theme(
data: ThemeData(
splashColor: Colors.transparent,
highlightColor: Colors.transparent,),
child: BottomNavigationBar(
backgroundColor: Colors.transparent,
showUnselectedLabels: false,
showSelectedLabels: false,
type: BottomNavigationBarType.fixed,
elevation: 0,
items: const <BottomNavigationBarItem>[
BottomNavigationBarItem(
icon: Icon(MyFlutterAppHouse.sketch_house,
size: 27.5,), label: (''),),
BottomNavigationBarItem(
icon: Icon(MyFlutterAppOptionsLong.sketch_options_long,
size: 35), label: (''),),
BottomNavigationBarItem(
icon: Icon((MyFlutterAppBook.sketch_book),
size: 34, ), label: (''),),
BottomNavigationBarItem(
icon: Icon(MyFlutterAppSearch.sketch_search,
size: 34), label: (''),),
BottomNavigationBarItem(
icon: Icon(MyFlutterAppPerson.sketch_person,
size: 30.5), label: (''),),
],
currentIndex: _selectedIndex,
onTap: _onItemTap,
unselectedItemColor: Colors.grey[600],
selectedItemColor: Colors.white,
),
),
),
);
}
}
yes it is the scaffold once its transparent you see the material app which is black ,
one you put color back it appears , it is that simple.
and if you want to see your home page from the radius gap you can add extendBody property to your scaffold
extendBody: true,

Flutter add a black outline to top of BottomNavigationBar

I am trying to figure out how to add a very subtle black line to the top of a BottomNavigationBar to make it's start more distinct from the rest of the content. AirBnb would be a good example of this.
Is there a way to achieve this with Flutter?
Below is the widget I am currently using to render the BottomNavigationBar and I have attached a sample below where there is a distinct grey line at the top of the navbar for AirBnb.
#override
Widget build(BuildContext context) {
return Scaffold(
body: currentPage,
bottomNavigationBar: PreferredSize(
preferredSize: Size.fromHeight(50),
child: Container (
decoration: BoxDecoration(
border: Border.all(color: Colors.black)
),
)
),
);
}
The parent of this Widget:
void main() => runApp(MaterialApp(
home: new MyApp(),
debugShowCheckedModeBanner: true,
));
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Navbar();
}
}
How to add line on top of bottom navigation view in flutter ?
Code
class BottomNavigationBarHandler {
Widget bar(int currentIndex) {
return Container(
decoration: BoxDecoration(
color: Colors.white,
border: Border(top: BorderSide(color: Colors.white, width: 3.0))),
child: BottomNavigationBar(
backgroundColor: Colors.black,
selectedItemColor: Colors.pinkAccent,
unselectedItemColor: Colors.white,
showSelectedLabels: false,
showUnselectedLabels: false,
onTap: onTabTapped,
currentIndex: currentIndex,
items: [
BottomNavigationBarItem(
icon: Icon(Icons.home_outlined),
title: Text('Home')),
BottomNavigationBarItem(
icon: Icon(Icons.search),
title: Text('Messages')),
BottomNavigationBarItem(
icon: Icon(Icons.add),
title: Text('Profile'))]));
}
void onTabTapped(int index) {
print('BottomNavigationBarIndex ::' + index.toString());
}
}
Output
Widget build(BuildContext context) {
return Scaffold(
appBar: PreferredSize(
preferredSize: Size.fromHeight(200),
child: Container(
alignment: Alignment.center,
color: globals.white,
height: 100,
child: Text('imyadunandan'),
),
),
body: Container(
color: globals.white,
),
bottomNavigationBar: Container(
decoration: BoxDecoration(
color: globals.white,
boxShadow: [
BoxShadow(
color: globals.black,
),
],
),
child: BottomNavigationBar(
items: [
BottomNavigationBarItem(
icon: Icon(Icons.android),
title: Text('Android'),
),
BottomNavigationBarItem(
icon: Icon(Icons.desktop_windows),
title: Text('Windows'),
),
],
backgroundColor: globals.white,
elevation: 0,
),
),
);
}
this code achieves the fallowing

How to set border radius to bottom app bar in a flutter app?

I want to set the borderRadius to an Bottom Navigation App Bar as its shown in the image. I have tried to put Bottom Navigation App Bar to a ClipRRect borderRadius and in a Container decoration but it didn't worked. So how can I apply the topLeft, and topRight border radius to my bottom navigation bar. Kindly help to let me know how can I do it?
main.dart
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Food Ordering',
theme: ThemeData(primarySwatch: Colors.blue, primaryColor: Colors.white),
home: MyStatefulWidget(),
routes: <String, WidgetBuilder>{
'/detail-page': (BuildContext context) => MyDetailPage(),
},
);
}
}
class MyStatefulWidget extends StatefulWidget {
MyStatefulWidget({Key key}) : super(key: key);
#override
_MyStatefulWidgetState createState() => _MyStatefulWidgetState();
}
class _MyStatefulWidgetState extends State<MyStatefulWidget> {
int _selectedIndex = 0;
static const TextStyle optionStyle =
TextStyle(fontSize: 30, fontWeight: FontWeight.bold);
static List<Widget> _widgetOptions = <Widget>[
HomePage(),
HomePage(),
HomePage(),
HomePage(),
];
void _onItemTapped(int index) {
setState(() {
_selectedIndex = index;
});
}
#override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
child: _widgetOptions.elementAt(_selectedIndex),
),
bottomNavigationBar: BottomNavigationBar(
items: <BottomNavigationBarItem>[
BottomNavigationBarItem(
icon: Image.asset('assets/icon-home.png'),
title: Text('Home'),
),
BottomNavigationBarItem(
icon: Image.asset('assets/icon-mentors.png'),
title: Text('Mentors'),
),
BottomNavigationBarItem(
icon: Image.asset('assets/icon-messages.png'),
title: Text('Messages'),
),
BottomNavigationBarItem(
icon: Image.asset('assets/icon-settings.png'),
title: Text('Settings'),
),
],
currentIndex: _selectedIndex,
selectedItemColor: Colors.blue,
onTap: _onItemTapped),
);
}
}
EDIT
Scaffold now has a property called extendBody which can be used to extend the body below a bottomBar. From the documentation,
If true, and bottomNavigationBar or persistentFooterButtons is specified, then the body extends to the bottom of the Scaffold, instead of only extending to the top of the bottomNavigationBar or the persistentFooterButtons.
This means that all you need to do is
class HomePage extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Some Text'),
),
body: bodyContent,
extendBody: true,
bottomNavigationBar: bottomNavigationBar,
);
}
Widget get bodyContent {
return Container(color: Colors.red);
}
Widget get bottomNavigationBar {
return ClipRRect(
borderRadius: const BorderRadius.only(
topRight: Radius.circular(40),
topLeft: Radius.circular(40),
),
child: BottomNavigationBar(
items: const [
BottomNavigationBarItem(icon: Icon(Icons.home), label: '1'),
BottomNavigationBarItem(icon: Icon(Icons.usb), label: '2'),
BottomNavigationBarItem(
icon: Icon(Icons.assignment_ind), label: '3'),
BottomNavigationBarItem(
icon: Icon(Icons.multiline_chart), label: '4'),
],
unselectedItemColor: Colors.grey,
selectedItemColor: Colors.black,
showUnselectedLabels: true,
),
);
}
}
OUTDATED
Put it inside a stack. Don't add the Bottom Navigation Bar to the scaffold directly.
class HomePage extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Some Text'),
),
body: Stack(
children: <Widget>[
bodyContent,
Positioned(
left: 0,
right: 0,
bottom: 0,
child: bottomNavigationBar,
),
],
),
);
}
Widget get bodyContent {
return Container(color: Colors.red);
}
Widget get bottomNavigationBar {
return ClipRRect(
borderRadius: BorderRadius.only(
topRight: Radius.circular(40),
topLeft: Radius.circular(40),
),
child: BottomNavigationBar(
items: [
BottomNavigationBarItem(icon: Icon(Icons.home), title: Text('1')),
BottomNavigationBarItem(icon: Icon(Icons.usb), title: Text('2')),
BottomNavigationBarItem(
icon: Icon(Icons.assignment_ind), title: Text('3')),
BottomNavigationBarItem(
icon: Icon(Icons.multiline_chart), title: Text('4')),
],
unselectedItemColor: Colors.grey,
selectedItemColor: Colors.black,
showUnselectedLabels: true,
),
);
}
}
Alternatively, if your goal is to only put a borderRadius you can just use ClipRRect and apply your desired borderRadius to it.
Here is my implementation of the solution:
ClipRRect _getBtmNavBar() {
return ClipRRect(
borderRadius: BorderRadius.only(
topLeft: Radius.circular(25),
topRight: Radius.circular(25),
),
child: BottomNavigationBar(
currentIndex: _selectedIndex,
onTap: _onTabTapped,
selectedLabelStyle: TextStyle(
color: Colors.black87,
fontSize: 16,
),
iconSize: 35,
selectedItemColor: Colors.white,
unselectedItemColor: Colors.black54,
items: <BottomNavigationBarItem>[
BottomNavigationBarItem(
backgroundColor: kBottomNavBarBgColor,
icon: Icon(Icons.home),
title: Text('Home'),
),
// more BottomNavigationBarItem() goes here.
Then plug it directly into your bottomNavigationBar
Code Example:
return Scaffold(
// more Scaffold code goes here
//bottom navigationBar
bottomNavigationBar: _getBtmNavBar(),
);
You may user bellow like .
My bottomNavigationBar image is look like
2. here is thecode
import 'package:flutter/material.dart';
class BottomTab extends StatefulWidget {
#override
State<StatefulWidget> createState() {
return _BottomTab();
}
}
class _BottomTab extends State<BottomTab> {
int _selectedTabIndex = 0;
List _pages = [
Text("Home"),
Text("Order"),
Text("Notfication"),
Text("More"),
];
_changeIndex(int index) {
setState(() {
_selectedTabIndex = index;
print("index..." + index.toString());
});
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('bottom nav bar'),
),
body: Center(child: _pages[_selectedTabIndex]),
bottomNavigationBar: bottomNavigationBar,
);
}
Widget get bottomNavigationBar {
return Container(
decoration: BoxDecoration(
borderRadius: BorderRadius.only(
topRight: Radius.circular(30), topLeft: Radius.circular(30)),
boxShadow: [
BoxShadow(color: Colors.black38, spreadRadius: 0, blurRadius: 10),
],
),
child: ClipRRect(
borderRadius: BorderRadius.only(
topLeft: Radius.circular(30.0),
topRight: Radius.circular(30.0),
),
child: BottomNavigationBar(
currentIndex: _selectedTabIndex,
onTap: _changeIndex,
type: BottomNavigationBarType.fixed,
selectedFontSize: 12,
unselectedFontSize: 12,
selectedItemColor: Colors.amber[800],
unselectedItemColor: Colors.grey[500],
showUnselectedLabels: true,
items: <BottomNavigationBarItem>[
BottomNavigationBarItem(
icon: new Icon(Icons.home),
title: new Text('Home'),
),
BottomNavigationBarItem(
icon: new Icon(Icons.shopping_cart_outlined),
title: new Text('Order'),
),
BottomNavigationBarItem(
icon: new Icon(Icons.mail),
title: new Text('Messages'),
),
BottomNavigationBarItem(
icon: Icon(Icons.more_horiz_rounded), title: Text('More')),
],
),
));
}
}
Just include the BottomNavigationBar inside the body, inside a circular border container. Like this (See the picture attached!)
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
body: Container(
decoration: BoxDecoration(
image: DecorationImage(
image: new AssetImage("assets/images/background.jpg"),
fit: BoxFit.cover)),
child: Stack(
alignment: Alignment.bottomCenter,
children: <Widget>[
Expanded(
child: Column(
children: <Widget>[
Expanded(child: _children[_currentIndex]),
],
),
),
Container(
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.only(
topLeft: Radius.circular(20),
topRight: Radius.circular(20),
bottomLeft: Radius.circular(0),
bottomRight: Radius.circular(0)),
boxShadow: [
BoxShadow(
offset: Offset(0.0, 1.00), //(x,y)
blurRadius: 4.00,
color: Colors.grey,
spreadRadius: 1.00),
],
),
height: 70,
child: ClipRRect(
clipBehavior: Clip.hardEdge,
borderRadius: BorderRadius.only(
topLeft: Radius.circular(25),
topRight: Radius.circular(25),
bottomLeft: Radius.circular(0),
bottomRight: Radius.circular(0)),
child: Container(
child: BottomNavigationBar(
backgroundColor: Color.fromRGBO(255, 255, 255, 50),
showSelectedLabels: false,
showUnselectedLabels: false,
onTap: onTabTapped,
// new
currentIndex: _currentIndex,
// new
items: [
new BottomNavigationBarItem(
icon: Icon(
Icons.phone,
size: 30,
),
title: Text('Calls'),
),
new BottomNavigationBarItem(
icon: Icon(
Icons.mail,
size: 30,
),
title: Text('Messages'),
),
new BottomNavigationBarItem(
icon: Icon(
Icons.person,
size: 30,
),
title: Text('Profile'))
],
),
)),
)
],
)),
));
}