簡體   English   中英

我在使用 Bloc/cubit 在 flutter 的其他小部件/類中使用 BlocBuilder 獲取上次發出的 state 時遇到問題

[英]I am having trouble getting last emitted state with BlocBuilder in other widgets/classes in flutter using Bloc/cubit

我有一個cubit的登錄,它將接受兩個參數,email和密碼。 然后它會要求存儲庫給他該請求的響應。 在調用存儲庫的 function 之前,我發出加載 state,當我從存儲庫收到數據時,發出另一個 state,即 SigninLoaded。 我的登錄Cubit:

final SignInRepository signInRepository;

SigninCubit({required this.signInRepository}) : super(SigninInitial());

Future<void> signIn({String email = '', String password = ''}) async {
  print("Cubit is invoked");
  emit(SigninInLoading());
  Timer(Duration(seconds: 0), () async {
    await signInRepository
        .signIn(email: email, password: password)
        .then((signinModel) {
      // print("SignIn Model is : ${signinModel}");‹‹
      emit(SigninLoaded(signInModel: signinModel));
    });
  });
}
}

登錄狀態

@immutable
abstract class SigninState {}

class SigninInitial extends SigninState {}

class SigninInLoading extends SigninState {}

class SigninLoaded extends SigninState {
  SignInModel? signInModel;
  SigninLoaded({required this.signInModel});
}

這就是我從 LoginPage class 調用我的 signinCubit 的方式。

BlocProvider.of<SigninCubit>(context).signIn(email: email, password: password);

當從 LoginPage class 調用 signinCubit 時,我看到它在同一個 class 中使用 BlocBuilder 的響應;

BlocBuilder<SigninCubit, SigninState>(
        builder: (context, state) {
          if ((state is SigninInitial)) {
            print("Initial State");
          } else if (state is SigninInLoading) {
            return Center(
              child: CircularProgressIndicator(
                color: AppColors.mainColor,
              ),
            );
          } else {
            final signinData = (state as SigninLoaded).signInModel;

            data = signinData;
          }

But when I try to access response or the last emitted state which was SigninLoaded, I get initial state in other class, I tried to get response in Profile class like this;

BlocBuilder<SigninCubit, SigninState>(
                builder: (context, state) {
                  print("State : $state");
                  if (state is SigninLoaded) {
                    name = (state as SigninLoaded).signInModel?.data?.firstName;
                    print("Name $name");
                  }
                  return Text(
                    'Welcome, ${name}!',
                    style: TextStyle(
                      color: Colors.black,
                      fontSize: 20,
                      fontWeight: FontWeight.w800,
                    ),
                  );
                },
              ),

我沒有得到回復,因為它說它在初始 state 中。

即使我也像這樣提供了 Blocs;

BlocProvider 到 LoginPage class;

MaterialPageRoute(
          builder: (_) => BlocProvider(
            create: (BuildContext context) =>
                SigninCubit(signInRepository: signInRepository),
            child: LoginPage(),
          ),
        );

BlocProvider 用於配置 class;

 MaterialPageRoute(
            builder: (_) => BlocProvider(
                  create: (context) =>
                      SigninCubit(signInRepository: signInRepository),
                  child: Profile(),
                ));

可能是我錯了,但在我看來,如果你想在 Profile 頁面中使用 SignInModel,你必須再次調用 signIn function

  • 另一種解決方案:僅將 SignInCubit 的一個 BlocProvider 定義為 Profile 頁面和 SignIn 頁面的父級,例如:

    MaterialPageRoute(builder: (_) => BlocProvider( create: (context) => SigninCubit(signInRepository: signInRepository), child: MyApp(), ));

  • 將signinModel或(登錄信息)保存在本地數據庫中,當我們進入ProfilePage時,從db中獲取

我有一個類似的問題。 我有一個適合我的臨時解決方法,我將emit包裝在 Future.delayed 中,就像這樣

Future.delayed(Duration.zero,()=>emit(<<newState>>));

然后 My BlocBuilder 識別 state 更改。 我不知道為什么,問題是,我的代碼曾經運行良好,然后因看似無關的更改而停止。 希望這會有所幫助,但更重要的是,我希望真正知道發生了什么的人可以告訴我我應該做什么來修復我的代碼:)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM