======== Exception caught by gesture =============================================================== The following ProviderNotFoundException was thrown while handling a gesture: Error: Could not find the correct Provider above this Test Widget
This happens because you used a BuildContext
that does not include the provider
of your choice. There are a few common scenarios:
You added a new provider in your
main.dart
and performed a hot-reload. To fix, perform a hot-restart.The provider you are trying to read is in a different route.
Providers are "scoped". So if you insert of provider inside a route, then other routes will not be able to access that provider.
You used a
BuildContext
that is an ancestor of the provider you are trying to read.Make sure that Test is under your MultiProvider/Provider. This usually happens when you are creating a provider and trying to read it immediately.
For example, instead of:
Widget build(BuildContext context) { return Provider<Example>( create: (_) => Example(), // Will throw a ProviderNotFoundError, because `context` is associated // to the widget that is the parent of `Provider<Example>` child: Text(context.watch<Example>()), ), }
consider using
builder
like so:Widget build(BuildContext context) { return Provider<Example>( create: (_) => Example(), // we use `builder` to obtain a new `BuildContext` that has access to the provider builder: (context) { // No longer throws return Text(context.watch<Example>()), } ), }
If none of these solutions work, consider asking for help on StackOverflow: https://stackoverflow.com/questions/tagged/flutter
I am building an Widget "Test" to search users by their username. This is the widget Test with Bloc.
class Test extends StatelessWidget {
const Test({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return BlocProvider(
create: (_) => DonorsCubit(),
child: BlocListener<DonorsCubit, DonorsState>(
listener: (context, state) {
print(state);
},
child: Scaffold(
appBar: AppBar(),
body: IconButton(
onPressed: () {
context.read<DonorsCubit>().searchDonors(searchKey: "masum");
},
icon: BlocBuilder<DonorsCubit, DonorsState>(
builder: (context, state) {
if (state is DonorsInitialState) return const Icon(Icons.add);
if (state is DonorsLoadedState) return const Icon(Icons.done);
if (state is DonorsLoadingState) return const Icon(Icons.circle);
return const SizedBox();
},
),
),
),
),
);
}
}
I used this cubit to manage states.
class DonorsCubit extends Cubit<DonorsState> {
List<MyUser> users = <MyUser>[];
final FirebaseDBRepo _firebaseDBRepo = FirebaseDBRepo();
late StreamSubscription _streamSubscription;
DonorsCubit() : super(DonorsInitialState()) {
_streamSubscription =
_firebaseDBRepo.usersStream().listen((List<MyUser> users) {
this.users = users;
});
}
void searchDonors({required String? searchKey}) {
emit(DonorsLoadingState());
List<MyUser> searchedUser = <MyUser>[];
searchedUser.clear();
if (searchKey == null) {
emit(DonorsLoadedState(users: users));
} else {
for (MyUser user in users) {
if (user.username!.toLowerCase().contains(searchKey.toLowerCase())) {
searchedUser.add(user);
}
}
emit(DonorsLoadedState(users: searchedUser));
}
}
@override
Future<void> close() {
_streamSubscription.cancel();
return super.close();
}
}
abstract class DonorsState extends Equatable {
const DonorsState();
}
class DonorsLoadingState extends DonorsState {
@override
List<Object> get props => [];
}
class DonorsInitialState extends DonorsState {
@override
List<Object> get props => [];
}
class DonorsLoadedState extends DonorsState {
final List<MyUser> users;
const DonorsLoadedState({required this.users});
@override
List<Object?> get props => [users];
}