LComingHome
LComingHome

Reputation: 91

Bottomnavigationbar item icon in flutter app

I want to change the icon of an active bottomnavigationbar item, ie if the item is selected the icon is filled and if it’s unselected it shows the outline. enter image description here

Upvotes: 1

Views: 7265

Answers (1)

tudorprodan
tudorprodan

Reputation: 965

Check the code below with explanations:

import 'package:flutter/material.dart';

class MainScreen extends StatefulWidget {

  @override
  _MainScreenState createState() => _MainScreenState();
}

class _MainScreenState extends State<MainScreen>
    with SingleTickerProviderStateMixin {
  // we need this to switch between tabs
  TabController _tabController;
  // here we remember the current tab, by default is the first one (index 0)
  int _currentTabIndex = 0;

  @override
  void initState() {
    super.initState();
    // init the TabController
    _tabController = TabController(vsync: this, length: _Tab.values.length);
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        elevation: 0.0,
        backgroundColor: Colors.white,
        title: Text(_getTitleForCurrentTab(_Tab.values[_currentTabIndex])), // set the title in the AppBar
      ),
      body: TabBarView(
        controller: _tabController, // we set our instantiated TabController as the controller
        children: <Widget>[
          // here we put the screen widgets corresponding to each tab
          // the order must correspond to the order given below in bottomNavigationBar
          Tab1Widget(), // these are your custom widgets for each tab you have
          Tab2Widget(),
          Tab3Widget(),
        ],
      ),
      bottomNavigationBar: BottomNavigationBar(
        type: BottomNavigationBarType.fixed,
        onTap: (int index) {
          // when a tab icon was tapped we just change the current index of the tab with the new one
          // this set state call will re-render the screen and will set new the tab as active
          setState(() {
            _currentTabIndex = index;
          });

          // also we want to change the screen content not just the active tab icon
          // so we use the TabController to go to another tab giving it the index of the tab which was just clicked
          _tabController.animateTo(index);
        },
        // here we render all the icons we want in the BottomNavigationBar
        // we get all the values of the _Tab enum and for each one we render a BottomNavigationBarItem
        items: _Tab.values
            .map((_Tab tab) => BottomNavigationBarItem(
                title: Text(_getTitleForCurrentTab(tab)), // set the title of the tab icon
                icon: Image.asset(
                  _getAssetForTab(tab),
                  width: 24.0,
                  height: 24.0,
                ))) // set the icon of the tab
            .toList(),
      ),
    );
  }

  /// Get the asset icon for the given tab
  String _getAssetForTab(_Tab tab) {
    // check if the given tab parameter is the current active tab
    final active = tab == _Tab.values[_currentTabIndex];

    // now given the tab param get its icon considering the fact that if it is active or not
    if (tab == _Tab.TAB1) {
      return active ? 'assets/tab1_active.png' : 'assets/tab1.png';
    } else if (tab == _Tab.TAB2) {
      return active ? 'assets/tab2_active.png' : 'assets/tab2.png';
    }
    return active ? 'assets/tab3_active.png' : 'assets/tab3.png';
  }

  /// Get the title for the current selected tab
  String _getTitleForCurrentTab(_Tab tab) {
    if (tab == _Tab.TAB1) {
      return 'tab1_title';
    } else if (tab == _Tab.TAB2) {
      return 'tab2_title';
    }
    return 'tab3_title';
  }
}

// Just an enum with all the tabs we want to have
enum _Tab {
  TAB1,
  TAB2,
  TAB3,
}

Upvotes: 8

Related Questions