I think your current code is enough, but if you want to use useMemoized I suggest this.
final future = useMemoized(SharedPreferences.getInstance);
final snapshot = useFuture(future, initialData: null);
useEffect(() {
final preferences = snapshot.data;
if (preferences == null) {
return;
}
preferences.getBool('');
}, [snapshot.data]);
Answer from jeiea on Stack OverflowVideos
The issue with:
useEffect(() {
model.fetchList();
}, []);
is that fetchList is called synchronously inside build and modify an ancestor widget, which is not good.
You can wrap the fetchList call in a microtask:
useEffect(() {
Future.microtask(() => model.fetchList());
}, []);
I know this question is old. But I hope my answer can help someone. I solved the problem by making the function call in the next frame
useEffect(() {
WidgetsBinding.instance.addPostFrameCallback((timeStamp) {
model.fetchList();
}
}, []);
you should use useEffect and useState for HookWidget is best as per my suggestion
useEffect -> when you want an effect (callback, listening other objects, more reactive stuff)
useMemoized -> expensive calculations that don't change that much (color based on a bool input and some other data, math, generate list based on other values)
useRef -> Creates an instance of an object as a reference and holds it until the widget is disposed (for example a http instance, you only want one for other things in your widget)
Create an async function inside your effect that wait the getData(1) result then call setData():
useEffect(() => {
const fetchData = async () => {
const data = await getData(1);
setData(data);
}
fetchData();
}, []);
If you're invoking it right-away you might want to use it as an anonymous function:
useEffect(() => {
(async () => {
const data = await getData(1);
setData(data);
})();
}, []);