2

I'm trying to find a way to add an AppBar only once without having to duplicate the AppBar code on different routes. I have tried different approaches but I still cant get the results that I want.

This is the main.dart file.

import 'package:flutter/material.dart';
import 'package:com.example.simple_app/pages/page_one.dart';
import 'package:com.example.simple_app/pages/page_one.dart';

void main() => runApp(SimpleApp());

final routes = {
  '/': (BuildContext context) => new PageOne(),
  '/pageone': (BuildContext context) => new PageOne(),
  '/pagetwo': (BuildContext context) => new PageTwo(),
};

class SimpleApp extends StatefulWidget {
  @override
  _SimpleAppState createState() => _SimpleAppState();
}

class _SimpleApp extends State<SimpleApp> {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Simple App',
      theme: ThemeData(
        // This is the theme of your application.
        //
        // Try running your application with "flutter run". You'll see the
        // application has a blue toolbar. Then, without quitting the app, try
        // changing the primarySwatch below to Colors.green and then invoke
        // "hot reload" (press "r" in the console where you ran "flutter run",
        // or simply save your changes to "hot reload" in a Flutter IDE).
        // Notice that the counter didn't reset back to zero; the application
        // is not restarted.
        primarySwatch: Colors.blueGrey,
      ),
      initialRoute: '/',
      routes: routes,
    );
  }
}

Below is PageOne.dart file where I've hardcoded AppBar code.

import 'package:flutter/material.dart';

class PageOne extends StatefulWidget {
  PageOne({Key key}) : super(key: key);

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

class _PageOneState extends State<PageOne> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Simple AppBar'),
      ),
    );
  }
}

Below is PageTwo.dart file where I've also put AppBar by writing the whole code, I'm duplicating AppBar code which is not cool.

import 'package:flutter/material.dart';

class PageOne extends StatefulWidget {
  PageOne({Key key}) : super(key: key);

  @override
  _PageTwoState createState() => _PageOneState();
}

class _PageTwoState extends State<PageOne> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Simple AppBar'),
      ),
    );
  }
}

I'm new to flutter but I hope you understand what I'm saying.

What I want is to be able to use AppBar in different routes without duplicating the code. For example when we go to web development, A website built in php you can simply include views. I want something similar here or better, Thank you.

James Mwase
  • 828
  • 1
  • 16
  • 29
  • Did you check this link? https://stackoverflow.com/questions/51659805/persisting-appbar-drawer-across-all-pages-flutter/51661319 – Ajay Kulkarni Dec 30 '19 at 09:16
  • I tried that approach before, and I have just tried it now just to be sure. I'm still getting nothing. The IDE is showing this `The argument type 'TopAppBar' can't be assigned to the parameter type 'PreferredSizeWidget'.dart(argument_type_not_assignable)` – James Mwase Dec 30 '19 at 09:24

3 Answers3

1

You can create a separate App bar Widget for achieving this Like :

Create an appbar.dart file as :

import 'package:flutter/material.dart';

Widget appbar(BuildContext context, String title, dynamic otherData) {
  return AppBar(
    title: Text(title),

    //Other data you want to show

  );
}

And import the appear. dart file wherever you want to display an App bar.

Screen1:

import 'appbar.dart';
import 'package:flutter/material.dart';

class Page1 extends StatefulWidget {
  @override
  _Page1State createState() => _Page1State();
}

class _Page1State extends State<Page1> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
        appBar: appbar(context, 'Chat App', {'icons' : Icons.menu}),
    );
  }
}

Screen2:

import 'appbar.dart';
import 'package:flutter/material.dart';

class Page12 extends StatefulWidget {
  @override
  _Page12State createState() => _Page12State();
}

class _Page12State extends State<Page12> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
        appBar: appbar(context, 'Chat App', {'icons' : Icons.menu}),
    );
  }
}

There are a lot more ways to achieve this. This is the simple one I tried.

Anil Chauhan
  • 658
  • 6
  • 17
1

Use builder property in MaterialApp to build common container for every page

import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: Theme.of(context).copyWith(highlightColor: Colors.amber),
      //TODO: Use `builder` to add top most container for all page
      builder: (context, child) {
        return Scaffold(
          appBar: AppBar(
            title: Text("Simple AppBar"),
          ),
          body: child, //this child is dynamically replaced with corresponding page when we navigate
        );
      },
      home: FirstPage(),
      debugShowCheckedModeBanner: false,
    );
  }
}

class FirstPage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Column(
      mainAxisAlignment: MainAxisAlignment.center,
      children: <Widget>[
        Text("This is First Page"),
        RaisedButton(
          child: Text("Goto Second Page"),
          onPressed: () {
            Navigator.push(
              context,
              MaterialPageRoute(
                builder: (context) => SecondPage(),
              ),
            );
          },
        ),
      ],
    );
  }
}

class SecondPage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Column(
      mainAxisAlignment: MainAxisAlignment.center,
      children: <Widget>[
        Text("This is First Page"),
        RaisedButton(
          child: Text("Go Back"),
          onPressed: () {
            Navigator.pop(context);
          },
        ),
      ],
    );
  }
}
Crazy Lazy Cat
  • 13,595
  • 4
  • 30
  • 54
0

First, create a file for example appBar.dart then place your personal appBar there like this:

 import 'package:flutter/material.dart';

final appBar = AppBar(
 backgroundColor: Colors.orange,
 elevation: 5.0,
 title: Center(
 child: SizedBox(
   height: 40.0,
   child:Image.asset("assets/images/myLogo.png"),
  ),
),
 );

now import and use the appBar anywhere you want.

import 'package:myApp/pages/appBar.dart';

return Scaffold(
    appBar: appBar,
    body:......
Md.shah
  • 48
  • 1
  • 8