Невозможно обновить пользовательский интерфейс за пределами виджета, используя шаблон flutter Bloc

#flutter #dart #bloc #stream-builder

#flutter #dart #блок #stream-builder

Вопрос:

Я пробую блок в flutter. Кажется, он отлично работает, например, при вызове блочной функции в виджете с отслеживанием состояния:

  RaisedButton(
 onPressed: () => _nextStep(),
 child: Text("Next"))
  

Это вызовет функцию _nextStep() и обновит пользовательский интерфейс.
Функция NeXTSTEP:

   _nextStep() async {
_bloc.StepEventSink.add(NextStep());
}
  

и я складываю виджет с помощью StreamBuider, и это работает. Но если я вызываю _nextStep() вне класса, данные обновляются, а пользовательский интерфейс — нет. Пример:

 class FormWizard extends StatefulWidget {
  @override
 _FormWizardState createState() => _FormWizardState();
  next() {
_FormWizardState()._nextStep();
  }
 }
  

Как я могу обновить пользовательский интерфейс за пределами виджета?

Комментарии:

1. Итак, что вы предлагаете?

Ответ №1:

Я решил свою проблему, используя управление состоянием поставщика. Я объявил класс SteppBloc и присвоил текущему шагу значение 0. Затем используйте notifyListeners для обновления значения в виджетах, которые его используют.

Класс StepBloc:

 import 'package:flutter/material.dart';

class StepperBloc extends ChangeNotifier {
  int _current = 0;
  int get currentStep => _current;

  set currentStep(int val) {
    _current = val;
    notifyListeners();
  }

  increment() {
    _current  ;
    notifyListeners();
  }

  decrement() {
    _current--;
    notifyListeners();
  }
}
  

Затем я оборачиваю основной виджет с помощью ChangeNotifierProvider из StepperBloc

   @override
  Widget build(BuildContext context) {
    return MultiProvider(
      providers: [
        ChangeNotifierProvider<StepperBloc>.value(value: StepperBloc())
      ],
      child: MaterialApp(
        debugShowCheckedModeBanner: false,
        theme: theme(),
        home: loading(),
        //initialRoute: SplashScreen.routeName,
        routes: routes,
      ),
    );
  }
}