Browse Source

refactor(neon): generalize OptionsCollection

Signed-off-by: Nikolas Rimikis <rimikis.nikolas@gmail.com>
pull/497/head
Nikolas Rimikis 1 year ago
parent
commit
d97c9f80fa
No known key found for this signature in database
GPG Key ID: 85ED1DE9786A4FF2
  1. 2
      packages/neon/neon/lib/settings.dart
  2. 2
      packages/neon/neon/lib/src/blocs/apps.dart
  3. 2
      packages/neon/neon/lib/src/models/app_implementation.dart
  4. 2
      packages/neon/neon/lib/src/models/notifications_interface.dart
  5. 48
      packages/neon/neon/lib/src/settings/models/options_collection.dart
  6. 21
      packages/neon/neon/lib/src/utils/account_options.dart
  7. 43
      packages/neon/neon/lib/src/utils/global_options.dart
  8. 2
      packages/neon/neon/lib/src/utils/settings_export_helper.dart

2
packages/neon/neon/lib/settings.dart

@ -1,6 +1,6 @@
export 'package:neon/src/models/label_builder.dart'; export 'package:neon/src/models/label_builder.dart';
export 'package:neon/src/settings/models/nextcloud_app_options.dart';
export 'package:neon/src/settings/models/options_category.dart'; export 'package:neon/src/settings/models/options_category.dart';
export 'package:neon/src/settings/models/options_collection.dart';
export 'package:neon/src/settings/models/select_option.dart'; export 'package:neon/src/settings/models/select_option.dart';
export 'package:neon/src/settings/models/storage.dart' show Storable; export 'package:neon/src/settings/models/storage.dart' show Storable;
export 'package:neon/src/settings/models/toggle_option.dart'; export 'package:neon/src/settings/models/toggle_option.dart';

2
packages/neon/neon/lib/src/blocs/apps.dart

@ -10,7 +10,7 @@ import 'package:neon/src/models/account.dart';
import 'package:neon/src/models/app_ids.dart'; import 'package:neon/src/models/app_ids.dart';
import 'package:neon/src/models/app_implementation.dart'; import 'package:neon/src/models/app_implementation.dart';
import 'package:neon/src/models/notifications_interface.dart'; import 'package:neon/src/models/notifications_interface.dart';
import 'package:neon/src/settings/models/nextcloud_app_options.dart'; import 'package:neon/src/settings/models/options_collection.dart';
import 'package:neon/src/utils/request_manager.dart'; import 'package:neon/src/utils/request_manager.dart';
import 'package:nextcloud/nextcloud.dart'; import 'package:nextcloud/nextcloud.dart';
import 'package:provider/provider.dart'; import 'package:provider/provider.dart';

2
packages/neon/neon/lib/src/models/app_implementation.dart

@ -7,7 +7,7 @@ import 'package:neon/l10n/localizations.dart';
import 'package:neon/src/bloc/bloc.dart'; import 'package:neon/src/bloc/bloc.dart';
import 'package:neon/src/blocs/accounts.dart'; import 'package:neon/src/blocs/accounts.dart';
import 'package:neon/src/models/account.dart'; import 'package:neon/src/models/account.dart';
import 'package:neon/src/settings/models/nextcloud_app_options.dart'; import 'package:neon/src/settings/models/options_collection.dart';
import 'package:neon/src/settings/models/storage.dart'; import 'package:neon/src/settings/models/storage.dart';
import 'package:neon/src/widgets/drawer_destination.dart'; import 'package:neon/src/widgets/drawer_destination.dart';
import 'package:provider/provider.dart'; import 'package:provider/provider.dart';

2
packages/neon/neon/lib/src/models/notifications_interface.dart

