如何在调用Navigator.pushNamed()后刷新StatefulWidget



我在做什么

有两个页面:个人资料和登录页面。

首先显示个人资料页面,但当用户尚未登录时,个人资料页面不显示个人资料和显示登录按钮。

概要文件代码

bool loggedin = false;      // If user already logged in return true

class Profile extends StatefulWidget {
const Profile({Key? key}) : super(key: key);
@override
_Profile createState() => _Profile();
}
class _Profile extends State<Profile> {
@override
Widget build(BuildContext context) {
return loggedin
? Column(children: [  //.... some user information
])
: needLogin(context);
}
}
Widget needLogin(BuildContext context) {
return Center(
TextButton(
onPressed: () {
Navigator.of(context).pushNamed("/login");
},
child: const Text(
"Login",
style: TextStyle(fontSize: 20),
)),
);
}

Loggin页面

// The code to login is omitted. if login succeeded do loggedin = true; in setState()
var user = FirebaseAuth.instance.currentUser;
if (user != null) {
Navigator.of(context).pop();
setState(() {
loggedin = true;
});
}
// Then back to profile page automatically 

我在setState()中做了loggedin = true;,但个人资料页面仍然显示needLogin()的登录按钮。

我在StatefulWidget之外写needLogin()的原因是为了与其他StatefulWidget重用它。

Navigator.of(context).pushNamed()生成的页面中调用setState(),如何更新上一页?

您必须编辑needLogin方法,并通过Navigator返回成功状态/bool:

概要文件代码

class Profile extends StatefulWidget {
const Profile({Key? key}) : super(key: key);
@override
_Profile createState() => _Profile();
}
class _Profile extends State<Profile> {
@override
Widget build(BuildContext context) {
return loggedin
? Column(children: [  //.... some user information
])
: needLogin(context, () => setState(() {loggedIn = true}));
}
}

Widget needLogin(BuildContext context, void Function() setStateFunction) {
return Center(
child: TextButton(
onPressed: () async {
await Navigator.of(context)
.pushNamed("/login")
.then((result) {
if (result as bool) {
setStateFunction.call();
}
});
},
child: const Text(
"Login",
style: TextStyle(fontSize: 20),
)),
);
}
登录页面


var user = FirebaseAuth.instance.currentUser;
if (user != null) {
Navigator.pop(context, true);
}

不要

loggedin

在小部件外部。

使用于:

类_Profile扩展状态{

另外,您可能想要研究一些状态管理技术,例如带有Change notification的Provider。它非常容易使用,并且可以完全满足您的需求。

UI不应该包含业务逻辑,而应该基于某种类型的控制器来呈现。这使得代码更加一致,可读性和可测试性。

相关内容

  • 没有找到相关文章

最新更新