Skip to content

Commit 192ea6a

Browse files
committed
feat(app_configuration): add push notification settings form
- Implement PushNotificationSettingsForm widget for configuring push notification settings - Add system status, primary provider, and delivery types configuration sections - Use ExpansionTile for collapsible sections - Implement SwitchListTile and SegmentedButton for user interactions - Localize all strings using AppLocalizations
1 parent 7a332b6 commit 192ea6a

File tree

1 file changed

+188
-0
lines changed

1 file changed

+188
-0
lines changed
Lines changed: 188 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,188 @@
1+
import 'package:core/core.dart';
2+
import 'package:flutter/material.dart';
3+
import 'package:flutter_news_app_web_dashboard_full_source_code/l10n/l10n.dart';
4+
import 'package:flutter_news_app_web_dashboard_full_source_code/shared/extensions/push_notification_provider_l10n.dart';
5+
import 'package:flutter_news_app_web_dashboard_full_source_code/shared/extensions/push_notification_subscription_delivery_type_l10n.dart';
6+
import 'package:ui_kit/ui_kit.dart';
7+
8+
/// {@template push_notification_settings_form}
9+
/// A form widget for configuring push notification settings.
10+
/// {@endtemplate}
11+
class PushNotificationSettingsForm extends StatelessWidget {
12+
/// {@macro push_notification_settings_form}
13+
const PushNotificationSettingsForm({
14+
required this.remoteConfig,
15+
required this.onConfigChanged,
16+
super.key,
17+
});
18+
19+
/// The current [RemoteConfig] object.
20+
final RemoteConfig remoteConfig;
21+
22+
/// Callback to notify parent of changes to the [RemoteConfig].
23+
final ValueChanged<RemoteConfig> onConfigChanged;
24+
25+
@override
26+
Widget build(BuildContext context) {
27+
final l10n = AppLocalizationsX(context).l10n;
28+
final pushConfig = remoteConfig.pushNotificationConfig;
29+
30+
return SingleChildScrollView(
31+
padding: const EdgeInsets.all(AppSpacing.lg),
32+
child: Column(
33+
crossAxisAlignment: CrossAxisAlignment.start,
34+
children: [
35+
ExpansionTile(
36+
initiallyExpanded: true,
37+
title: Text(l10n.pushNotificationSettingsTitle),
38+
childrenPadding: const EdgeInsetsDirectional.only(
39+
start: AppSpacing.lg,
40+
top: AppSpacing.md,
41+
bottom: AppSpacing.md,
42+
),
43+
expandedCrossAxisAlignment: CrossAxisAlignment.start,
44+
children: [
45+
Text(
46+
l10n.pushNotificationSettingsDescription,
47+
style: Theme.of(context).textTheme.bodySmall?.copyWith(
48+
color: Theme.of(
49+
context,
50+
).colorScheme.onSurface.withOpacity(0.7),
51+
),
52+
),
53+
const SizedBox(height: AppSpacing.lg),
54+
_buildSystemStatusSection(context, l10n, pushConfig),
55+
const SizedBox(height: AppSpacing.lg),
56+
_buildPrimaryProviderSection(context, l10n, pushConfig),
57+
const SizedBox(height: AppSpacing.lg),
58+
_buildDeliveryTypesSection(context, l10n, pushConfig),
59+
],
60+
),
61+
],
62+
),
63+
);
64+
}
65+
66+
Widget _buildSystemStatusSection(
67+
BuildContext context,
68+
AppLocalizations l10n,
69+
PushNotificationConfig pushConfig,
70+
) {
71+
return ExpansionTile(
72+
title: Text(l10n.pushNotificationSystemStatusTitle),
73+
childrenPadding: const EdgeInsets.symmetric(
74+
horizontal: AppSpacing.lg,
75+
vertical: AppSpacing.md,
76+
),
77+
children: [
78+
SwitchListTile(
79+
title: Text(l10n.enabledLabel),
80+
subtitle: Text(l10n.pushNotificationSystemStatusDescription),
81+
value: pushConfig.enabled,
82+
onChanged: (value) {
83+
onConfigChanged(
84+
remoteConfig.copyWith(
85+
pushNotificationConfig: pushConfig.copyWith(enabled: value),
86+
),
87+
);
88+
},
89+
),
90+
],
91+
);
92+
}
93+
94+
Widget _buildPrimaryProviderSection(
95+
BuildContext context,
96+
AppLocalizations l10n,
97+
PushNotificationConfig pushConfig,
98+
) {
99+
return ExpansionTile(
100+
title: Text(l10n.pushNotificationPrimaryProviderTitle),
101+
childrenPadding: const EdgeInsets.symmetric(
102+
horizontal: AppSpacing.lg,
103+
vertical: AppSpacing.md,
104+
),
105+
expandedCrossAxisAlignment: CrossAxisAlignment.start,
106+
children: [
107+
Text(
108+
l10n.pushNotificationPrimaryProviderDescription,
109+
style: Theme.of(context).textTheme.bodySmall?.copyWith(
110+
color: Theme.of(context).colorScheme.onSurface.withOpacity(0.7),
111+
),
112+
),
113+
const SizedBox(height: AppSpacing.lg),
114+
SegmentedButton<PushNotificationProvider>(
115+
segments: PushNotificationProvider.values
116+
.map(
117+
(provider) => ButtonSegment<PushNotificationProvider>(
118+
value: provider,
119+
label: Text(provider.l10n(context)),
120+
),
121+
)
122+
.toList(),
123+
selected: {pushConfig.primaryProvider},
124+
onSelectionChanged: (newSelection) {
125+
onConfigChanged(
126+
remoteConfig.copyWith(
127+
pushNotificationConfig: pushConfig.copyWith(
128+
primaryProvider: newSelection.first,
129+
),
130+
),
131+
);
132+
},
133+
),
134+
],
135+
);
136+
}
137+
138+
Widget _buildDeliveryTypesSection(
139+
BuildContext context,
140+
AppLocalizations l10n,
141+
PushNotificationConfig pushConfig,
142+
) {
143+
return ExpansionTile(
144+
title: Text(l10n.pushNotificationDeliveryTypesTitle),
145+
childrenPadding: const EdgeInsets.symmetric(
146+
horizontal: AppSpacing.lg,
147+
vertical: AppSpacing.md,
148+
),
149+
expandedCrossAxisAlignment: CrossAxisAlignment.start,
150+
children: [
151+
Text(
152+
l10n.pushNotificationDeliveryTypesDescription,
153+
style: Theme.of(context).textTheme.bodySmall?.copyWith(
154+
color: Theme.of(context).colorScheme.onSurface.withOpacity(0.7),
155+
),
156+
),
157+
const SizedBox(height: AppSpacing.lg),
158+
Column(
159+
children: PushNotificationSubscriptionDeliveryType.values
160+
.map(
161+
(type) => SwitchListTile(
162+
title: Text(type.l10n(context)),
163+
value: pushConfig.deliveryConfigs[type] ?? false,
164+
onChanged: (value) {
165+
final newDeliveryConfigs =
166+
Map<
167+
PushNotificationSubscriptionDeliveryType,
168+
bool
169+
>.from(
170+
pushConfig.deliveryConfigs,
171+
);
172+
newDeliveryConfigs[type] = value;
173+
onConfigChanged(
174+
remoteConfig.copyWith(
175+
pushNotificationConfig: pushConfig.copyWith(
176+
deliveryConfigs: newDeliveryConfigs,
177+
),
178+
),
179+
);
180+
},
181+
),
182+
)
183+
.toList(),
184+
),
185+
],
186+
);
187+
}
188+
}

0 commit comments

Comments
 (0)