在我的 Flutter 应用程序中使用新的 Navigator 2.0 API 进行导航,我的代码具有以下简单版本:
import 'package:flutter/material.dart';
void main() {
runApp(const MainApp());
}
class MainApp extends StatelessWidget {
const MainApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Router(
routerDelegate: AppRouterDelegate(),
backButtonDispatcher: RootBackButtonDispatcher(),
),
);
}
}
class MainPage extends StatelessWidget {
const MainPage({super.key, required this.openFirstPage});
final VoidCallback openFirstPage;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Main page'),
backgroundColor: Colors.lightGreen,
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const Text('Welcome to main page!'),
ElevatedButton(
onPressed: openFirstPage,
child: const Text('Go to first page'),
),
],
),
),
);
}
}
class FirstPage extends StatelessWidget {
const FirstPage({super.key, required this.openSecondPage});
final VoidCallback openSecondPage;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('First page'),
backgroundColor: Colors.amber,
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const Text('Welcome to first page!'),
ElevatedButton(
onPressed: openSecondPage,
child: const Text('Go to second page'),
),
],
),
),
);
}
}
class SecondPage extends StatelessWidget {
const SecondPage({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Second page'),
backgroundColor: Colors.lightBlueAccent,
),
body: const Center(
child: Text('Welcome to second page!'),
),
);
}
}
class AppRouterDelegate extends RouterDelegate
with ChangeNotifier, PopNavigatorRouterDelegateMixin {
bool _showFirstPage = false;
void showFirstPage() {
_showFirstPage = true;
notifyListeners();
}
bool _showSecondPage = false;
void showSecondPage() {
_showSecondPage = true;
notifyListeners();
}
@override
Widget build(BuildContext context) {
return Navigator(
pages: [
MaterialPage(
key: const ValueKey('MainPage'),
child: MainPage(openFirstPage: showFirstPage),
),
if (_showFirstPage)
MaterialPage(
key: const ValueKey('FirstPage'),
child: FirstPage(openSecondPage: showSecondPage),
),
if (_showSecondPage)
const MaterialPage(
key: ValueKey('SecondPage'),
child: SecondPage(),
),
],
onDidRemovePage: (page) {
if (_showSecondPage) {
_showSecondPage = false;
return;
}
if (_showFirstPage) _showFirstPage = false;
},
);
}
@override
GlobalKey<NavigatorState>? get navigatorKey => GlobalKey();
@override
Future<void> setNewRoutePath(configuration) async {
// Do nothing
}
}
当点击
AppBar
中的后退按钮时,页面会按预期弹出(当前页面关闭并显示下面的页面):
Second Page ---> pop ---
| │
| ↓
First Page First Page ---> pop ---
| | │
| | ↓
Main Page Main Page Main Page
...,但是当按下/滑动 Android 后退按钮时,会关闭整个应用程序而不是当前页面。
Second Page ---> Android back btn pop ---
| │
| |
First Page |
| |
| ↓
Main Page App is closed
这是一个例子:
只需删除清单文件中的
android:enableOnBackInvokedCallback="true"