我正在寻找一种在InitState方法上加载异步数据的方法,在构建方法运行之前我需要一些数据.我正在使用GoogleAuth代码,我需要执行构建方法,直到Stream运行.
我的initState方法是:
@override
void initState () {
super.initState();
_googleSignIn.onCurrentUserChanged.listen((GoogleSignInAccount account) {
setState(() {
_currentUser = account;
});
});
_googleSignIn.signInSilently();
}
Run Code Online (Sandbox Code Playgroud)
我将不胜感激任何反馈.
die*_*per 19
您可以创建一个async方法并在您的内部调用它initState
@override
void initState () {
super.initState();
_asyncMethod();
}
_asyncMethod() async {
_googleSignIn.onCurrentUserChanged.listen((GoogleSignInAccount account) {
setState(() {
_currentUser = account;
});
});
_googleSignIn.signInSilently();
}
Run Code Online (Sandbox Code Playgroud)
Nae*_*Nae 15
截至目前,使用.then符号似乎有效:
// ...
@override
initState() {
super.initState();
asyncFunction.then((result) {
print("result: $result");
setState(() {});
});
}
//...
Run Code Online (Sandbox Code Playgroud)
iDe*_*ode 10
initState像这样在里面创建匿名函数:
@override
void initState() {
super.initState();
// Create anonymous function:
() async {
await _performYourTask();
setState(() {
// Update your UI with the desired changes.
});
} ();
}
Run Code Online (Sandbox Code Playgroud)
您可以创建一个异步方法并在initState中调用它
@override
void initState() {
super.initState();
asyncMethod(); ///initiate your method here
}
Future<void> asyncMethod async{
await ///write your method body here
}
Run Code Online (Sandbox Code Playgroud)
您可以使用StreamBuilder执行此操作.只要流中的数据发生更改,这将运行构建器方法.
以下是我的一个示例项目的代码片段:
StreamBuilder<List<Content>> _getContentsList(BuildContext context) {
final BlocProvider blocProvider = BlocProvider.of(context);
int page = 1;
return StreamBuilder<List<Content>>(
stream: blocProvider.contentBloc.contents,
initialData: [],
builder: (context, snapshot) {
if (snapshot.data.isNotEmpty) {
return ListView.builder(itemBuilder: (context, index) {
if (index < snapshot.data.length) {
return ContentBox(content: snapshot.data.elementAt(index));
} else if (index / 5 == page) {
page++;
blocProvider.contentBloc.index.add(index);
}
});
} else {
return Center(
child: CircularProgressIndicator(),
);
}
});
}
Run Code Online (Sandbox Code Playgroud)
在上面的代码中,StreamBuilder监听内容的任何变化,最初是一个空数组并显示CircularProgressIndicator.一旦我进行API调用,就会将fetched数据添加到contents数组中,该数组将运行builder方法.
当用户向下滚动时,将获取更多内容并将其添加到内容数组中,这将再次运行构建器方法.
在您的情况下,只需要初始加载.但是,这为您提供了一个选项,可以在屏幕上显示其他内容,直到获取数据.
希望这是有帮助的.
编辑:
在你的情况下,我猜它将看起来如下所示:
StreamBuilder<List<Content>>(
stream: account, // stream data to listen for change
builder: (context, snapshot) {
if(account != null) {
return _googleSignIn.signInSilently();
} else {
// show loader or animation
}
});
Run Code Online (Sandbox Code Playgroud)
上一个答案!!
您可以设置一个布尔值,例如加载并在您的监听函数中将其设置为 true,并使您的构建函数在加载设置为 true 时返回您的数据,否则只抛出一个 CircularProgressIndicator
编辑 - 我不建议在您在 initState 中调用的方法中调用 setState。如果在调用 setState 时(在异步操作完成时)未安装小部件,则会报告错误。我建议你使用一个包after_layout
看看这个答案以更好地理解 initState 中的 setState :https ://stackoverflow.com/a/53373017/9206337
这篇文章将让您知道应用程序何时完成构建方法。这样您就可以在挂载小部件后等待异步方法设置状态:https : //stackoverflow.com/a/51273797/9206337
小智 6
@override
void initState() {
super.initState();
asyncInitState(); // async is not allowed on initState() directly
}
void asyncInitState() async {
await yourAsyncCalls();
}
Run Code Online (Sandbox Code Playgroud)
小智 6
根据https://pub.dev/packages/provider上的文档
initState() {
super.initState();
Future.microtask(() =>
context.read<MyNotifier>(context).fetchSomething(someValue);
);
}
Run Code Online (Sandbox Code Playgroud)
小智 5
这个怎么样?
@override
void initState() {
//you are not allowed to add async modifier to initState
Future.delayed(Duration.zero,() async {
//your async 'await' codes goes here
});
super.initState();
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
11027 次 |
| 最近记录: |