为什么这个bloc getter被调用为null?

问题描述 投票:0回答:1

以前我在main.dart中初始化我的PersonBlocProvider

return PersonBlocProvider(
        personBloc: PersonBloc(this._apiInterface),
        child: AlarmBlocProvider(
            alarmBloc: AlarmBloc(this._apiInterface),
            child: EventBlocProvider(
                eventBloc: EventBloc(this._apiInterface),
                child: MaterialApp(
                  title: 'Hat Mobile',
                  theme: ThemeData(
                    primarySwatch: Colors.green,
                  ),
                  home: LoginScreen(),
                )

            )
        )
    );

并在另一个视图中使用BLOC:

class AlarmView extends StatelessWidget {
  Widget build(BuildContext context) {
    final personBlocProvider = PersonBlocProvider.of(context);
    final alarmBlocProvider = AlarmBlocProvider.of(context);

    return
        DefaultTabController(
        length: 4,
        child: Scaffold(
          appBar: AppBar(
            automaticallyImplyLeading: false,
            actions: <Widget>[
              Padding(
                  padding: EdgeInsets.only(top: 10, right: 10),
                  child: Text(StringLiterals.ALARM_TEXT)),
              Padding(
                  padding: EdgeInsets.only(right: 15),
                  child: _BuildSwitch(bloc:  alarmBlocProvider))
            ],
            title: Text(StringLiterals.PAGE_TITLE_ALARM),
            bottom: MyTabBar(),
          ),
          body: TabBarView(
            children: <Widget>[
              _ListPage(StringLiterals.PRESENT, personBlocProvider),
              _ListPage(StringLiterals.SAFE, personBlocProvider),
              _ListPage(StringLiterals.UNKNOWN, personBlocProvider),
              _ListPage(StringLiterals.HOLIDAY, personBlocProvider),
            ],
          ),
        ),
    );
    }
}

这很有效,但是一旦应用程序启动就产生了BLoC,我意识到我不想这样做。

所以我决定将BlocProviders从main移动到我的视图文件。

我的主要成了

              return MaterialApp(
                  title: 'Hat Mobile',
                  theme: ThemeData(
                    primarySwatch: Colors.green,
                  ),
                  home: LoginScreen(),
                );

并查看:

class AlarmView extends StatelessWidget {
  Widget build(BuildContext context) {
    final personBlocProvider = PersonBlocProvider.of(context);
    final alarmBlocProvider = AlarmBlocProvider.of(context);

    return PersonBlocProvider(
        personBloc: PersonBloc(BlueApiMock()),
        child: AlarmBlocProvider(
            alarmBloc: AlarmBloc(BlueApiMock()),
            child: DefaultTabController(
              length: 4,
              child: Scaffold(
                appBar: AppBar(
                  automaticallyImplyLeading: false,
                  actions: <Widget>[
                    Padding(
                        padding: EdgeInsets.only(top: 10, right: 10),
                        child: Text(StringLiterals.ALARM_TEXT)),
                    Padding(
                        padding: EdgeInsets.only(right: 15),
                        child: _BuildSwitch(bloc: alarmBlocProvider))
//                  child: _BuildSwitch(bloc:  AlarmBloc(BlueApiMock())))
                  ],
                  title: Text(StringLiterals.PAGE_TITLE_ALARM),
                  bottom: MyTabBar(),
                ),
                body: TabBarView(
                  children: <Widget>[
                    _ListPage(StringLiterals.PRESENT, personBlocProvider),
                    _ListPage(StringLiterals.SAFE, personBlocProvider),
                    _ListPage(StringLiterals.UNKNOWN, personBlocProvider),
                    _ListPage(StringLiterals.HOLIDAY, personBlocProvider),
                  ],
                ),
              ),
            )
        ));
  }
}

但现在这导致了错误:

I/flutter ( 6448): The following NoSuchMethodError was thrown building AlarmView(dirty):
I/flutter ( 6448): The getter 'personBloc' was called on null.
I/flutter ( 6448): Receiver: null
I/flutter ( 6448): Tried calling: personBloc
I/flutter ( 6448): 
I/flutter ( 6448): When the exception was thrown, this was the stack:
I/flutter ( 6448): #0      Object.noSuchMethod (dart:core/runtime/libobject_patch.dart:50:5)
I/flutter ( 6448): #1      PersonBlocProvider.of (package:red_photon/alarm/providers/person_bloc_provider.dart:14:30)
I/flutter ( 6448): #2      AlarmView.build (package:red_photon/alarm/views/alarm_view.dart:17:51)

为什么现在为空?

dart flutter bloc
1个回答
2
投票

是的,你不能这样做,因为你传递的context不会有任何集团祖先,而是尝试在DefaultTabController Widget中包装Builder并使用该上下文(它将在集群树中将集团作为祖先)。

例:

class AlarmView extends StatelessWidget {
  Widget build(BuildContext context) {
    return PersonBlocProvider(
      personBloc: PersonBloc(BlueApiMock()),
      child: AlarmBlocProvider(
        alarmBloc: AlarmBloc(BlueApiMock()),
        child: Builder(
          builder: (context) {
            final personBlocProvider = PersonBlocProvider.of(context);
            final alarmBlocProvider = AlarmBlocProvider.of(context);

            return DefaultTabController(
              length: 4,
              child: Scaffold(
                appBar: AppBar(
                  automaticallyImplyLeading: false,
                  actions: <Widget>[
                    Padding(
                        padding: EdgeInsets.only(top: 10, right: 10),
                        child: Text(StringLiterals.ALARM_TEXT)),
                    Padding(
                        padding: EdgeInsets.only(right: 15),
                        child: _BuildSwitch(bloc: alarmBlocProvider))
                    //                  child: _BuildSwitch(bloc:  AlarmBloc(BlueApiMock())))
                  ],
                  title: Text(StringLiterals.PAGE_TITLE_ALARM),
                  bottom: MyTabBar(),
                ),
                body: TabBarView(
                  children: <Widget>[
                    _ListPage(StringLiterals.PRESENT, personBlocProvider),
                    _ListPage(StringLiterals.SAFE, personBlocProvider),
                    _ListPage(StringLiterals.UNKNOWN, personBlocProvider),
                    _ListPage(StringLiterals.HOLIDAY, personBlocProvider),
                  ],
                ),
              ),
            );
          },
        ),
      ),
    );
  }
}

这应该工作。

希望能帮助到你!

© www.soinside.com 2019 - 2024. All rights reserved.