blackpool
blackpool

Reputation: 505

How to keep AppBar and back arrow stationary when navigating to a new screen

I want to have the top half of by screen appear static when navigating between pages in Flutter.

To try to make this happen I put use the Hero widget and use it on a column that contains an AppBar and some other content that I want to appear static when pushing a new page.

The App Bar itself remains static but the back arrow disappears when the animation starts and reappears when the animation is done.

How can I have the back arrow remain visible the entire time while the rest of the page is animating into place?

 class FirstScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Column(
        children: [
          Hero(
            tag: 'top',
            child: Column(
              children: <Widget>[
                AppBar(
                  title: Text('First'),
                  backgroundColor: Color.fromARGB(255, 50, 64, 182),
                ),
                Container(
                  height: 80.0,
                )
              ],
            ),
          ),
          RaisedButton(
            child: Text('Next'),
            onPressed: () {
              Navigator.pushNamed(context, '/second');
            },
          ),
        ],
      ),
    );
  }
}

class SecondScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Column(
        children: [
          Hero(
            tag: 'top',
            child: Column(
              children: <Widget>[
                AppBar(
                  title: Text('Second'),
                ),
                Container(
                  height: 80.0,
                  // color: Colors.green,
                ),
              ],
            ),
          ),
          RaisedButton(
            child: Text('Back'),
            onPressed: () {
              Navigator.pop(context);
            },
          ),
        ],
      ),
    );
  }
}

Upvotes: 5

Views: 5784

Answers (3)

Margriet
Margriet

Reputation: 197

I have it done this way, by adding automaticallyImplyLeading: true,

Hope this solves your problem!

  appBar: AppBar(
    automaticallyImplyLeading: true,
    ),

Upvotes: 0

leodriesch
leodriesch

Reputation: 5780

You could do automaticallyImplyLeading: false and then do

leading: IconButton(
        icon: Icon(Icons.arrow_back),
        onPressed: () => Navigator.of(context).pop(),
),

Upvotes: 0

soupjake
soupjake

Reputation: 3449

Things weren't quite set up right in your code. It should go Scaffold/Hero/your content. I've also used this simple fading page route when performing the navigation:

class HomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
          title: Text('First'),
          leading: Icon(null),
          backgroundColor: Color.fromARGB(255, 50, 64, 182)),
      body: Hero(
        tag: 'top',
        child: Column(
          children: <Widget>[
            Container(height: 80.0),
            RaisedButton(
              child: Text('Next'),
              onPressed: () {
                Navigator.push(context, MyCustomRoute(builder: (context) {
                  return SecondScreen();
                }));
              },
            ),
          ],
        ),
      ),
    );
  }
}

class SecondScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
          title: Text('Second'),
          leading: IconButton(icon: Icon(Icons.arrow_back), onPressed: () {
            Navigator.pop(context);
          },),
          backgroundColor: Color.fromARGB(255, 50, 64, 182)),
      body: Hero(
        tag: 'top',
        child: Column(
          children: <Widget>[
            Container(height: 80.0),
            RaisedButton(
              child: Text('Back'),
              onPressed: () {
                Navigator.pop(context);
              },
            ),
          ],
        ),
      ),
    );
  }
}

class MyCustomRoute<T> extends MaterialPageRoute<T> {
  MyCustomRoute({ WidgetBuilder builder, RouteSettings settings })
      : super(builder: builder, settings: settings);

  @override
  Widget buildTransitions(BuildContext context,
      Animation<double> animation,
      Animation<double> secondaryAnimation,
      Widget child) {
    if (settings.isInitialRoute)
      return child;
    // Fades between routes. (If you don't want any animation, 
    // just return child.)
    return new FadeTransition(opacity: animation, child: child);
  }
}

Demo gif

Upvotes: 1

Related Questions