@@ -18,11 +18,11 @@ class SourcesFilterBloc extends Bloc<SourcesFilterEvent, SourcesFilterState> {
18
18
super (const SourcesFilterState ()) {
19
19
on < LoadSourceFilterData > (_onLoadSourceFilterData);
20
20
on < CountryCapsuleToggled > (_onCountryCapsuleToggled);
21
- on < AllSourceTypesCapsuleToggled > (_onAllSourceTypesCapsuleToggled); // Added
21
+ on < AllSourceTypesCapsuleToggled > (_onAllSourceTypesCapsuleToggled);
22
22
on < SourceTypeCapsuleToggled > (_onSourceTypeCapsuleToggled);
23
23
on < SourceCheckboxToggled > (_onSourceCheckboxToggled);
24
24
on < ClearSourceFiltersRequested > (_onClearSourceFiltersRequested);
25
- on < _FetchFilteredSourcesRequested > (_onFetchFilteredSourcesRequested);
25
+ // Removed _FetchFilteredSourcesRequested event listener
26
26
}
27
27
28
28
final HtDataRepository <Source > _sourcesRepository;
@@ -40,32 +40,35 @@ class SourcesFilterBloc extends Bloc<SourcesFilterEvent, SourcesFilterState> {
40
40
final initialSelectedSourceIds =
41
41
event.initialSelectedSources.map ((s) => s.id).toSet ();
42
42
43
- // Initialize selected capsules based on initialSelectedSources
44
- final initialSelectedCountryIsoCodes = < String > {};
45
- final initialSelectedSourceTypes = < SourceType > {};
46
-
47
- if (event.initialSelectedSources.isNotEmpty) {
48
- for (final source in event.initialSelectedSources) {
49
- if (source.headquarters? .isoCode != null ) {
50
- initialSelectedCountryIsoCodes.add (source.headquarters! .isoCode);
51
- }
52
- if (source.sourceType != null ) {
53
- initialSelectedSourceTypes.add (source.sourceType! );
54
- }
55
- }
56
- }
43
+ // Use the passed-in initial capsule selections directly
44
+ final initialSelectedCountryIsoCodes =
45
+ event.initialSelectedCountryIsoCodes;
46
+ final initialSelectedSourceTypes = event.initialSelectedSourceTypes;
47
+
48
+ final allSourcesResponse = await _sourcesRepository.readAll ();
49
+ final allAvailableSources = allSourcesResponse.items;
50
+
51
+ // Initially, display all sources. Capsules are visually set but don't filter the list yet.
52
+ // Filtering will occur if a capsule is manually toggled.
53
+ // However, if initial capsule filters ARE provided, we should respect them for the initial display.
54
+ final displayableSources = _getFilteredSources (
55
+ allSources: allAvailableSources,
56
+ selectedCountries: initialSelectedCountryIsoCodes, // Use event's data
57
+ selectedTypes: initialSelectedSourceTypes, // Use event's data
58
+ );
57
59
58
60
emit (
59
61
state.copyWith (
60
62
availableCountries: availableCountries.items,
63
+ allAvailableSources: allAvailableSources,
64
+ displayableSources: displayableSources, // Now correctly filtered if initial capsules were set
61
65
finallySelectedSourceIds: initialSelectedSourceIds,
62
- selectedCountryIsoCodes: initialSelectedCountryIsoCodes,
63
- selectedSourceTypes: initialSelectedSourceTypes,
64
- // Keep loading status until sources are fetched
66
+ selectedCountryIsoCodes: initialSelectedCountryIsoCodes, // Use event's data
67
+ selectedSourceTypes: initialSelectedSourceTypes, // Use event's data
68
+ dataLoadingStatus: SourceFilterDataLoadingStatus .success,
69
+ clearErrorMessage: true ,
65
70
),
66
71
);
67
- // Trigger initial fetch of displayable sources
68
- add (const _FetchFilteredSourcesRequested ());
69
72
} catch (e) {
70
73
emit (
71
74
state.copyWith (
@@ -95,34 +98,57 @@ class SourcesFilterBloc extends Bloc<SourcesFilterEvent, SourcesFilterState> {
95
98
currentSelected.add (event.countryIsoCode);
96
99
}
97
100
}
98
- emit (state.copyWith (selectedCountryIsoCodes: currentSelected));
99
- add (const _FetchFilteredSourcesRequested ());
101
+ final newDisplayableSources = _getFilteredSources (
102
+ allSources: state.allAvailableSources,
103
+ selectedCountries: currentSelected,
104
+ selectedTypes: state.selectedSourceTypes,
105
+ );
106
+ emit (
107
+ state.copyWith (
108
+ selectedCountryIsoCodes: currentSelected,
109
+ displayableSources: newDisplayableSources,
110
+ ),
111
+ );
100
112
}
101
113
102
- Future < void > _onAllSourceTypesCapsuleToggled (
114
+ void _onAllSourceTypesCapsuleToggled (
103
115
AllSourceTypesCapsuleToggled event,
104
116
Emitter <SourcesFilterState > emit,
105
- ) async {
106
- // Toggling "All" for source types means clearing any specific selections.
107
- // If already clear, it remains clear.
108
- emit (state.copyWith (selectedSourceTypes: {}));
109
- add (const _FetchFilteredSourcesRequested ());
117
+ ) {
118
+ final newDisplayableSources = _getFilteredSources (
119
+ allSources: state.allAvailableSources,
120
+ selectedCountries: state.selectedCountryIsoCodes,
121
+ selectedTypes: {}, // Cleared source types
122
+ );
123
+ emit (
124
+ state.copyWith (
125
+ selectedSourceTypes: {},
126
+ displayableSources: newDisplayableSources,
127
+ ),
128
+ );
110
129
}
111
130
112
- Future < void > _onSourceTypeCapsuleToggled (
131
+ void _onSourceTypeCapsuleToggled (
113
132
SourceTypeCapsuleToggled event,
114
133
Emitter <SourcesFilterState > emit,
115
- ) async {
134
+ ) {
116
135
final currentSelected = Set <SourceType >.from (state.selectedSourceTypes);
117
136
if (currentSelected.contains (event.sourceType)) {
118
137
currentSelected.remove (event.sourceType);
119
138
} else {
120
139
currentSelected.add (event.sourceType);
121
140
}
122
- // If specific types are selected, "All" is no longer true.
123
- // The UI will derive "All" state from selectedSourceTypes.isEmpty
124
- emit (state.copyWith (selectedSourceTypes: currentSelected));
125
- add (const _FetchFilteredSourcesRequested ());
141
+ final newDisplayableSources = _getFilteredSources (
142
+ allSources: state.allAvailableSources,
143
+ selectedCountries: state.selectedCountryIsoCodes,
144
+ selectedTypes: currentSelected,
145
+ );
146
+ emit (
147
+ state.copyWith (
148
+ selectedSourceTypes: currentSelected,
149
+ displayableSources: newDisplayableSources,
150
+ ),
151
+ );
126
152
}
127
153
128
154
void _onSourceCheckboxToggled (
@@ -147,55 +173,31 @@ class SourcesFilterBloc extends Bloc<SourcesFilterEvent, SourcesFilterState> {
147
173
selectedCountryIsoCodes: {},
148
174
selectedSourceTypes: {},
149
175
finallySelectedSourceIds: {},
150
- // Keep availableCountries and availableSourceTypes
151
- ),
152
- );
153
- add (const _FetchFilteredSourcesRequested ());
154
- }
155
-
156
- Future <void > _onFetchFilteredSourcesRequested (
157
- _FetchFilteredSourcesRequested event,
158
- Emitter <SourcesFilterState > emit,
159
- ) async {
160
- emit (
161
- state.copyWith (
162
- dataLoadingStatus: SourceFilterDataLoadingStatus .loading,
163
- displayableSources: [], // Clear previous sources
176
+ displayableSources: List .from (state.allAvailableSources), // Reset
177
+ dataLoadingStatus: SourceFilterDataLoadingStatus .success,
164
178
clearErrorMessage: true ,
165
179
),
166
180
);
167
- try {
168
- final queryParameters = < String , dynamic > {};
169
- if (state.selectedCountryIsoCodes.isNotEmpty) {
170
- queryParameters['countries' ] = state.selectedCountryIsoCodes.join (',' );
171
- }
172
- if (state.selectedSourceTypes.isNotEmpty) {
173
- queryParameters['sourceTypes' ] = state.selectedSourceTypes
174
- .map ((st) => st.name)
175
- .join (',' );
176
- }
181
+ }
177
182
178
- final response = await _sourcesRepository.readAllByQuery (queryParameters);
179
- emit (
180
- state.copyWith (
181
- displayableSources: response.items,
182
- dataLoadingStatus: SourceFilterDataLoadingStatus .success,
183
- ),
184
- );
185
- } on HtHttpException catch (e) {
186
- emit (
187
- state.copyWith (
188
- dataLoadingStatus: SourceFilterDataLoadingStatus .failure,
189
- errorMessage: e.message,
190
- ),
191
- );
192
- } catch (e) {
193
- emit (
194
- state.copyWith (
195
- dataLoadingStatus: SourceFilterDataLoadingStatus .failure,
196
- errorMessage: 'An unexpected error occurred while fetching sources.' ,
197
- ),
198
- );
183
+ // Helper method to filter sources based on selected countries and types
184
+ List <Source > _getFilteredSources ({
185
+ required List <Source > allSources,
186
+ required Set <String > selectedCountries,
187
+ required Set <SourceType > selectedTypes,
188
+ }) {
189
+ if (selectedCountries.isEmpty && selectedTypes.isEmpty) {
190
+ return List .from (allSources); // Return all if no filters
199
191
}
192
+
193
+ return allSources.where ((source) {
194
+ final matchesCountry = selectedCountries.isEmpty ||
195
+ (source.headquarters != null &&
196
+ selectedCountries.contains (source.headquarters! .isoCode));
197
+ final matchesType = selectedTypes.isEmpty ||
198
+ (source.sourceType != null &&
199
+ selectedTypes.contains (source.sourceType! ));
200
+ return matchesCountry && matchesType;
201
+ }).toList ();
200
202
}
201
203
}
0 commit comments