@ -1,7 +1,7 @@
import 'package:meta/meta.dart'; import 'package:meta/meta.dart';
import 'package:neon/src/bloc/bloc.dart'; import 'package:neon/src/bloc/bloc.dart';
import 'package:neon/src/models/app_implementation.dart'; import 'package:neon/src/models/app_implementation.dart';
import 'package:neon/src/settings/models/nextcloud_app_options.dart'; import 'package:neon/src/settings/models/options_collection.dart';
abstract interface class NotificationsAppInterface<T extends NotificationsBlocInterface, abstract interface class NotificationsAppInterface<T extends NotificationsBlocInterface,
R extends NotificationsOptionsInterface> extends AppImplementation<T, R> { R extends NotificationsOptionsInterface> extends AppImplementation<T, R> {

48
packages/neon/neon/lib/src/settings/models/options_collection.dart

@ -0,0 +1,48 @@
import 'package:meta/meta.dart';
import 'package:neon/src/settings/models/option.dart';
import 'package:neon/src/settings/models/options_category.dart';
import 'package:neon/src/settings/models/storage.dart';
/// Collection of [Option]s.
abstract class OptionsCollection {
OptionsCollection(this.storage);
/// Storage backend to use.
@protected
final SettingsStorage storage;
/// Collection of options.
@protected
Iterable<Option> get options;
/// Resets all [options].
///
/// Implementers extending this must call super.
@mustCallSuper
void reset() {
for (final option in options) {
option.reset();
}
}
/// Disposes all [options].
///
/// Implementers extending this must call super.
@mustCallSuper
void dispose() {
for (final option in options) {
option.dispose();
}
}
}
/// OpptionsCollection for a neon app.
abstract class NextcloudAppOptions extends OptionsCollection {
NextcloudAppOptions(super.storage);
/// Collection of categories to display the options in the settings.
late final Iterable<OptionsCategory> categories;
@override
late final Iterable<Option> options;
}

21
packages/neon/neon/lib/src/utils/account_options.dart

@ -2,14 +2,15 @@ import 'package:meta/meta.dart';
import 'package:neon/l10n/localizations.dart'; import 'package:neon/l10n/localizations.dart';
import 'package:neon/src/blocs/apps.dart'; import 'package:neon/src/blocs/apps.dart';
import 'package:neon/src/settings/models/option.dart'; import 'package:neon/src/settings/models/option.dart';
import 'package:neon/src/settings/models/options_collection.dart';
import 'package:neon/src/settings/models/select_option.dart'; import 'package:neon/src/settings/models/select_option.dart';
import 'package:neon/src/settings/models/storage.dart'; import 'package:neon/src/settings/models/storage.dart';
@internal @internal
@immutable @immutable
class AccountSpecificOptions { class AccountSpecificOptions extends OptionsCollection {
AccountSpecificOptions( AccountSpecificOptions(
this._storage, super.storage,
this._appsBloc, this._appsBloc,
) { ) {
_appsBloc.appImplementations.listen((final result) { _appsBloc.appImplementations.listen((final result) {
@ -26,27 +27,15 @@ class AccountSpecificOptions {
}); });
} }
final AppStorage _storage;
final AppsBloc _appsBloc; final AppsBloc _appsBloc;
@override
late final List<Option> options = [ late final List<Option> options = [
initialApp, initialApp,
]; ];
void reset() {
for (final option in options) {
option.reset();
}
}
void dispose() {
for (final option in options) {
option.dispose();
}
}
late final initialApp = SelectOption<String?>( late final initialApp = SelectOption<String?>(
storage: _storage, storage: storage,
key: AccountOptionKeys.initialApp, key: AccountOptionKeys.initialApp,
label: (final context) => AppLocalizations.of(context).accountOptionsInitialApp, label: (final context) => AppLocalizations.of(context).accountOptionsInitialApp,
defaultValue: null, defaultValue: null,

43
packages/neon/neon/lib/src/utils/global_options.dart

@ -1,4 +1,3 @@
import 'dart:async';
import 'dart:io'; import 'dart:io';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
@ -6,6 +5,7 @@ import 'package:meta/meta.dart';
import 'package:neon/l10n/localizations.dart'; import 'package:neon/l10n/localizations.dart';
import 'package:neon/src/models/account.dart'; import 'package:neon/src/models/account.dart';
import 'package:neon/src/settings/models/option.dart'; import 'package:neon/src/settings/models/option.dart';
import 'package:neon/src/settings/models/options_collection.dart';
import 'package:neon/src/settings/models/select_option.dart'; import 'package:neon/src/settings/models/select_option.dart';
import 'package:neon/src/settings/models/storage.dart'; import 'package:neon/src/settings/models/storage.dart';
import 'package:neon/src/settings/models/toggle_option.dart'; import 'package:neon/src/settings/models/toggle_option.dart';
@ -16,10 +16,10 @@ const unifiedPushNextPushID = 'org.unifiedpush.distributor.nextpush';
@internal @internal
@immutable @immutable
class GlobalOptions { class GlobalOptions extends OptionsCollection {
GlobalOptions( GlobalOptions(
this._packageInfo, this._packageInfo,
) { ) : super(const AppStorage(StorageKeys.global)) {
pushNotificationsEnabled.addListener(_pushNotificationsEnabledListener); pushNotificationsEnabled.addListener(_pushNotificationsEnabledListener);
rememberLastUsedAccount.addListener(_rememberLastUsedAccountListener); rememberLastUsedAccount.addListener(_rememberLastUsedAccountListener);
} }
@ -49,7 +49,6 @@ class GlobalOptions {
} }
} }
late final AppStorage _storage = const AppStorage(StorageKeys.global);
final PackageInfo _packageInfo; final PackageInfo _packageInfo;
late final _distributorsMap = <String, String Function(BuildContext)>{ late final _distributorsMap = <String, String Function(BuildContext)>{
@ -68,6 +67,7 @@ class GlobalOptions {
AppLocalizations.of(context).globalOptionsPushNotificationsDistributorNoProvider2Push, AppLocalizations.of(context).globalOptionsPushNotificationsDistributorNoProvider2Push,
}; };
@override
late final List<Option> options = [ late final List<Option> options = [
themeMode, themeMode,
themeOLEDAsDark, themeOLEDAsDark,
@ -83,16 +83,9 @@ class GlobalOptions {
navigationMode, navigationMode,
]; ];
void reset() { @override
for (final option in options) {
option.reset();
}
}
void dispose() { void dispose() {
for (final option in options) { super.dispose();
option.dispose();
}
pushNotificationsEnabled.removeListener(_pushNotificationsEnabledListener); pushNotificationsEnabled.removeListener(_pushNotificationsEnabledListener);
rememberLastUsedAccount.removeListener(_rememberLastUsedAccountListener); rememberLastUsedAccount.removeListener(_rememberLastUsedAccountListener);
@ -124,7 +117,7 @@ class GlobalOptions {
} }
late final themeMode = SelectOption<ThemeMode>( late final themeMode = SelectOption<ThemeMode>(
storage: _storage, storage: storage,
key: GlobalOptionKeys.themeMode, key: GlobalOptionKeys.themeMode,
label: (final context) => AppLocalizations.of(context).globalOptionsThemeMode, label: (final context) => AppLocalizations.of(context).globalOptionsThemeMode,
defaultValue: ThemeMode.system, defaultValue: ThemeMode.system,
@ -136,28 +129,28 @@ class GlobalOptions {
); );
late final themeOLEDAsDark = ToggleOption( late final themeOLEDAsDark = ToggleOption(
storage: _storage, storage: storage,
key: GlobalOptionKeys.themeOledAsDark, key: GlobalOptionKeys.themeOledAsDark,
label: (final context) => AppLocalizations.of(context).globalOptionsThemeOLEDAsDark, label: (final context) => AppLocalizations.of(context).globalOptionsThemeOLEDAsDark,
defaultValue: false, defaultValue: false,
); );
late final themeKeepOriginalAccentColor = ToggleOption( late final themeKeepOriginalAccentColor = ToggleOption(
storage: _storage, storage: storage,
key: GlobalOptionKeys.themeKeepOriginalAccentColor, key: GlobalOptionKeys.themeKeepOriginalAccentColor,
label: (final context) => AppLocalizations.of(context).globalOptionsThemeKeepOriginalAccentColor, label: (final context) => AppLocalizations.of(context).globalOptionsThemeKeepOriginalAccentColor,
defaultValue: false, defaultValue: false,
); );
late final pushNotificationsEnabled = ToggleOption( late final pushNotificationsEnabled = ToggleOption(
storage: _storage, storage: storage,
key: GlobalOptionKeys.pushNotificationsEnabled, key: GlobalOptionKeys.pushNotificationsEnabled,
label: (final context) => AppLocalizations.of(context).globalOptionsPushNotificationsEnabled, label: (final context) => AppLocalizations.of(context).globalOptionsPushNotificationsEnabled,
defaultValue: false, defaultValue: false,
); );
late final pushNotificationsDistributor = SelectOption<String?>.depend( late final pushNotificationsDistributor = SelectOption<String?>.depend(
storage: _storage, storage: storage,
key: GlobalOptionKeys.pushNotificationsDistributor, key: GlobalOptionKeys.pushNotificationsDistributor,
label: (final context) => AppLocalizations.of(context).globalOptionsPushNotificationsDistributor, label: (final context) => AppLocalizations.of(context).globalOptionsPushNotificationsDistributor,
defaultValue: null, defaultValue: null,
@ -166,14 +159,14 @@ class GlobalOptions {
); );
late final startupMinimized = ToggleOption( late final startupMinimized = ToggleOption(
storage: _storage, storage: storage,
key: GlobalOptionKeys.startupMinimized, key: GlobalOptionKeys.startupMinimized,
label: (final context) => AppLocalizations.of(context).globalOptionsStartupMinimized, label: (final context) => AppLocalizations.of(context).globalOptionsStartupMinimized,
defaultValue: false, defaultValue: false,
); );
late final startupMinimizeInsteadOfExit = ToggleOption( late final startupMinimizeInsteadOfExit = ToggleOption(
storage: _storage, storage: storage,
key: GlobalOptionKeys.startupMinimizeInsteadOfExit, key: GlobalOptionKeys.startupMinimizeInsteadOfExit,
label: (final context) => AppLocalizations.of(context).globalOptionsStartupMinimizeInsteadOfExit, label: (final context) => AppLocalizations.of(context).globalOptionsStartupMinimizeInsteadOfExit,
defaultValue: false, defaultValue: false,
@ -182,14 +175,14 @@ class GlobalOptions {
// TODO: Autostart option // TODO: Autostart option
late final systemTrayEnabled = ToggleOption( late final systemTrayEnabled = ToggleOption(
storage: _storage, storage: storage,
key: GlobalOptionKeys.systemtrayEnabled, key: GlobalOptionKeys.systemtrayEnabled,
label: (final context) => AppLocalizations.of(context).globalOptionsSystemTrayEnabled, label: (final context) => AppLocalizations.of(context).globalOptionsSystemTrayEnabled,
defaultValue: false, defaultValue: false,
); );
late final systemTrayHideToTrayWhenMinimized = ToggleOption.depend( late final systemTrayHideToTrayWhenMinimized = ToggleOption.depend(
storage: _storage, storage: storage,
key: GlobalOptionKeys.systemtrayHideToTrayWhenMinimized, key: GlobalOptionKeys.systemtrayHideToTrayWhenMinimized,
label: (final context) => AppLocalizations.of(context).globalOptionsSystemTrayHideToTrayWhenMinimized, label: (final context) => AppLocalizations.of(context).globalOptionsSystemTrayHideToTrayWhenMinimized,
defaultValue: true, defaultValue: true,
@ -197,14 +190,14 @@ class GlobalOptions {
); );
late final rememberLastUsedAccount = ToggleOption( late final rememberLastUsedAccount = ToggleOption(
storage: _storage, storage: storage,
key: GlobalOptionKeys.rememberLastUsedAccount, key: GlobalOptionKeys.rememberLastUsedAccount,
label: (final context) => AppLocalizations.of(context).globalOptionsAccountsRememberLastUsedAccount, label: (final context) => AppLocalizations.of(context).globalOptionsAccountsRememberLastUsedAccount,
defaultValue: true, defaultValue: true,
); );
late final initialAccount = SelectOption<String?>( late final initialAccount = SelectOption<String?>(
storage: _storage, storage: storage,
key: GlobalOptionKeys.initialAccount, key: GlobalOptionKeys.initialAccount,
label: (final context) => AppLocalizations.of(context).globalOptionsAccountsInitialAccount, label: (final context) => AppLocalizations.of(context).globalOptionsAccountsInitialAccount,
defaultValue: null, defaultValue: null,
@ -212,7 +205,7 @@ class GlobalOptions {
); );
late final navigationMode = SelectOption<NavigationMode>( late final navigationMode = SelectOption<NavigationMode>(
storage: _storage, storage: storage,
key: GlobalOptionKeys.navigationMode, key: GlobalOptionKeys.navigationMode,
label: (final context) => AppLocalizations.of(context).globalOptionsNavigationMode, label: (final context) => AppLocalizations.of(context).globalOptionsNavigationMode,
defaultValue: Platform.isAndroid || Platform.isIOS ? NavigationMode.drawer : NavigationMode.drawerAlwaysVisible, defaultValue: Platform.isAndroid || Platform.isIOS ? NavigationMode.drawer : NavigationMode.drawerAlwaysVisible,

2
packages/neon/neon/lib/src/utils/settings_export_helper.dart

@ -50,7 +50,7 @@ class SettingsExportHelper {
} }
} }
Future _applyOptionsMapToOptions(final List<Option> options, final Map<String, dynamic> data) async { Future _applyOptionsMapToOptions(final Iterable<Option> options, final Map<String, dynamic> data) async {
for (final optionKey in data.keys) { for (final optionKey in data.keys) {
for (final option in options) { for (final option in options) {
if (option.key.value == optionKey) { if (option.key.value == optionKey) {

Loading…
Cancel
Save