Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
1.8k views
in Technique[技术] by (71.8m points)

flutter - How can I initialize my app with provider?

I choose to use provider as my state management so I saw I have to use Multi provider.

My struggle is how to architect my code that I can initialize all the data I need when my app first run and give the providers to the multi provider.

Provider example

import 'package:cron/cron.dart';
import 'package:flutter/material.dart';
import 'package:web_app/models/fixture.dart';
import 'package:web_app/services/fixture_service.dart';

class HighlightsProvider extends ChangeNotifier {
  final List<Fixture> _highlights = [];

  List<Fixture> get() => _highlights;

  Future<void> fetchHighlights() async {
    try {
      List<Fixture> highlightFixtures = [];
      final response = await FixtureService().getAppHighlightFixtures();
      [...response].asMap().forEach((index, element) {
        highlightFixtures.add(new Fixture.fromJson(element));
      });
      _highlights.clear();
      _highlights.addAll(highlightFixtures);
      notifyListeners();
    } catch (e) {
      print('error');
      print(e);
    }
  }

  runJob(cron) {
    cron.schedule(Schedule.parse('* * * * *'), () async {
      fetchHighlights();
      print('fetch highlights every one minute');
    });
  }
}

Let's say this class will get all my providers and initialize theme:

class InitializeApp {
  final cron = Cron();

  Future run(HighlightsProvider highlightsProvider) async {
    return Future.wait([
      initiakizeHighlights(highlightsProvider),
    ]);
  }

  Future initiakizeHighlights(HighlightsProvider highlightsProvider) async {
    highlightsProvider.runJob(cron);
    await highlightsProvider.fetchHighlights();
  }
}

Then I have to deliver those provider to the multi provider:

void main() async {
  final highlightsProvider = HighlightsProvider();
  await InitializeApp().run(highlightsProvider);
  print('ready');
  runApp(MyApp(highlightsProvider: highlightsProvider));
}

class MyApp extends StatelessWidget {
  final highlightsProvider;

  const MyApp({Key key, this.highlightsProvider}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    print('build');

    return MultiProvider(
      providers: [
        ChangeNotifierProvider<HighlightsProvider>.value(
          value: highlightsProvider,
        )
      ],
      child: MaterialApp(
          title: 'tech',
          theme: ThemeData(
            primarySwatch: Colors.amber,
            brightness: Brightness.light,
          ),
          routes: <String, WidgetBuilder>{
            '/': (BuildContext context) {
              return MyHomePage(title: 'Flutter Demo Home Page');
            }
          }),
    );
  }
}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Normally you just wrap your MaterialApp with the MultiProvider, then you already have access to all Providers you will define.

Widget build(BuildContext context) {
return MultiProvider(
  providers: [
    StreamProvider<RecipeStreamService>.value(value: RecipeStreamService().controllerOut)
  ],
  child: MaterialApp(
        debugShowCheckedModeBanner: false,
        title: 'Home Food',
        routes: {
          '/register': (BuildContext context) => RegisterPage(),
          '/login': (BuildContext context) => LoginPage()
        },
        ),
        home: HomePage(title: 'Home'),
      ),
  );
}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...