diff --git a/lib/app_theme.dart b/lib/app_theme.dart index 47bdaee..97957db 100644 --- a/lib/app_theme.dart +++ b/lib/app_theme.dart @@ -1,14 +1,36 @@ +import 'package:color_blindness/color_blindness.dart'; +import 'package:color_blindness/color_blindness_color_scheme.dart'; +import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; -class AppTheme { - static ThemeData light = ThemeData( - colorSchemeSeed: Colors.indigo, - useMaterial3: true, - ); +const _seedColor = Colors.indigo; +final _lightScheme = ColorScheme.fromSeed( + seedColor: _seedColor, + brightness: Brightness.light, +); - static ThemeData dark = ThemeData( - colorSchemeSeed: Colors.indigo, +final _darkScheme = ColorScheme.fromSeed( + seedColor: _seedColor, + brightness: Brightness.dark, +); + +ThemeData buildTheme({ + required Brightness brightness, + ColorBlindnessType blindnessType = ColorBlindnessType.none, +}) { + final baseScheme = + brightness == Brightness.light ? _lightScheme : _darkScheme; + late final ColorScheme scheme; + + if (!kReleaseMode && blindnessType != ColorBlindnessType.none) { + scheme = colorBlindnessColorScheme(baseScheme, blindnessType); + } else { + scheme = baseScheme; + } + + return ThemeData( + colorScheme: scheme, + brightness: brightness, useMaterial3: true, - brightness: Brightness.dark, ); } diff --git a/lib/controls/audio_video/media_kit_av_control.dart b/lib/controls/audio_video/media_kit_av_control.dart index 4d0d557..305ccf3 100644 --- a/lib/controls/audio_video/media_kit_av_control.dart +++ b/lib/controls/audio_video/media_kit_av_control.dart @@ -30,7 +30,7 @@ class _MediaKitAvControlState extends State { super.initState(); Future.microtask(() async { _logger.info('initializing'); - controller = await VideoController.create(player.handle); + controller = await VideoController.create(player); _logger.info('initialized'); if (context.mounted) { setState(() {}); diff --git a/lib/main.dart b/lib/main.dart index 3b50dd9..b6b2e32 100644 --- a/lib/main.dart +++ b/lib/main.dart @@ -27,7 +27,7 @@ import 'utils/old_android_letsencrypte_cert.dart'; void main() async { WidgetsFlutterBinding.ensureInitialized(); // await dotenv.load(fileName: '.env'); - const enablePreview = false; + const enablePreview = true; Logger.root.level = Level.FINER; Logger.root.onRecord.listen((event) { final logName = event.loggerName.isEmpty ? 'ROOT' : event.loggerName; @@ -51,6 +51,7 @@ class App extends StatelessWidget { // This widget is the root of your application. @override Widget build(BuildContext context) { + final settingsService = getIt(); return AnimatedBuilder( builder: (context, child) { return Portal( @@ -111,9 +112,15 @@ class App extends StatelessWidget { useInheritedMediaQuery: true, locale: DevicePreview.locale(context), builder: DevicePreview.appBuilder, - theme: AppTheme.light, - darkTheme: AppTheme.dark, - themeMode: getIt().themeMode, + theme: buildTheme( + brightness: Brightness.light, + blindnessType: settingsService.colorBlindnessType, + ), + darkTheme: buildTheme( + brightness: Brightness.dark, + blindnessType: settingsService.colorBlindnessType, + ), + themeMode: settingsService.themeMode, debugShowCheckedModeBanner: false, scrollBehavior: AppScrollingBehavior(), routerDelegate: appRouter.routerDelegate, diff --git a/lib/screens/settings_screen.dart b/lib/screens/settings_screen.dart index f1eea7e..ee36300 100644 --- a/lib/screens/settings_screen.dart +++ b/lib/screens/settings_screen.dart @@ -1,3 +1,5 @@ +import 'package:color_blindness/color_blindness.dart'; +import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:provider/provider.dart'; @@ -20,6 +22,7 @@ class SettingsScreen extends StatelessWidget { children: [ buildLowBandwidthWidget(settings), buildThemeWidget(settings), + if (!kReleaseMode) buildColorBlindnessTestSettings(settings), ], ), ), @@ -55,4 +58,18 @@ class SettingsScreen extends StatelessWidget { ), ); } + + Widget buildColorBlindnessTestSettings(SettingsService settings) { + return ListTile( + title: const Text('Color Blindness Testing'), + trailing: DropdownButton( + value: settings.colorBlindnessType, + items: ColorBlindnessType.values + .map((c) => DropdownMenuItem(value: c, child: Text(c.name))) + .toList(), + onChanged: (value) { + settings.colorBlindnessType = value ?? ColorBlindnessType.none; + }), + ); + } } diff --git a/lib/services/setting_service.dart b/lib/services/setting_service.dart index 58bf0ed..44b0220 100644 --- a/lib/services/setting_service.dart +++ b/lib/services/setting_service.dart @@ -1,3 +1,4 @@ +import 'package:color_blindness/color_blindness.dart'; import 'package:flutter/material.dart'; import 'package:shared_preferences/shared_preferences.dart'; @@ -29,6 +30,16 @@ class SettingsService extends ChangeNotifier { notifyListeners(); } + ColorBlindnessType _colorBlindnessType = ColorBlindnessType.none; + + ColorBlindnessType get colorBlindnessType => _colorBlindnessType; + + set colorBlindnessType(ColorBlindnessType type) { + _colorBlindnessType = type; + _prefs.setString(_colorBlindnessTestingModeKey, type.name); + notifyListeners(); + } + Future initialize() async { if (_initialized) { return; @@ -36,9 +47,22 @@ class SettingsService extends ChangeNotifier { _prefs = await SharedPreferences.getInstance(); _lowBandwidthMode = _prefs.getBool(_lowBandwidthModeKey) ?? false; _themeMode = ThemeModeExtensions.parse(_prefs.getString(_themeModeKey)); + _colorBlindnessType = _colorBlindnessTypeFromPrefs(_prefs); _initialized = true; } } const _lowBandwidthModeKey = 'LowBandwidthMode'; const _themeModeKey = 'ThemeMode'; +const _colorBlindnessTestingModeKey = 'ColorBlindnessTestingMode'; + +ColorBlindnessType _colorBlindnessTypeFromPrefs(SharedPreferences prefs) { + final cbString = prefs.getString(_colorBlindnessTestingModeKey); + if (cbString?.isEmpty ?? true) { + return ColorBlindnessType.none; + } + return ColorBlindnessType.values.firstWhere( + (c) => c.name == cbString, + orElse: () => ColorBlindnessType.none, + ); +} diff --git a/pubspec.lock b/pubspec.lock index cdfd75b..de4b89f 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -21,10 +21,10 @@ packages: dependency: transitive description: name: archive - sha256: d6347d54a2d8028e0437e3c099f66fdb8ae02c4720c1e7534c9f24c10351f85d + sha256: "0c8368c9b3f0abbc193b9d6133649a614204b528982bebc7026372d61677ce3a" url: "https://pub.dev" source: hosted - version: "3.3.6" + version: "3.3.7" args: dependency: transitive description: @@ -185,6 +185,14 @@ packages: url: "https://pub.dev" source: hosted version: "1.17.0" + color_blindness: + dependency: "direct main" + description: + name: color_blindness + sha256: "8e85c212aa21ed74e7067ed7ff0a3dce39a366023bd4ca17820981dc8681a6e6" + url: "https://pub.dev" + source: hosted + version: "0.1.2" convert: dependency: transitive description: @@ -261,10 +269,10 @@ packages: dependency: "direct main" description: name: device_info_plus - sha256: "1d6e5a61674ba3a68fb048a7c7b4ff4bebfed8d7379dbe8f2b718231be9a7c95" + sha256: "435383ca05f212760b0a70426b5a90354fe6bd65992b3a5e27ab6ede74c02f5c" url: "https://pub.dev" source: hosted - version: "8.1.0" + version: "8.2.0" device_info_plus_platform_interface: dependency: transitive description: @@ -309,10 +317,10 @@ packages: dependency: "direct main" description: name: file_picker - sha256: "0d923fb610d0abf67f2149c3a50ef85f78bebecfc4d645719ca70bcf4abc788f" + sha256: dcde5ad1a0cebcf3715ea3f24d0db1888bf77027a26c77d7779e8ef63b8ade62 url: "https://pub.dev" source: hosted - version: "5.2.7" + version: "5.2.9" fixnum: dependency: transitive description: @@ -452,18 +460,18 @@ packages: dependency: "direct main" description: name: flutter_web_auth_2 - sha256: "6aebfb1797bb1dd38cd32753832670482792e4f0b9cef0329d357f889dbf07c9" + sha256: "354002de1cf644b98af9b1b8c7a0f50f55d738667a54786ae4197e6ff87b224a" url: "https://pub.dev" source: hosted - version: "2.1.2" + version: "2.1.3" flutter_web_auth_2_platform_interface: dependency: transitive description: name: flutter_web_auth_2_platform_interface - sha256: dd934033564cacff127b4776798dc2b27b2f2ebfd6b669746455b91c3611cfde + sha256: "91ff7f0bf4ca530aabf857433db2fbcc3d1b8e3c5347ecf58e5ace8f9d29edb0" url: "https://pub.dev" source: hosted - version: "2.1.0" + version: "2.1.3" flutter_web_plugins: dependency: transitive description: flutter @@ -537,10 +545,10 @@ packages: dependency: "direct main" description: name: go_router - sha256: feab99a20fd248c658c923ba98f4449ca6e575c3dee9fdf07146f4f33482c6bc + sha256: "99c7fbd4f73da5268046374576af2f6fef970088038d626c5c689a359479af40" url: "https://pub.dev" source: hosted - version: "6.5.5" + version: "6.5.7" graphs: dependency: transitive description: @@ -593,18 +601,18 @@ packages: dependency: "direct main" description: name: image_picker - sha256: cb25f04595a88450970dbe727243ba8cd21b6f7e0d7d1fc5b789fc6f52e95494 + sha256: f202f5d730eb8219e35e80c4461fb3a779940ad30ce8fde1586df756e3af25e6 url: "https://pub.dev" source: hosted - version: "0.8.7+1" + version: "0.8.7+3" image_picker_android: dependency: transitive description: name: image_picker_android - sha256: dfb5b0f28b8786fcc662b7ed42bfb4b82a6cbbd74da1958384b10d40bdf212a7 + sha256: "1ea6870350f56af8dab716459bd9d5dc76947e29e07a2ba1d0c172eaaf4f269c" url: "https://pub.dev" source: hosted - version: "0.8.6+6" + version: "0.8.6+7" image_picker_for_web: dependency: transitive description: @@ -617,10 +625,10 @@ packages: dependency: transitive description: name: image_picker_ios - sha256: d4cb8ab04f770dab9d04c7959e5f6d22e8c5280343d425f9344f93832cf58445 + sha256: a1546ff5861fc15812953d4733b520c3d371cec3d2859a001ff04c46c4d81883 url: "https://pub.dev" source: hosted - version: "0.8.7+2" + version: "0.8.7+3" image_picker_platform_interface: dependency: transitive description: @@ -705,58 +713,58 @@ packages: dependency: "direct main" description: name: media_kit - sha256: defc249a792bf39346e6ee3ec40bbe48685c54aab86a25c4c27cc54a99afb6b1 + sha256: "4c2b3bb600c063ad194934ea7439bce3135cc6b4f9555222c3dc12ca1aa1d85c" url: "https://pub.dev" source: hosted - version: "0.0.4+1" + version: "0.0.5+1" media_kit_libs_ios_video: dependency: "direct main" description: name: media_kit_libs_ios_video - sha256: a6ee06d466f539d161ef3b0c13f101713fd051d90c435a503420cb6a6f4c6e66 + sha256: "28c6ddd5ed43263641293832c8d1fb3f24af81b4eba0b61d6da9bedadbf2e1b1" url: "https://pub.dev" source: hosted - version: "1.0.3" + version: "1.0.4" media_kit_libs_linux: dependency: "direct main" description: name: media_kit_libs_linux - sha256: "7310b17dd2abc2e7363f78a273086445c2216c7b6dfb60933ca3814031d03814" + sha256: "21acc71cbae3518b3aeef9023a6a3a3decb579a40153764333814987ccd61040" url: "https://pub.dev" source: hosted - version: "1.0.1" + version: "1.0.2" media_kit_libs_macos_video: dependency: "direct main" description: name: media_kit_libs_macos_video - sha256: b3259875e201ec66d98ed33b32687ff14fcce7d91e74d420733c039556dff8cd + sha256: ab1cbdf51400e30a9087bd7d6e10c6130d17296e76313fedd0ef0c57dae8c0f4 url: "https://pub.dev" source: hosted - version: "1.0.3" + version: "1.0.4" media_kit_libs_windows_video: dependency: "direct main" description: name: media_kit_libs_windows_video - sha256: c2bcbe31e6e6f1e6ae5813c5fe9b7bfde1110c2e95643869919972a7845948e1 + sha256: "99a3a85b185ae012a8e3bd596cf0ca425834477d0bec86207548d6ff7c926254" url: "https://pub.dev" source: hosted - version: "1.0.1" + version: "1.0.2" media_kit_native_event_loop: dependency: "direct main" description: name: media_kit_native_event_loop - sha256: "677ea41d13a2013ca7fe050674eac3b5d891185d4300779727a5860a85cdda60" + sha256: ed87140ad4b64156b2b470c8105f48d8cad7923c952ca05d23e02d28978d2cb3 url: "https://pub.dev" source: hosted - version: "1.0.2" + version: "1.0.3" media_kit_video: dependency: "direct main" description: name: media_kit_video - sha256: "1a870a3d731a9ce34e12ec5baed05b3081164f0c85b71baf05900ca47ee5639c" + sha256: "3860b1e8b2779a5702ecea7e6e3d8b16a79407ad478234008550cca660ac52ad" url: "https://pub.dev" source: hosted - version: "0.0.4" + version: "0.0.6" meta: dependency: transitive description: @@ -865,18 +873,18 @@ packages: dependency: transitive description: name: path_provider_android - sha256: "019f18c9c10ae370b08dce1f3e3b73bc9f58e7f087bb5e921f06529438ac0ae7" + sha256: da97262be945a72270513700a92b39dd2f4a54dad55d061687e2e37a6390366a url: "https://pub.dev" source: hosted - version: "2.0.24" + version: "2.0.25" path_provider_foundation: dependency: transitive description: name: path_provider_foundation - sha256: "818b2dc38b0f178e0ea3f7cf3b28146faab11375985d815942a68eee11c2d0f7" + sha256: ad4c4d011830462633f03eb34445a45345673dfd4faf1ab0b4735fbd93b19183 url: "https://pub.dev" source: hosted - version: "2.2.1" + version: "2.2.2" path_provider_linux: dependency: transitive description: @@ -937,10 +945,10 @@ packages: dependency: transitive description: name: pointycastle - sha256: c3120a968135aead39699267f4c74bc9a08e4e909e86bc1b0af5bfd78691123c + sha256: "7c1e5f0d23c9016c5bbd8b1473d0d3fb3fc851b876046039509e18e0c7485f2c" url: "https://pub.dev" source: hosted - version: "3.7.2" + version: "3.7.3" pool: dependency: transitive description: @@ -1025,18 +1033,18 @@ packages: dependency: transitive description: name: shared_preferences_android - sha256: "8304d8a1f7d21a429f91dee552792249362b68a331ac5c3c1caf370f658873f6" + sha256: "7fa90471a6875d26ad78c7e4a675874b2043874586891128dc5899662c97db46" url: "https://pub.dev" source: hosted - version: "2.1.0" + version: "2.1.2" shared_preferences_foundation: dependency: transitive description: name: shared_preferences_foundation - sha256: cf2a42fb20148502022861f71698db12d937c7459345a1bdaa88fc91a91b3603 + sha256: "0c1c16c56c9708aa9c361541a6f0e5cc6fc12a3232d866a687a7b7db30032b07" url: "https://pub.dev" source: hosted - version: "2.2.0" + version: "2.2.1" shared_preferences_linux: dependency: transitive description: @@ -1126,10 +1134,10 @@ packages: dependency: "direct main" description: name: sqlite3 - sha256: "822d321a008e194d7929357e5b58d2e4a04ab670d137182f9759152aa33180ff" + sha256: a3ba4b66a7ab170ce7aa3f5ac43c19ee8d6637afbe7b7c95c94112b4f4d91566 url: "https://pub.dev" source: hosted - version: "1.10.1" + version: "1.11.0" stack_trace: dependency: transitive description: @@ -1238,18 +1246,18 @@ packages: dependency: transitive description: name: url_launcher_android - sha256: dd729390aa936bf1bdf5cd1bc7468ff340263f80a2c4f569416507667de8e3c8 + sha256: a52628068d282d01a07cd86e6ba99e497aa45ce8c91159015b2416907d78e411 url: "https://pub.dev" source: hosted - version: "6.0.26" + version: "6.0.27" url_launcher_ios: dependency: transitive description: name: url_launcher_ios - sha256: "3dedc66ca3c0bef9e6a93c0999aee102556a450afcc1b7bcfeace7a424927d92" + sha256: "9af7ea73259886b92199f9e42c116072f05ff9bea2dcb339ab935dfc957392c2" url: "https://pub.dev" source: hosted - version: "6.1.3" + version: "6.1.4" url_launcher_linux: dependency: transitive description: @@ -1262,10 +1270,10 @@ packages: dependency: transitive description: name: url_launcher_macos - sha256: "0ef2b4f97942a16523e51256b799e9aa1843da6c60c55eefbfa9dbc2dcb8331a" + sha256: "91ee3e75ea9dadf38036200c5d3743518f4a5eb77a8d13fda1ee5764373f185e" url: "https://pub.dev" source: hosted - version: "3.0.4" + version: "3.0.5" url_launcher_platform_interface: dependency: transitive description: @@ -1326,10 +1334,10 @@ packages: dependency: transitive description: name: video_player_avfoundation - sha256: af308d08c672d5ff718c60127665249617c37a709cb8f0a18dd28a0360299b7c + sha256: "75c6d68cd479a25f34d635149ba6887bc8f1b2b2921841121fd44ea0c5bc1927" url: "https://pub.dev" source: hosted - version: "2.4.3" + version: "2.4.4" video_player_platform_interface: dependency: transitive description: @@ -1358,18 +1366,18 @@ packages: dependency: transitive description: name: web_socket_channel - sha256: ca49c0bc209c687b887f30527fb6a9d80040b072cc2990f34b9bec3e7663101b + sha256: d88238e5eac9a42bb43ca4e721edba3c08c6354d4a53063afaa568516217621b url: "https://pub.dev" source: hosted - version: "2.3.0" + version: "2.4.0" win32: dependency: transitive description: name: win32 - sha256: c9ebe7ee4ab0c2194e65d3a07d8c54c5d00bb001b76081c4a04cdb8448b59e46 + sha256: a6f0236dbda0f63aa9a25ad1ff9a9d8a4eaaa5012da0dc59d21afdb1dc361ca4 url: "https://pub.dev" source: hosted - version: "3.1.3" + version: "3.1.4" window_to_front: dependency: transitive description: diff --git a/pubspec.yaml b/pubspec.yaml index 03b4995..cbc3cee 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -53,6 +53,7 @@ dependencies: device_info_plus: ^8.0.0 string_validator: ^0.3.0 device_preview: ^1.1.0 + color_blindness: ^0.1.2 dev_dependencies: flutter_test: diff --git a/windows/flutter/generated_plugin_registrant.cc b/windows/flutter/generated_plugin_registrant.cc index 75c7ec2..6b3d3e0 100644 --- a/windows/flutter/generated_plugin_registrant.cc +++ b/windows/flutter/generated_plugin_registrant.cc @@ -8,6 +8,7 @@ #include #include +#include #include #include #include @@ -18,6 +19,8 @@ void RegisterPlugins(flutter::PluginRegistry* registry) { registry->GetRegistrarForPlugin("DesktopWindowPlugin")); FlutterSecureStorageWindowsPluginRegisterWithRegistrar( registry->GetRegistrarForPlugin("FlutterSecureStorageWindowsPlugin")); + MediaKitLibsWindowsVideoPluginCApiRegisterWithRegistrar( + registry->GetRegistrarForPlugin("MediaKitLibsWindowsVideoPluginCApi")); MediaKitVideoPluginCApiRegisterWithRegistrar( registry->GetRegistrarForPlugin("MediaKitVideoPluginCApi")); ObjectboxFlutterLibsPluginRegisterWithRegistrar( diff --git a/windows/flutter/generated_plugins.cmake b/windows/flutter/generated_plugins.cmake index f149558..f4d8ce9 100644 --- a/windows/flutter/generated_plugins.cmake +++ b/windows/flutter/generated_plugins.cmake @@ -5,6 +5,7 @@ list(APPEND FLUTTER_PLUGIN_LIST desktop_window flutter_secure_storage_windows + media_kit_libs_windows_video media_kit_video objectbox_flutter_libs url_launcher_windows @@ -12,7 +13,6 @@ list(APPEND FLUTTER_PLUGIN_LIST ) list(APPEND FLUTTER_FFI_PLUGIN_LIST - media_kit_libs_windows_video media_kit_native_event_loop )