如何为 Stateful Widget 创建 Flutter 路由?
How to create Flutter route for Stateful Widget?
我收到了我的 Flutter 应用程序的 Navigator operation requested with a context that does not include a Navigator.
错误日志。我看到的所有示例都是针对 "Stateless" 小部件的,所以我认为这可能是问题或我的代码?我怎样才能路由到我的 LoginPage
?这是我的代码,没有任何导航器或路线...
void main() {
runApp(new MyApp());
}
final googleSignIn = new GoogleSignIn();
final fb = FirebaseDatabase.instance.reference();
final auth = FirebaseAuth.instance;
class MyApp extends StatefulWidget {
@override
_MyAppState createState() => new _MyAppState();
}
class _MyAppState extends State<MyApp> {
String _platformVersion = 'Unknown';
@override
initState() {
super.initState();
initPlatformState();
}
// Platform messages are asynchronous, so we initialize in an async method.
initPlatformState() async {
String platformVersion;
// Platform messages may fail, so we use a try/catch PlatformException.
try {
platformVersion = await Myfavkpopflutter.platformVersion;
} on PlatformException {
platformVersion = 'Failed to get platform version.';
}
// If the widget was removed from the tree while the asynchronous platform
// message was in flight, we want to discard the reply rather than calling
// setState to update our non-existent appearance.
if (!mounted) return;
setState(() {
_platformVersion = platformVersion;
});
}
void MyFavAction() {
setState(() {
print("MYFAV");
// fb.child("messages").orderByValue().onChildAdded.listen((Event event) {
// print('Child added: ${event.snapshot.value}');
// });
});
}
void SearchAction() {
setState(() {
print("Search");
});
}
@override
Widget build(BuildContext context) {
if (auth.currentUser == null) {
return new MaterialApp(
routes: <String, WidgetBuilder>{
'/settings': (BuildContext context) => new LoginPage(),
},
home: new Scaffold(
backgroundColor: Colors.white70,
appBar: new AppBar(
title: new Text(
"MyFavKPop",
style: new TextStyle(
color: Colors.black,
fontWeight: FontWeight.bold,
fontSize: 25.00),
),
backgroundColor: Colors.amber,
),
body: new Container(
child: new Center(
child: new Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new RaisedButton(
onPressed: MyFavAction,
color: Colors.lightBlue,
elevation: 20.00,
splashColor: Colors.amber,
child: new Text(
"MyFav KPOP",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(padding: new EdgeInsets.all(30.00)),
new RaisedButton(
onPressed: SearchAction,
color: Colors.lightBlue,
elevation: 20.00,
splashColor: Colors.amber,
child: new Text(
"MyFav SEARCH",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(padding: new EdgeInsets.all(30.00),
),
new RaisedButton(
onPressed: SearchAction,
elevation: 20.00,
splashColor: Colors.amber,
color: Colors.lightBlue,
child: new Text(
"MyFav FRIENDS",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(
padding: new EdgeInsets.all(30.00),
),
new RaisedButton(
onPressed: SearchAction,
elevation: 20.00,
splashColor: Colors.amber,
color: Colors.lightBlue,
child: new Text(
"MyFav CHAT",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(
padding: new EdgeInsets.all(30.00),
),
new RaisedButton(
onPressed: SearchAction,
elevation: 20.00,
splashColor: Colors.amber,
color: Colors.lightBlue,
child: new Text(
"MyFav #1'S",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
)
],
))),
floatingActionButton: new FloatingActionButton(
child: new Text(
"Log Out",
style: new TextStyle(fontWeight: FontWeight.bold, fontSize: 12.00),
),
onPressed: () => Navigator.of(context).pushNamed('/settings'),,
),
));
}
}
}
class LoginPage extends StatelessWidget {
@override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text("Login / Signup"),
),
body: new Container(
child: new Center(
child: new Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new TextField(
decoration: new InputDecoration(
hintText: "E M A I L A D D R E S S"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new TextField(
obscureText: true,
decoration:
new InputDecoration(hintText: "P A S S W O R D"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new TextField(
decoration:
new InputDecoration(hintText: "U S E R N A M E"),
),
new RaisedButton(
onPressed: null,
child: new Text("SIGNUP"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new RaisedButton(
onPressed: null,
child: new Text("LOGIN"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new RaisedButton(
onPressed: null,
child: new Text("Facebook"),
),
new Padding(padding: new EdgeInsets.all(5.00)),
new RaisedButton(
onPressed: null,
child: new Text("Google"),
)
],
),
),
margin: new EdgeInsets.all(15.00),
),
);
}
}
**** 编辑这是我收到的错误日志...
══╡手势异常╞═══════════════════════════════════ ══════════════════════════════
处理手势时抛出以下断言:
使用不包含导航器的上下文请求的导航器操作。
用于从导航器推送或弹出路由的上下文必须是一个小部件的上下文
导航器小部件的后代。
═══════════════════════════════════════════ ══════════════════════════════════════════════════ ═════
此错误与有状态或无状态路由无关。您可以查看我的回答 以获取工作示例。
顺便说一句:我在你的代码中找不到你对 Navigator 的调用。你如何以及在哪里调用推送?
编辑
您的应用程序中应该始终只有一个 MaterialApp。您可以为一个 MaterialApp 提供各种路由(参见我的示例)。
您在标题中说明您的问题是导航到 StatefulWidget,而在您的 post 中您询问如何导航到 StatelessWidget LoginPage。
无论如何,无论状态如何,您都应该能够以相同的方式实现导航。
尝试遵循以下流程,该流程取自我正在开发的应用程序。
//Local Imports
//MyTabs.dart is where I define my home page which is a StatefulWidget with TabBarView
import 'MyTabs.dart' as first;
.....
//My main function where I start my app
void main() {
runApp( new MaterialApp(
home: new SignIn(),
routes: <String, WidgetBuilder>{
"/mytabs" : (BuildContext context)=> new first.MyTabs(),
//add more routes here
},
));
}
我的应用程序从一个登录页面开始,我创建了一个比展示想法更简单的页面
class SignIn extends StatelessWidget {
@override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text("Sign In"),
),
body: new IconButton(icon: new Icon(Icons.arrow_forward), onPressed: (){Navigator.of(context).pushNamed("/mytabs");}),
)
希望对您有所帮助,尝试在您的代码中遵循此流程,让我知道进展如何。
Navigator.of(context).push(new MaterialPageRoute(builder:
(BuildContext context) => new MyTabs()));
对于导航,我们也可以使用上面的代码。
我收到了我的 Flutter 应用程序的 Navigator operation requested with a context that does not include a Navigator.
错误日志。我看到的所有示例都是针对 "Stateless" 小部件的,所以我认为这可能是问题或我的代码?我怎样才能路由到我的 LoginPage
?这是我的代码,没有任何导航器或路线...
void main() {
runApp(new MyApp());
}
final googleSignIn = new GoogleSignIn();
final fb = FirebaseDatabase.instance.reference();
final auth = FirebaseAuth.instance;
class MyApp extends StatefulWidget {
@override
_MyAppState createState() => new _MyAppState();
}
class _MyAppState extends State<MyApp> {
String _platformVersion = 'Unknown';
@override
initState() {
super.initState();
initPlatformState();
}
// Platform messages are asynchronous, so we initialize in an async method.
initPlatformState() async {
String platformVersion;
// Platform messages may fail, so we use a try/catch PlatformException.
try {
platformVersion = await Myfavkpopflutter.platformVersion;
} on PlatformException {
platformVersion = 'Failed to get platform version.';
}
// If the widget was removed from the tree while the asynchronous platform
// message was in flight, we want to discard the reply rather than calling
// setState to update our non-existent appearance.
if (!mounted) return;
setState(() {
_platformVersion = platformVersion;
});
}
void MyFavAction() {
setState(() {
print("MYFAV");
// fb.child("messages").orderByValue().onChildAdded.listen((Event event) {
// print('Child added: ${event.snapshot.value}');
// });
});
}
void SearchAction() {
setState(() {
print("Search");
});
}
@override
Widget build(BuildContext context) {
if (auth.currentUser == null) {
return new MaterialApp(
routes: <String, WidgetBuilder>{
'/settings': (BuildContext context) => new LoginPage(),
},
home: new Scaffold(
backgroundColor: Colors.white70,
appBar: new AppBar(
title: new Text(
"MyFavKPop",
style: new TextStyle(
color: Colors.black,
fontWeight: FontWeight.bold,
fontSize: 25.00),
),
backgroundColor: Colors.amber,
),
body: new Container(
child: new Center(
child: new Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new RaisedButton(
onPressed: MyFavAction,
color: Colors.lightBlue,
elevation: 20.00,
splashColor: Colors.amber,
child: new Text(
"MyFav KPOP",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(padding: new EdgeInsets.all(30.00)),
new RaisedButton(
onPressed: SearchAction,
color: Colors.lightBlue,
elevation: 20.00,
splashColor: Colors.amber,
child: new Text(
"MyFav SEARCH",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(padding: new EdgeInsets.all(30.00),
),
new RaisedButton(
onPressed: SearchAction,
elevation: 20.00,
splashColor: Colors.amber,
color: Colors.lightBlue,
child: new Text(
"MyFav FRIENDS",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(
padding: new EdgeInsets.all(30.00),
),
new RaisedButton(
onPressed: SearchAction,
elevation: 20.00,
splashColor: Colors.amber,
color: Colors.lightBlue,
child: new Text(
"MyFav CHAT",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
),
new Padding(
padding: new EdgeInsets.all(30.00),
),
new RaisedButton(
onPressed: SearchAction,
elevation: 20.00,
splashColor: Colors.amber,
color: Colors.lightBlue,
child: new Text(
"MyFav #1'S",
style: new TextStyle(color: Colors.black, fontSize: 20.00),
),
)
],
))),
floatingActionButton: new FloatingActionButton(
child: new Text(
"Log Out",
style: new TextStyle(fontWeight: FontWeight.bold, fontSize: 12.00),
),
onPressed: () => Navigator.of(context).pushNamed('/settings'),,
),
));
}
}
}
class LoginPage extends StatelessWidget {
@override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text("Login / Signup"),
),
body: new Container(
child: new Center(
child: new Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new TextField(
decoration: new InputDecoration(
hintText: "E M A I L A D D R E S S"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new TextField(
obscureText: true,
decoration:
new InputDecoration(hintText: "P A S S W O R D"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new TextField(
decoration:
new InputDecoration(hintText: "U S E R N A M E"),
),
new RaisedButton(
onPressed: null,
child: new Text("SIGNUP"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new RaisedButton(
onPressed: null,
child: new Text("LOGIN"),
),
new Padding(padding: new EdgeInsets.all(15.00)),
new RaisedButton(
onPressed: null,
child: new Text("Facebook"),
),
new Padding(padding: new EdgeInsets.all(5.00)),
new RaisedButton(
onPressed: null,
child: new Text("Google"),
)
],
),
),
margin: new EdgeInsets.all(15.00),
),
);
}
}
**** 编辑这是我收到的错误日志...
══╡手势异常╞═══════════════════════════════════ ══════════════════════════════ 处理手势时抛出以下断言: 使用不包含导航器的上下文请求的导航器操作。 用于从导航器推送或弹出路由的上下文必须是一个小部件的上下文 导航器小部件的后代。
═══════════════════════════════════════════ ══════════════════════════════════════════════════ ═════
此错误与有状态或无状态路由无关。您可以查看我的回答
顺便说一句:我在你的代码中找不到你对 Navigator 的调用。你如何以及在哪里调用推送?
编辑
您的应用程序中应该始终只有一个 MaterialApp。您可以为一个 MaterialApp 提供各种路由(参见我的示例)。
您在标题中说明您的问题是导航到 StatefulWidget,而在您的 post 中您询问如何导航到 StatelessWidget LoginPage。
无论如何,无论状态如何,您都应该能够以相同的方式实现导航。
尝试遵循以下流程,该流程取自我正在开发的应用程序。
//Local Imports
//MyTabs.dart is where I define my home page which is a StatefulWidget with TabBarView
import 'MyTabs.dart' as first;
.....
//My main function where I start my app
void main() {
runApp( new MaterialApp(
home: new SignIn(),
routes: <String, WidgetBuilder>{
"/mytabs" : (BuildContext context)=> new first.MyTabs(),
//add more routes here
},
));
}
我的应用程序从一个登录页面开始,我创建了一个比展示想法更简单的页面
class SignIn extends StatelessWidget {
@override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text("Sign In"),
),
body: new IconButton(icon: new Icon(Icons.arrow_forward), onPressed: (){Navigator.of(context).pushNamed("/mytabs");}),
)
希望对您有所帮助,尝试在您的代码中遵循此流程,让我知道进展如何。
Navigator.of(context).push(new MaterialPageRoute(builder:
(BuildContext context) => new MyTabs()));
对于导航,我们也可以使用上面的代码。