Learn about flutter MultiBlocProvider with HydratedBLoC. To use them together, we need install them both
flutter_bloc: ^8.1.1
hydrated_bloc: ^8.1.0
Your bloc or cubit must extend HydratedBloc or HydratedCubit to do it. They both need to store data in the device in a directory.
These directories could be created by the app. For this, we need to install another plugin.
path_provider: ^2.0.11
Now let’s take a look at our main() function.
void main() async {
WidgetsFlutterBinding.ensureInitialized();
final storage = await HydratedStorage.build(
storageDirectory: await getApplicationDocumentsDirectory()
);
HydratedBlocOverrides.runZoned(
() => runApp(const WorkoutTime()),
storage: storage
);
}
HydratedStorage.build() creates a directory based on the device (android or iOS) and return the storage path.
The path or directory for storing data is created using
getApplicationDocumentsDirectory()
HydratedBlocOverrides helps you to monitor blocs and states including the storage.
After that we connect our storage and app together.
In this app we wanted to use many BlocProviders. So that’s why we used MultiBlocProvider
MultiBlocProvider(
providers: [
BlocProvider<WorkoutsCubit>(create: (BuildContext context) {
WorkoutsCubit workoutsCubit = WorkoutsCubit();
if (workoutsCubit.state.isEmpty) {
workoutsCubit.getWorkouts();
} else {
}
return workoutsCubit;
}),
BlocProvider<WorkoutCubit>(create: (BuildContext context)=>WorkoutCubit())
],
child: BlocBuilder<WorkoutCubit, WorkoutState>(
builder: (context, state){
if(state is WorkoutInitial){
return const HomePage();
}else if(state is WorkoutEditing){
return EditWorkoutScreen();
}
return Container();
},
)
),
MultiBlocProvider takes a list of providers. So we see like below
MultiBlocProvider(
providers:[
]
)
In the list up, you can put as many BlocProviders as you want. This is also part of DI which is dependency injection.
Of course, inside MultiBlocProvider you need to put the child. Most of the cases the child is another flutter widget BlocBuilder
Complete code
void main() async {
WidgetsFlutterBinding.ensureInitialized();
final storage = await HydratedStorage.build(
storageDirectory: await getApplicationDocumentsDirectory()
);
HydratedBlocOverrides.runZoned(
() => runApp(const WorkoutTime()),
storage: storage
);
}
class WorkoutTime extends StatelessWidget {
const WorkoutTime({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'My Workouts',
theme: ThemeData(
primaryColor: Colors.blue,
textTheme: const TextTheme(
bodyText2: TextStyle(color: Color.fromARGB(255, 66, 74, 96)),
)),
home:
MultiBlocProvider(
providers: [
BlocProvider<WorkoutsCubit>(create: (BuildContext context) {
WorkoutsCubit workoutsCubit = WorkoutsCubit();
if (workoutsCubit.state.isEmpty) {
workoutsCubit.getWorkouts();
} else {
}
return workoutsCubit;
}),
BlocProvider<WorkoutCubit>(create: (BuildContext context)=>WorkoutCubit())
],
child: BlocBuilder<WorkoutCubit, WorkoutState>(
builder: (context, state){
if(state is WorkoutInitial){
return const HomePage();
}else if(state is WorkoutEditing){
return EditWorkoutScreen();
}
return Container();
},
)
),
);
}
}
In the providers list we have many BlocProviders. One of the BlocProviders is extending HydratedBloc.
Flutter BLoC App