Flutter: Ask for Confirmation when Back button pressed

Updated: February 4, 2023 By: A Goodman 2 comments

When developing Flutter apps, there might be cases where we want to display a confirmation dialog when a user presses the back button. The purpose is to prevent accidentally leaving a screen (page), especially a screen with unsaved form data. A good solution for this is to wrap the screen that requires confirmation before leaving within a WillPopScope widget:

Widget build(BuildContext context) {
    return WillPopScope(
        onWillPop: () {
          /* ... */
          // Show the confirmation dialog
          // Return "true" means "go back", return "false" means "stay here"
        },
        child: Scaffold(
          /* ... */
        ));
}

For more clarity, see the example below.

Example

The tiny app we are going to build has 2 screens:

  • HomeScreen: Contains a button in the center of the screen that lets the user navigate to OtherScreen.
  • OtherScreen: Contains nothing but an app bar with a back button. When the back button is pressed, a confirmation popup will show up. If the user selects “Yes”, he or she will go back to the HomeScreen. If the user selects “No”, they will stay here, and the popup will go away too.

Preview

The Complete Code

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

void main() {
  runApp(const MyApp());
}

class MyApp extends StatelessWidget {
  const MyApp({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
        // Remove the debug banner
        debugShowCheckedModeBanner: false,
        title: 'Kindacode.com',
        theme: ThemeData(
          primarySwatch: Colors.purple,
        ),
        home: const HomeScreen());
  }
}

class HomeScreen extends StatelessWidget {
  const HomeScreen({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Kindacode.com'),
      ),
      body: Center(
        child: ElevatedButton(
          onPressed: () {
            Navigator.of(context)
                .push(MaterialPageRoute(builder: (_) => const OtherScreen()));
          },
          child: const Text('Navigate to OtherScreen'),
        ),
      ),
    );
  }
}

class OtherScreen extends StatelessWidget {
  const OtherScreen({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return WillPopScope(
        onWillPop: () async {
          bool willLeave = false;
          // show the confirm dialog
          await showDialog(
              context: context,
              builder: (_) => AlertDialog(
                    title: const Text('Are you sure want to leave?'),
                    actions: [
                      ElevatedButton(
                          onPressed: () {
                            willLeave = true;
                            Navigator.of(context).pop();
                          },
                          child: const Text('Yes')),
                      TextButton(
                          onPressed: () => Navigator.of(context).pop(),
                          child: const Text('No'))
                    ],
                  ));
          return willLeave;
        },
        child: Scaffold(
          appBar: AppBar(
            title: const Text('Other Screen'),
          ),
          body: const Center(),
        ));
  }
}

Conclusion

We’ve examined a complete example of displaying a confirmation popup when the user presses the back button. If you’d like to learn more new and interesting things about Flutter, have a look at the following articles:

You can also check out our Flutter category page or Dart category page for the latest tutorials and examples.

Subscribe
Notify of
guest
2 Comments
Inline Feedbacks
View all comments
Steven Jennings
Steven Jennings
2 years ago

In the dialog’s ElevatedButton’s onPressed you need to set willLeave=true or you will not leave. Otherwise code works great.

Related Articles