从数据库中获取状态对象
Fetch state-object from database
我想在启动时从数据库中获取我的状态。我在我的第一个小部件中使用提供程序和 ChangeNotivierProvider。包含用于说明的代码。
这是我的主要方法,它有提供我计划在应用程序中使用的状态的小部件:
void main() => runApp(
ChangeNotifierProvider(
child: MyApp(),
builder: (context) => StateDao.get(),
),
}
我的 DAO 只是 returns 来自数据库的状态(我使用 sembast,但也可以很容易地成为 sqflite 或 Firebase)
Future<State> get() async {
// Database logic
}
State 只是一个扩展 ChangeNotifier 的对象
class State extends ChangeNotifier {
// Getters, setters, changeNotifiers etc.
}
这将不起作用,因为我无法在 ChangeNotifierProvider 的构建器方法中调用 async 方法。应该如何、何时、何地对其进行初始化?据我了解,不应该在任何构建方法中进行异步调用。我尝试覆盖提供上下文访问的 didChangeDependencies,但我无法通过构建器方法限制中的异步调用。
可以在initState中初始化值。例如,您可以存储 Future 对象并在解析值时使用 FutureBuilder 构建小部件:
Future<State> futureState;
@override
void initState() {
// Calling async method and storing Future object
futureState = StateDao.get();
super.initState();
}
@override
Widget build(BuildContext context) {
return FutureBuilder<State>(
future: futureState,
builder: (context, snapshot) {
// No data yet, showing loader
if (!snapshot.hasData) {
return CircularProgressIndicator();
}
return ChangeNotifierProvider(
child: MyApp(),
builder: (context) => snapshot.data,
);
},
);
}
另一种类似的方法是使用 StreamController 和 StreamBuilder:
final StreamController<State> stateStream = StreamController<State>();
@override
void initState() {
// Calling async method and setting callback to add data to the stream
StateDao.get().then((v) => stateStream.add(v));
super.initState();
}
@override
void dispose() {
// Closing the sink
stateStream.close();
super.dispose();
}
@override
Widget build(BuildContext context) {
return StreamBuilder<State>(
stream: stateStream.stream,
builder: (context, snapshot) {
// No data yet, showing loader
if (!snapshot.hasData) {
return CircularProgressIndicator();
}
return ChangeNotifierProvider(
child: MyApp(),
builder: (context) => snapshot.data,
);
},
);
}
如果你需要更复杂的架构,你可能想看看 BLoC,这是 Flutter 社区中非常流行的架构。
我想在启动时从数据库中获取我的状态。我在我的第一个小部件中使用提供程序和 ChangeNotivierProvider。包含用于说明的代码。
这是我的主要方法,它有提供我计划在应用程序中使用的状态的小部件:
void main() => runApp(
ChangeNotifierProvider(
child: MyApp(),
builder: (context) => StateDao.get(),
),
}
我的 DAO 只是 returns 来自数据库的状态(我使用 sembast,但也可以很容易地成为 sqflite 或 Firebase)
Future<State> get() async {
// Database logic
}
State 只是一个扩展 ChangeNotifier 的对象
class State extends ChangeNotifier {
// Getters, setters, changeNotifiers etc.
}
这将不起作用,因为我无法在 ChangeNotifierProvider 的构建器方法中调用 async 方法。应该如何、何时、何地对其进行初始化?据我了解,不应该在任何构建方法中进行异步调用。我尝试覆盖提供上下文访问的 didChangeDependencies,但我无法通过构建器方法限制中的异步调用。
可以在initState中初始化值。例如,您可以存储 Future 对象并在解析值时使用 FutureBuilder 构建小部件:
Future<State> futureState;
@override
void initState() {
// Calling async method and storing Future object
futureState = StateDao.get();
super.initState();
}
@override
Widget build(BuildContext context) {
return FutureBuilder<State>(
future: futureState,
builder: (context, snapshot) {
// No data yet, showing loader
if (!snapshot.hasData) {
return CircularProgressIndicator();
}
return ChangeNotifierProvider(
child: MyApp(),
builder: (context) => snapshot.data,
);
},
);
}
另一种类似的方法是使用 StreamController 和 StreamBuilder:
final StreamController<State> stateStream = StreamController<State>();
@override
void initState() {
// Calling async method and setting callback to add data to the stream
StateDao.get().then((v) => stateStream.add(v));
super.initState();
}
@override
void dispose() {
// Closing the sink
stateStream.close();
super.dispose();
}
@override
Widget build(BuildContext context) {
return StreamBuilder<State>(
stream: stateStream.stream,
builder: (context, snapshot) {
// No data yet, showing loader
if (!snapshot.hasData) {
return CircularProgressIndicator();
}
return ChangeNotifierProvider(
child: MyApp(),
builder: (context) => snapshot.data,
);
},
);
}
如果你需要更复杂的架构,你可能想看看 BLoC,这是 Flutter 社区中非常流行的架构。