Search code examples
fluttertabs

Creating a TabBar with completely custom design


I want to achieve a TabBar with Tabs with the following layout:

enter image description here

I found multiple examples where the whole TabBar background is changed but I could not find out how to customize the background for unselected tabs individually, since the grey background is bound to the TabView and not the individual Tab.

In the example image provided, the grey background progress depends on a bool property isAvailable of the data that is used to render the respective Tab/ TabView. The green progress bar indicates which tabs are done. The grey progress bar indicates which tabs are available but not done yet. The last tab is not available yet, therefore it is not included in the grey progress.

Question: How can I achieve a Tab layout/ design like in the image provided? And if not with the Tab/ TabView widget, is there another way?

Thanks for your help!


Solution

  • Tab bar offers only few customizations but this can be achieve using custom code. You can set position and colors of multiple containers to achieve this, like in below example.

    class MyHomePage extends StatelessWidget {
      const MyHomePage({super.key});
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
        appBar: AppBar(
          title: const Text("Title"),
        ),
        body: SizedBox(
          height: 50,
          child: Stack(
            children: [
              Row(
                children: [
                  Expanded(
                    flex: 5,
                    child: Container(
                      decoration: const BoxDecoration(color: Colors.grey),
                    ),
                  ),
                  Expanded(
                    flex: 5,
                    child: Container(
                      decoration: const BoxDecoration(color: Colors.white),
                    ),
                  ),
                ],
              ),
              const Row(
                children: [
                  ColoredContainer(
                    color: Colors.green,
                    radius: 50,
                  ),
                  ColoredContainer(
                    color: Colors.grey,
                    radius: 50,
                  ),
                  ColoredContainer(
                    color: Colors.white,
                    radius: 0,
                  ),
                ],
              )
            ],
          ),
        ),
      );
    } }
    
    class ColoredContainer extends StatelessWidget {
    final Color color;
    final double radius;
    
    const ColoredContainer({
      super.key,
      required this.color,
      required this.radius,
    });
    
    @override
    Widget build(BuildContext context) {
      return Expanded(
        child: Container(
          decoration: BoxDecoration(
            color: color,
            borderRadius: BorderRadius.only(
              topRight: Radius.circular(radius),
              bottomRight: Radius.circular(radius),
            ),
          ),
        ),
      );
    }}
    

    You can set colors, radius and visibility according to your conditions. Hope this helps.