在 Flutter 中使用 Bloc/Cubit 时绕过 CONTEXT
Posted
技术标签:
【中文标题】在 Flutter 中使用 Bloc/Cubit 时绕过 CONTEXT【英文标题】:Get around of CONTEXT while using Bloc/Cubit in Flutter 【发布时间】:2021-01-06 02:58:27 【问题描述】:我做了一段时间的flutter,一直在使用setState()。最近决定学习BLoC。现在在 v6 中,Bloc 带有 Cubit,因此开始跟进 BLoC-Cubit 的教程,了解它们如何工作以及如何实现。到目前为止,无论我学到什么,我都在一个演示项目中实现了。
我遇到了这个错误:
使用不包含 Cubit 类型的 Cubit 的上下文调用 BlocProvider.of()。
从传递给 BlocProvider.of
() 的上下文开始找不到祖先。 如果您使用的上下文来自 BlocProvider 上方的小部件,则会发生这种情况。
使用的上下文是:BlocConsumer
(dirty)
The relevant error-causing widget was BlocConsumer<Cubit<dynamic>, dynamic>
这会将我重定向到 CreateProfile.dart 行号。 3、查看下方。
我猜这个错误与我没有将正确的上下文传递给 CreateProfile 的 BlocConsumer 的上下文有关。但是,登录和 Otp 页面中的 Bloc 工作正常。
小部件树去:Main->Splash->Login->Otp->CreateProfile.
如果我的不正确,请帮我解决这个问题,并提出正确的 bloc 实施做法。
main.dart
class MyApp extends StatelessWidget
@override
Widget build(BuildContext context)
return MaterialApp(
debugShowCheckedModeBanner: false,
home: Splash(),
routes:
Splash.id : (context) => Splash(),
,
);
飞溅飞镖
FlatButton(
onTap: ()
Navigator.push(context, MaterialPageRoute(builder: (context) => BlocProvider(
create: (context) => LoginCubit(),
child: Login(),)));
,
child: Text('Get Started', style: kText18SemiBold.copyWith(color: Colors.white)),
),
登录.dart
return Scaffold(
backgroundColor: kBackgroundColor,
body: BlocConsumer<LoginCubit, LoginState>(
listener: (context, state)
if(state is LoginApiSuccess)
Navigator.push(context, MaterialPageRoute(builder: (context) => BlocProvider(
create: (context) => OtpCubit(),
child: Otp(),
)));
,
builder: (context, state)
return Stack(
// Contains Login UI
)
)
);
Otp.dart
return Scaffold(
backgroundColor: kBackgroundColor,
body: BlocConsumer<OtpCubit, OtpState>(
listener: (context, state)
if(state is OtpApiSuccess)
Navigator.push(context, MaterialPageRoute(builder: (context) => BlocProvider(
create: (context) => CreateprofileCubit(),
child: CreateProfile(),
)));
,
builder: (context, state)
return Stack(
// Contains OTP UI
)
)
);
CreateProfile.dart
return Scaffold(
backgroundColor: kBackgroundColor,
body: BlocConsumer<CreateprofileCubit, CreateprofileState>( // Error redirects here
listener: (context, state)
if(state is ProfileCreated)
Navigator.push(context, MaterialPageRoute(builder: (context) => AddProfileImages(),));
,
builder: (context, state)
return Stack(
// Contains CreateProfile UI
)
)
);
【问题讨论】:
【参考方案1】:BlocProvider 是一个泛型类,你需要为它提供一个类型。尝试替换:
BlocProvider(
create: (context) => OtpCubit(),
child: Otp(),
)
与:
BlocProvider<OtpCubit>(
create: (context) => OtpCubit(),
child: Otp(),
)
同样的事情适用于您使用的所有其他 BlocProviders。
【讨论】:
谢谢你这工作,但为什么它没有导致登录或 otp 错误?以上是关于在 Flutter 中使用 Bloc/Cubit 时绕过 CONTEXT的主要内容,如果未能解决你的问题,请参考以下文章
Flutter BLoC 库:将 TextEditingController 对象保存在哪里:在 State、BLoC / Cubit 类中还是在小部件中?
Flutter BLoC/Cubit STATE 类最佳实践
具有多个firebase请求的flutter bloc cubit最佳实践
我应该先启动 Cubit,然后再将代码重构为 Bloc 吗?