如何在Flutter中停用或覆盖Android“后退”按钮?
在特定页面上,有没有办法停用Android后退按钮?
class WakeUpApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return new MaterialApp(
title: "Time To Wake Up ?",
home: new WakeUpHome(),
routes: {
'/pageOne': (BuildContext context) => new pageOne(),
'/pageTwo': (BuildContext context) => new pageTwo(),
},
);
}
}
在pageOne上,我有一个转到pageTwo的按钮:
new FloatingActionButton(
onPressed: () {
Navigator.of(context).pushNamed('/pageTwo');
},
)
我的问题是,如果我按下android屏幕底部的“后退”箭头,则会回到pageOne。 我希望此按钮完全不显示。理想情况下,除非用户例如在屏幕上按住手指5秒钟,否则我将无法离开该屏幕。 (我正在尝试为幼儿编写一个应用程序,希望只有父母能够导航到特定屏幕之外)。
Jackpap asked 2020-06-20T23:58:29Z
8个解决方案
89 votes
答案是WillPopScope。这将防止系统弹出页面。 您仍然可以使用Navigator.of(context).pop()
@override
Widget build(BuildContext context) {
return new WillPopScope(
onWillPop: () async => false,
child: new Scaffold(
appBar: new AppBar(
title: new Text("data"),
leading: new IconButton(
icon: new Icon(Icons.ac_unit),
onPressed: () => Navigator.of(context).pop(),
),
),
),
);
}
Rémi Rousselet answered 2020-06-20T23:58:43Z
6 votes
正如RémiRousselet所指出的那样,通常是WillPopScope。 但是,如果要开发一个有状态的小部件,该小部件应直接对后退按钮做出反应,则可以使用以下方法:
[HTTPS://普遍.大热天狼.org/packages/back_button_interceptor]
MarcG answered 2020-06-20T23:59:07Z
2 votes
我将其发布在这里,以防有人发现并希望他们能找到一个简单的示例[https://gist.github.com/b-cancel/0ca372017a25f0c120b14dfca3591aa5]
import 'package:flutter/material.dart';
import 'dart:async';
void main() => runApp(new BackButtonOverrideDemoWidget());
class BackButtonOverrideDemoWidget extends StatefulWidget{
@override
_BackButtonOverrideDemoWidgetState createState() => new _BackButtonOverrideDemoWidgetState();
}
class _BackButtonOverrideDemoWidgetState extends State with WidgetsBindingObserver{
//-------------------------Test Variable
bool isBackButtonActivated = false;
//-------------------------Required For WidgetsBindingObserver
@override
void initState() {
super.initState();
WidgetsBinding.instance.addObserver(this);
}
@override
void dispose() {
WidgetsBinding.instance.removeObserver(this);
super.dispose();
}
//-------------------------Function That Triggers when you hit the back key
@override
didPopRoute(){
bool override;
if(isBackButtonActivated)
override = false;
else
override = true;
return new Future.value(override);
}
//-------------------------Build Method
@override
Widget build(BuildContext context) {
return new Directionality(
textDirection: TextDirection.ltr,
child: new Container(
color: (isBackButtonActivated) ? Colors.green : Colors.red,
child: new Center(
child: new FlatButton(
color: Colors.white,
onPressed: () {
isBackButtonActivated = !isBackButtonActivated;
setState(() {});
},
child: (isBackButtonActivated) ?
new Text("DeActive the Back Button") : new Text("Activate the Back Button"),
)
)
),
);
}
}
Bryan Cancel answered 2020-06-20T23:59:27Z
2 votes
您可以使用Future.value(bool)处理后退按钮。
bool _allow = true;
@override
Widget build(BuildContext context) {
return WillPopScope(
child: Scaffold(appBar: AppBar(title: Text("Back"))),
onWillPop: () {
return Future.value(_allow); // if true allow back else block it
},
);
}
CopsOnRoad answered 2020-06-20T23:59:47Z
0 votes
您应该使用方法popAndPushNamed而不是pushNamed。它将弹出当前路径并推送所需的路径。
话虽如此,您的FAB代码应如下所示
new FloatingActionButton(
onPressed: () {
Navigator.popAndPushNamed(context, '/pageTwo');
},
)
icazevedo answered 2020-06-21T00:00:12Z
0 votes
尽管Remi的答案是正确的,但通常您不想简单地阻止后退按钮,而希望用户确认退出。
您可以通过从确认对话框中获得答案来类似地进行操作,因为onWillPop是未来。
@override
Widget build(BuildContext context) {
return WillPopScope(
child: Scaffold(...),
onWillPop: () => showDialog(
context: context,
builder: (c) => AlertDialog(
title: Text('Warning'),
content: Text('Do you really want to exit'),
actions: [
FlatButton(
child: Text('Yes'),
onPressed: () => Navigator.pop(c, true),
),
FlatButton(
child: Text('No'),
onPressed: () => Navigator.pop(c, false),
),
],
),
),
);
}
Airon Tark answered 2020-06-21T00:00:36Z
0 votes
我使用mixin和WillPopScope小部件只是无法为我完成工作。我发现这是最好的方法,比我认为的WillPopScope好得多。
final bool canPop = ModalRoute.of(context)?.canPop ?? false;
在应用栏内这样使用它:
leading: ModalRoute.of(context)?.canPop ?? false
? IconButton(
onPressed: () {
Navigator.pop(context);
},
icon: (Platform.isAndroid)
? const Icon(Icons.arrow_back)
: const Icon(Icons.arrow_back_ios),
)
: Container(),
Djordje Komazec answered 2020-06-21T00:01:05Z
-2 votes
您可以使用的方法如下:
new FloatingActionButton(
onPressed: () {
Navigator.of(context).pushReplacementNamed('/pageTwo');
},
)
希望这可以帮助。 谢谢
Bernard Nongpoh answered 2020-06-21T00:01:29Z