英文:
BlocProvider.of() called with a context that does not contain a HomeBloc
问题
Sure, here is the translated content without the code parts:
-
I first defined a class that can record
BlocandGoRouterWidgetBuilder, collectively referred to as RouterWidgetBuilder. -
I initialized a map in the following format:
-
For the route "/":
- It uses a
RouterWidgetBuilderwithHomeBlocand theMyHomeScreenas the builder.
- It uses a
-
For the route "/details":
- It uses a
RouterWidgetBuilderwithDetailBlocand theDetailsScreenas the builder.
- It uses a
-
I printed it through the logger and found that homeBuilder!.create is HomeBloc. However, in HomeScreen, when using BlocProvider.of<HomeBloc>(context), an error is reported: "BlocProvider.of() called with a context that does not contain a HomeBloc."
May I ask how to solve this problem: "BlocProvider.of() called with a context that does not contain a HomeBloc."
英文:
**1、**I first defined a class that can record Bloc and GoRouterWidgetBuilder,The following collectively refer to it as: RouterWidgetBuilder
**2、**I initialized a map in the following format:
static final GoRouter routers = RouterX.generateRoutes(
routeMaps: {
"/" : RouterWidgetBuilder(
create: HomeBloc(),
builder: (context, params) => const MyHomeScreen(),
),
"/details" : RouterWidgetBuilder(
create: DetailBloc(),
builder: (context, params) => const DetailsScreen(),
),
}
);
GoRouter(
errorBuilder: (context, state) {
logger.e(state.error);
return PageNotFound();
},
routes: <RouteBase>[
GoRoute(
path: "/",
builder: (BuildContext context, GoRouterState state) {
return BlocProvider(
create: (context) => homeBuilder!.create,
child: homeBuilder!.builder(context, state),
);
},
routes: otherPageRouters,
),
],
)
I printed it through the logger and found that homeBuilder!.create is HomeBloc
But in HomeScreen, through BlocProvider.of<HomeBloc>(context), an error is reported:
BlocProvider.of() called with a context that does not contain a HomeBloc.
May I ask how to solve this problem: BlocProvider.of() called with a context that does not contain a HomeBloc.
答案1
得分: 1
This is a standard mistake. Your RouterWidgetBuilder is a class without generics and thus the type of RouterWidgetBuilder.create is Bloc and not HomeBloc, which makes the Provider also provide the implicit type Bloc. If you want to continue using your RouterWidgetBuilder, you should add a generic:
class RouterWidgetBuilder<B extends Bloc>{
final B create;
...
}
Also, your create should be a function, since the Bloc is initialized before there is even a Provider to dispose it. Because of this you can not use your RouterWidgetBuilder more than once. Currently your create object is disposed as soon as a the first Provider is disposed and cannot be created again, since you don't use a function for create.
EDIT:
If you absolutely want to keep your structure, you can move the builder from your widget to the RouterWidgetBuilder class, which will allow you to use the appropriate generics of the right type here:
GoRoute(
path: "/",
builder: (BuildContext context, GoRouterState state) {
return homeBuilder!.completeBuilder(context, state);
},
routes: otherPageRouters,
)
class RouterWidgetBuilder<B extends StateStreamableSource>{
final B Function(BuildContext context) create;
...
Widget completeBuilder(BuildContext context, GoRouterState state){
return BlocProvider<B>(
create: create,
child: builder(context, state),
);
}
}
英文:
This is a standard mistake. Your RouterWidgetBuilder is a class without generics and thus the type of RouterWidgetBuilder.create is Bloc and not HomeBloc, which makes the Provider also provide the implicit type Bloc. If you want to continue using your RouterWidgetBuilder, you should add a generic:
class RouterWidgetBuilder<B extends Bloc>{
final B create;
...
}
Also, your create should be a function, since the Bloc is initialized before there is even a Provider to dispose it. Because of this you can not use your RouterWidgetBuilder more than once. Currently your create object is disposed as soon as a the first Provider is disposed and cannot be created again, since you don't use a function for create.
EDIT:
If you absolutely want to keep your structure, you can move the builder from your widget to the RouterWidgetBuilder class, which will allow you to use the appropriate generics of the right type here:
GoRoute(
path: "/",
builder: (BuildContext context, GoRouterState state) {
return homeBuilder!.completeBuilder(context, state);
},
routes: otherPageRouters,
)
class RouterWidgetBuilder<B extends StateStreamableSource>{
final B Function(BuildContext context) create;
...
Widget completeBuilder(BuildContext context, GoRouterState state){
return BlocProvider<B>(
create: create,
child: builder(context, state),
);
}
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。


评论