From ec8ee21749f29f927bc93b69407d4b890b82db95 Mon Sep 17 00:00:00 2001 From: otsmr Date: Tue, 31 Dec 2024 17:50:53 +0900 Subject: [PATCH] add files --- .gitignore | 44 + README.md | 119 ++ analysis_options.yaml | 28 + android/.gitignore | 13 + android/app/build.gradle | 45 + android/app/proguard-rules.pro | 1 + android/app/src/debug/AndroidManifest.xml | 7 + android/app/src/main/AndroidManifest.xml | 45 + .../com/example/connect/MainActivity.kt | 5 + .../res/drawable-v21/launch_background.xml | 12 + .../main/res/drawable/launch_background.xml | 12 + .../src/main/res/mipmap-hdpi/ic_launcher.png | Bin 0 -> 544 bytes .../main/res/mipmap-hdpi/launcher_icon.png | Bin 0 -> 1357 bytes .../src/main/res/mipmap-mdpi/ic_launcher.png | Bin 0 -> 442 bytes .../main/res/mipmap-mdpi/launcher_icon.png | Bin 0 -> 1277 bytes .../src/main/res/mipmap-xhdpi/ic_launcher.png | Bin 0 -> 721 bytes .../main/res/mipmap-xhdpi/launcher_icon.png | Bin 0 -> 1527 bytes .../main/res/mipmap-xxhdpi/ic_launcher.png | Bin 0 -> 1031 bytes .../main/res/mipmap-xxhdpi/launcher_icon.png | Bin 0 -> 1903 bytes .../main/res/mipmap-xxxhdpi/ic_launcher.png | Bin 0 -> 1443 bytes .../main/res/mipmap-xxxhdpi/launcher_icon.png | Bin 0 -> 2376 bytes .../app/src/main/res/values-night/styles.xml | 18 + android/app/src/main/res/values/styles.xml | 18 + android/app/src/profile/AndroidManifest.xml | 7 + android/build.gradle | 18 + android/gradle.properties | 3 + .../gradle/wrapper/gradle-wrapper.properties | 5 + android/settings.gradle | 25 + assets/images/2.0x/flutter_logo.png | Bin 0 -> 619 bytes assets/images/3.0x/flutter_logo.png | Bin 0 -> 810 bytes assets/images/flutter_logo.png | Bin 0 -> 419 bytes assets/images/logo.png | Bin 0 -> 5327 bytes assets/images/logo/android/play_store_512.png | Bin 0 -> 14021 bytes .../res/mipmap-anydpi-v26/ic_launcher.xml | 6 + .../android/res/mipmap-hdpi/ic_launcher.png | Bin 0 -> 4540 bytes .../mipmap-hdpi/ic_launcher_background.png | Bin 0 -> 1914 bytes .../mipmap-hdpi/ic_launcher_foreground.png | Bin 0 -> 2633 bytes .../mipmap-hdpi/ic_launcher_monochrome.png | Bin 0 -> 2572 bytes .../android/res/mipmap-mdpi/ic_launcher.png | Bin 0 -> 3005 bytes .../mipmap-mdpi/ic_launcher_background.png | Bin 0 -> 1360 bytes .../mipmap-mdpi/ic_launcher_foreground.png | Bin 0 -> 1589 bytes .../mipmap-mdpi/ic_launcher_monochrome.png | Bin 0 -> 1607 bytes .../android/res/mipmap-xhdpi/ic_launcher.png | Bin 0 -> 6392 bytes .../mipmap-xhdpi/ic_launcher_background.png | Bin 0 -> 2521 bytes .../mipmap-xhdpi/ic_launcher_foreground.png | Bin 0 -> 3808 bytes .../mipmap-xhdpi/ic_launcher_monochrome.png | Bin 0 -> 3713 bytes .../android/res/mipmap-xxhdpi/ic_launcher.png | Bin 0 -> 10421 bytes .../mipmap-xxhdpi/ic_launcher_background.png | Bin 0 -> 4219 bytes .../mipmap-xxhdpi/ic_launcher_foreground.png | Bin 0 -> 6563 bytes .../mipmap-xxhdpi/ic_launcher_monochrome.png | Bin 0 -> 6364 bytes .../res/mipmap-xxxhdpi/ic_launcher.png | Bin 0 -> 14427 bytes .../mipmap-xxxhdpi/ic_launcher_background.png | Bin 0 -> 6027 bytes .../mipmap-xxxhdpi/ic_launcher_foreground.png | Bin 0 -> 9500 bytes .../mipmap-xxxhdpi/ic_launcher_monochrome.png | Bin 0 -> 9222 bytes assets/images/logo/ios/AppIcon-20@2x.png | Bin 0 -> 1155 bytes assets/images/logo/ios/AppIcon-20@2x~ipad.png | Bin 0 -> 1155 bytes assets/images/logo/ios/AppIcon-20@3x.png | Bin 0 -> 1443 bytes assets/images/logo/ios/AppIcon-20~ipad.png | Bin 0 -> 661 bytes assets/images/logo/ios/AppIcon-29.png | Bin 0 -> 900 bytes assets/images/logo/ios/AppIcon-29@2x.png | Bin 0 -> 1531 bytes assets/images/logo/ios/AppIcon-29@2x~ipad.png | Bin 0 -> 1531 bytes assets/images/logo/ios/AppIcon-29@3x.png | Bin 0 -> 2155 bytes assets/images/logo/ios/AppIcon-29~ipad.png | Bin 0 -> 900 bytes assets/images/logo/ios/AppIcon-40@2x.png | Bin 0 -> 1930 bytes assets/images/logo/ios/AppIcon-40@2x~ipad.png | Bin 0 -> 1930 bytes assets/images/logo/ios/AppIcon-40@3x.png | Bin 0 -> 2602 bytes assets/images/logo/ios/AppIcon-40~ipad.png | Bin 0 -> 1155 bytes assets/images/logo/ios/AppIcon-60@2x~car.png | Bin 0 -> 2602 bytes assets/images/logo/ios/AppIcon-60@3x~car.png | Bin 0 -> 3937 bytes .../images/logo/ios/AppIcon-83.5@2x~ipad.png | Bin 0 -> 3756 bytes assets/images/logo/ios/AppIcon@2x.png | Bin 0 -> 2602 bytes assets/images/logo/ios/AppIcon@2x~ipad.png | Bin 0 -> 3479 bytes assets/images/logo/ios/AppIcon@3x.png | Bin 0 -> 3937 bytes .../images/logo/ios/AppIcon~ios-marketing.png | Bin 0 -> 36801 bytes assets/images/logo/ios/AppIcon~ipad.png | Bin 0 -> 1966 bytes assets/images/logo/ios/Contents.json | 134 ++ assets/images/logo/logo.png | Bin 0 -> 14021 bytes assets/images/logo/web/README.txt | 18 + assets/images/logo/web/apple-touch-icon.png | Bin 0 -> 3937 bytes assets/images/logo/web/favicon.ico | Bin 0 -> 5238 bytes assets/images/logo/web/icon-192-maskable.png | Bin 0 -> 4243 bytes assets/images/logo/web/icon-192.png | Bin 0 -> 5262 bytes assets/images/logo/web/icon-512-maskable.png | Bin 0 -> 14021 bytes assets/images/logo/web/icon-512.png | Bin 0 -> 17428 bytes assets/images/shield-solid.svg | 1 + ios/.gitignore | 34 + ios/Flutter/AppFrameworkInfo.plist | 26 + ios/Flutter/Debug.xcconfig | 2 + ios/Flutter/Release.xcconfig | 2 + ios/Podfile | 41 + ios/Runner.xcodeproj/project.pbxproj | 616 +++++++++ .../contents.xcworkspacedata | 7 + .../xcshareddata/IDEWorkspaceChecks.plist | 8 + .../xcshareddata/WorkspaceSettings.xcsettings | 8 + .../xcshareddata/xcschemes/Runner.xcscheme | 98 ++ .../contents.xcworkspacedata | 7 + .../xcshareddata/IDEWorkspaceChecks.plist | 8 + .../xcshareddata/WorkspaceSettings.xcsettings | 8 + ios/Runner/AppDelegate.swift | 13 + .../AppIcon.appiconset/Contents.json | 1 + .../Icon-App-1024x1024@1x.png | Bin 0 -> 11537 bytes .../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 0 -> 1162 bytes .../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 0 -> 1221 bytes .../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 0 -> 1316 bytes .../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 0 -> 1192 bytes .../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 0 -> 1308 bytes .../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 0 -> 1440 bytes .../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 0 -> 1221 bytes .../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 0 -> 1433 bytes .../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 0 -> 1672 bytes .../AppIcon.appiconset/Icon-App-50x50@1x.png | Bin 0 -> 1254 bytes .../AppIcon.appiconset/Icon-App-50x50@2x.png | Bin 0 -> 1543 bytes .../AppIcon.appiconset/Icon-App-57x57@1x.png | Bin 0 -> 1308 bytes .../AppIcon.appiconset/Icon-App-57x57@2x.png | Bin 0 -> 1644 bytes .../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 0 -> 1672 bytes .../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 0 -> 2207 bytes .../AppIcon.appiconset/Icon-App-72x72@1x.png | Bin 0 -> 1357 bytes .../AppIcon.appiconset/Icon-App-72x72@2x.png | Bin 0 -> 1903 bytes .../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 0 -> 1391 bytes .../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 0 -> 1996 bytes .../Icon-App-83.5x83.5@2x.png | Bin 0 -> 2069 bytes .../LaunchImage.imageset/Contents.json | 23 + .../LaunchImage.imageset/LaunchImage.png | Bin 0 -> 68 bytes .../LaunchImage.imageset/LaunchImage@2x.png | Bin 0 -> 68 bytes .../LaunchImage.imageset/LaunchImage@3x.png | Bin 0 -> 68 bytes .../LaunchImage.imageset/README.md | 5 + ios/Runner/Base.lproj/LaunchScreen.storyboard | 37 + ios/Runner/Base.lproj/Main.storyboard | 26 + ios/Runner/Info.plist | 53 + ios/Runner/Runner-Bridging-Header.h | 1 + ios/RunnerTests/RunnerTests.swift | 12 + l10n.yaml | 3 + lib/main.dart | 66 + lib/src/app.dart | 85 ++ lib/src/localization/app_en.arb | 7 + lib/src/model/identity_key_store_model.dart | 34 + lib/src/model/model_constants.dart | 5 + lib/src/model/pre_key_model.dart | 29 + lib/src/model/sender_key_store_model.dart | 29 + lib/src/model/session_store_model.dart | 33 + lib/src/model/user.dart | 27 + lib/src/model/user.g.dart | 21 + lib/src/providers/api_provider.dart | 144 +++ lib/src/providers/db_provider.dart | 83 ++ lib/src/settings/settings_controller.dart | 50 + lib/src/settings/settings_service.dart | 17 + lib/src/settings/settings_view.dart | 49 + .../signal/connect_identitiy_key_store.dart | 68 + lib/src/signal/connect_pre_key_store.dart | 49 + lib/src/signal/connect_sender_key_store.dart | 31 + lib/src/signal/connect_session_store.dart | 73 ++ .../signal/connect_signal_protocol_store.dart | 110 ++ .../signal/connect_signed_pre_key_store.dart | 69 + lib/src/signal/signal_helper.dart | 186 +++ lib/src/utils.dart | 68 + lib/src/views/add_new_user_view.dart | 148 +++ lib/src/views/camera_editor_view.dart | 288 +++++ lib/src/views/camera_preview_view.dart | 357 ++++++ lib/src/views/chat_item_details_view.dart | 22 + lib/src/views/chat_list_view.dart | 277 ++++ lib/src/views/home_view.dart | 77 ++ lib/src/views/permissions_view.dart | 85 ++ lib/src/views/profile_view.dart | 59 + lib/src/views/register_view.dart | 152 +++ linux/.gitignore | 1 + linux/CMakeLists.txt | 145 +++ linux/flutter/CMakeLists.txt | 88 ++ linux/flutter/generated_plugin_registrant.cc | 19 + linux/flutter/generated_plugin_registrant.h | 15 + linux/flutter/generated_plugins.cmake | 25 + linux/main.cc | 6 + linux/my_application.cc | 124 ++ linux/my_application.h | 18 + macos/.gitignore | 7 + macos/Flutter/Flutter-Debug.xcconfig | 2 + macos/Flutter/Flutter-Release.xcconfig | 2 + macos/Flutter/GeneratedPluginRegistrant.swift | 24 + macos/Podfile | 43 + macos/Podfile.lock | 54 + macos/Runner.xcodeproj/project.pbxproj | 801 ++++++++++++ .../xcshareddata/IDEWorkspaceChecks.plist | 8 + .../xcshareddata/xcschemes/Runner.xcscheme | 98 ++ .../contents.xcworkspacedata | 10 + .../xcshareddata/IDEWorkspaceChecks.plist | 8 + macos/Runner/AppDelegate.swift | 9 + .../AppIcon.appiconset/Contents.json | 68 + .../AppIcon.appiconset/app_icon_1024.png | Bin 0 -> 102994 bytes .../AppIcon.appiconset/app_icon_128.png | Bin 0 -> 5680 bytes .../AppIcon.appiconset/app_icon_16.png | Bin 0 -> 520 bytes .../AppIcon.appiconset/app_icon_256.png | Bin 0 -> 14142 bytes .../AppIcon.appiconset/app_icon_32.png | Bin 0 -> 1066 bytes .../AppIcon.appiconset/app_icon_512.png | Bin 0 -> 36406 bytes .../AppIcon.appiconset/app_icon_64.png | Bin 0 -> 2218 bytes macos/Runner/Base.lproj/MainMenu.xib | 343 +++++ macos/Runner/Configs/AppInfo.xcconfig | 14 + macos/Runner/Configs/Debug.xcconfig | 2 + macos/Runner/Configs/Release.xcconfig | 2 + macos/Runner/Configs/Warnings.xcconfig | 13 + macos/Runner/DebugProfile.entitlements | 12 + macos/Runner/Info.plist | 32 + macos/Runner/MainFlutterWindow.swift | 15 + macos/Runner/Release.entitlements | 8 + macos/RunnerTests/RunnerTests.swift | 12 + pubspec.lock | 1124 +++++++++++++++++ pubspec.yaml | 57 + test/unit_test.dart | 15 + test/widget_test.dart | 31 + web/favicon.png | Bin 0 -> 917 bytes web/icons/Icon-192.png | Bin 0 -> 5292 bytes web/icons/Icon-512.png | Bin 0 -> 8252 bytes web/icons/Icon-maskable-192.png | Bin 0 -> 5594 bytes web/icons/Icon-maskable-512.png | Bin 0 -> 20998 bytes web/index.html | 38 + web/manifest.json | 35 + windows/.gitignore | 17 + windows/CMakeLists.txt | 108 ++ windows/flutter/CMakeLists.txt | 109 ++ .../flutter/generated_plugin_registrant.cc | 20 + windows/flutter/generated_plugin_registrant.h | 15 + windows/flutter/generated_plugins.cmake | 26 + windows/runner/CMakeLists.txt | 40 + windows/runner/Runner.rc | 121 ++ windows/runner/flutter_window.cpp | 71 ++ windows/runner/flutter_window.h | 33 + windows/runner/main.cpp | 43 + windows/runner/resource.h | 16 + windows/runner/resources/app_icon.ico | Bin 0 -> 33772 bytes windows/runner/runner.exe.manifest | 14 + windows/runner/utils.cpp | 65 + windows/runner/utils.h | 19 + windows/runner/win32_window.cpp | 288 +++++ windows/runner/win32_window.h | 102 ++ 232 files changed, 8856 insertions(+) create mode 100644 .gitignore create mode 100644 README.md create mode 100644 analysis_options.yaml create mode 100644 android/.gitignore create mode 100644 android/app/build.gradle create mode 100644 android/app/proguard-rules.pro create mode 100644 android/app/src/debug/AndroidManifest.xml create mode 100644 android/app/src/main/AndroidManifest.xml create mode 100644 android/app/src/main/kotlin/com/example/connect/MainActivity.kt create mode 100644 android/app/src/main/res/drawable-v21/launch_background.xml create mode 100644 android/app/src/main/res/drawable/launch_background.xml create mode 100644 android/app/src/main/res/mipmap-hdpi/ic_launcher.png create mode 100644 android/app/src/main/res/mipmap-hdpi/launcher_icon.png create mode 100644 android/app/src/main/res/mipmap-mdpi/ic_launcher.png create mode 100644 android/app/src/main/res/mipmap-mdpi/launcher_icon.png create mode 100644 android/app/src/main/res/mipmap-xhdpi/ic_launcher.png create mode 100644 android/app/src/main/res/mipmap-xhdpi/launcher_icon.png create mode 100644 android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png create mode 100644 android/app/src/main/res/mipmap-xxhdpi/launcher_icon.png create mode 100644 android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png create mode 100644 android/app/src/main/res/mipmap-xxxhdpi/launcher_icon.png create mode 100644 android/app/src/main/res/values-night/styles.xml create mode 100644 android/app/src/main/res/values/styles.xml create mode 100644 android/app/src/profile/AndroidManifest.xml create mode 100644 android/build.gradle create mode 100644 android/gradle.properties create mode 100644 android/gradle/wrapper/gradle-wrapper.properties create mode 100644 android/settings.gradle create mode 100644 assets/images/2.0x/flutter_logo.png create mode 100644 assets/images/3.0x/flutter_logo.png create mode 100644 assets/images/flutter_logo.png create mode 100644 assets/images/logo.png create mode 100644 assets/images/logo/android/play_store_512.png create mode 100644 assets/images/logo/android/res/mipmap-anydpi-v26/ic_launcher.xml create mode 100644 assets/images/logo/android/res/mipmap-hdpi/ic_launcher.png create mode 100644 assets/images/logo/android/res/mipmap-hdpi/ic_launcher_background.png create mode 100644 assets/images/logo/android/res/mipmap-hdpi/ic_launcher_foreground.png create mode 100644 assets/images/logo/android/res/mipmap-hdpi/ic_launcher_monochrome.png create mode 100644 assets/images/logo/android/res/mipmap-mdpi/ic_launcher.png create mode 100644 assets/images/logo/android/res/mipmap-mdpi/ic_launcher_background.png create mode 100644 assets/images/logo/android/res/mipmap-mdpi/ic_launcher_foreground.png create mode 100644 assets/images/logo/android/res/mipmap-mdpi/ic_launcher_monochrome.png create mode 100644 assets/images/logo/android/res/mipmap-xhdpi/ic_launcher.png create mode 100644 assets/images/logo/android/res/mipmap-xhdpi/ic_launcher_background.png create mode 100644 assets/images/logo/android/res/mipmap-xhdpi/ic_launcher_foreground.png create mode 100644 assets/images/logo/android/res/mipmap-xhdpi/ic_launcher_monochrome.png create mode 100644 assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher.png create mode 100644 assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher_background.png create mode 100644 assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher_foreground.png create mode 100644 assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher_monochrome.png create mode 100644 assets/images/logo/android/res/mipmap-xxxhdpi/ic_launcher.png create mode 100644 assets/images/logo/android/res/mipmap-xxxhdpi/ic_launcher_background.png create mode 100644 assets/images/logo/android/res/mipmap-xxxhdpi/ic_launcher_foreground.png create mode 100644 assets/images/logo/android/res/mipmap-xxxhdpi/ic_launcher_monochrome.png create mode 100644 assets/images/logo/ios/AppIcon-20@2x.png create mode 100644 assets/images/logo/ios/AppIcon-20@2x~ipad.png create mode 100644 assets/images/logo/ios/AppIcon-20@3x.png create mode 100644 assets/images/logo/ios/AppIcon-20~ipad.png create mode 100644 assets/images/logo/ios/AppIcon-29.png create mode 100644 assets/images/logo/ios/AppIcon-29@2x.png create mode 100644 assets/images/logo/ios/AppIcon-29@2x~ipad.png create mode 100644 assets/images/logo/ios/AppIcon-29@3x.png create mode 100644 assets/images/logo/ios/AppIcon-29~ipad.png create mode 100644 assets/images/logo/ios/AppIcon-40@2x.png create mode 100644 assets/images/logo/ios/AppIcon-40@2x~ipad.png create mode 100644 assets/images/logo/ios/AppIcon-40@3x.png create mode 100644 assets/images/logo/ios/AppIcon-40~ipad.png create mode 100644 assets/images/logo/ios/AppIcon-60@2x~car.png create mode 100644 assets/images/logo/ios/AppIcon-60@3x~car.png create mode 100644 assets/images/logo/ios/AppIcon-83.5@2x~ipad.png create mode 100644 assets/images/logo/ios/AppIcon@2x.png create mode 100644 assets/images/logo/ios/AppIcon@2x~ipad.png create mode 100644 assets/images/logo/ios/AppIcon@3x.png create mode 100644 assets/images/logo/ios/AppIcon~ios-marketing.png create mode 100644 assets/images/logo/ios/AppIcon~ipad.png create mode 100644 assets/images/logo/ios/Contents.json create mode 100644 assets/images/logo/logo.png create mode 100644 assets/images/logo/web/README.txt create mode 100644 assets/images/logo/web/apple-touch-icon.png create mode 100644 assets/images/logo/web/favicon.ico create mode 100644 assets/images/logo/web/icon-192-maskable.png create mode 100644 assets/images/logo/web/icon-192.png create mode 100644 assets/images/logo/web/icon-512-maskable.png create mode 100644 assets/images/logo/web/icon-512.png create mode 100644 assets/images/shield-solid.svg create mode 100644 ios/.gitignore create mode 100644 ios/Flutter/AppFrameworkInfo.plist create mode 100644 ios/Flutter/Debug.xcconfig create mode 100644 ios/Flutter/Release.xcconfig create mode 100644 ios/Podfile create mode 100644 ios/Runner.xcodeproj/project.pbxproj create mode 100644 ios/Runner.xcodeproj/project.xcworkspace/contents.xcworkspacedata create mode 100644 ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist create mode 100644 ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings create mode 100644 ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme create mode 100644 ios/Runner.xcworkspace/contents.xcworkspacedata create mode 100644 ios/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist create mode 100644 ios/Runner.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings create mode 100644 ios/Runner/AppDelegate.swift create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-1024x1024@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-50x50@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-50x50@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-57x57@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-57x57@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-72x72@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-72x72@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png create mode 100644 ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png create mode 100644 ios/Runner/Assets.xcassets/LaunchImage.imageset/Contents.json create mode 100644 ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage.png create mode 100644 ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@2x.png create mode 100644 ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@3x.png create mode 100644 ios/Runner/Assets.xcassets/LaunchImage.imageset/README.md create mode 100644 ios/Runner/Base.lproj/LaunchScreen.storyboard create mode 100644 ios/Runner/Base.lproj/Main.storyboard create mode 100644 ios/Runner/Info.plist create mode 100644 ios/Runner/Runner-Bridging-Header.h create mode 100644 ios/RunnerTests/RunnerTests.swift create mode 100644 l10n.yaml create mode 100644 lib/main.dart create mode 100644 lib/src/app.dart create mode 100644 lib/src/localization/app_en.arb create mode 100644 lib/src/model/identity_key_store_model.dart create mode 100644 lib/src/model/model_constants.dart create mode 100644 lib/src/model/pre_key_model.dart create mode 100644 lib/src/model/sender_key_store_model.dart create mode 100644 lib/src/model/session_store_model.dart create mode 100644 lib/src/model/user.dart create mode 100644 lib/src/model/user.g.dart create mode 100644 lib/src/providers/api_provider.dart create mode 100644 lib/src/providers/db_provider.dart create mode 100644 lib/src/settings/settings_controller.dart create mode 100644 lib/src/settings/settings_service.dart create mode 100644 lib/src/settings/settings_view.dart create mode 100644 lib/src/signal/connect_identitiy_key_store.dart create mode 100644 lib/src/signal/connect_pre_key_store.dart create mode 100644 lib/src/signal/connect_sender_key_store.dart create mode 100644 lib/src/signal/connect_session_store.dart create mode 100644 lib/src/signal/connect_signal_protocol_store.dart create mode 100644 lib/src/signal/connect_signed_pre_key_store.dart create mode 100644 lib/src/signal/signal_helper.dart create mode 100644 lib/src/utils.dart create mode 100644 lib/src/views/add_new_user_view.dart create mode 100644 lib/src/views/camera_editor_view.dart create mode 100644 lib/src/views/camera_preview_view.dart create mode 100644 lib/src/views/chat_item_details_view.dart create mode 100644 lib/src/views/chat_list_view.dart create mode 100644 lib/src/views/home_view.dart create mode 100644 lib/src/views/permissions_view.dart create mode 100644 lib/src/views/profile_view.dart create mode 100644 lib/src/views/register_view.dart create mode 100644 linux/.gitignore create mode 100644 linux/CMakeLists.txt create mode 100644 linux/flutter/CMakeLists.txt create mode 100644 linux/flutter/generated_plugin_registrant.cc create mode 100644 linux/flutter/generated_plugin_registrant.h create mode 100644 linux/flutter/generated_plugins.cmake create mode 100644 linux/main.cc create mode 100644 linux/my_application.cc create mode 100644 linux/my_application.h create mode 100644 macos/.gitignore create mode 100644 macos/Flutter/Flutter-Debug.xcconfig create mode 100644 macos/Flutter/Flutter-Release.xcconfig create mode 100644 macos/Flutter/GeneratedPluginRegistrant.swift create mode 100644 macos/Podfile create mode 100644 macos/Podfile.lock create mode 100644 macos/Runner.xcodeproj/project.pbxproj create mode 100644 macos/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist create mode 100644 macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme create mode 100644 macos/Runner.xcworkspace/contents.xcworkspacedata create mode 100644 macos/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist create mode 100644 macos/Runner/AppDelegate.swift create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_1024.png create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_128.png create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_16.png create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_256.png create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_32.png create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_512.png create mode 100644 macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_64.png create mode 100644 macos/Runner/Base.lproj/MainMenu.xib create mode 100644 macos/Runner/Configs/AppInfo.xcconfig create mode 100644 macos/Runner/Configs/Debug.xcconfig create mode 100644 macos/Runner/Configs/Release.xcconfig create mode 100644 macos/Runner/Configs/Warnings.xcconfig create mode 100644 macos/Runner/DebugProfile.entitlements create mode 100644 macos/Runner/Info.plist create mode 100644 macos/Runner/MainFlutterWindow.swift create mode 100644 macos/Runner/Release.entitlements create mode 100644 macos/RunnerTests/RunnerTests.swift create mode 100644 pubspec.lock create mode 100644 pubspec.yaml create mode 100644 test/unit_test.dart create mode 100644 test/widget_test.dart create mode 100644 web/favicon.png create mode 100644 web/icons/Icon-192.png create mode 100644 web/icons/Icon-512.png create mode 100644 web/icons/Icon-maskable-192.png create mode 100644 web/icons/Icon-maskable-512.png create mode 100644 web/index.html create mode 100644 web/manifest.json create mode 100644 windows/.gitignore create mode 100644 windows/CMakeLists.txt create mode 100644 windows/flutter/CMakeLists.txt create mode 100644 windows/flutter/generated_plugin_registrant.cc create mode 100644 windows/flutter/generated_plugin_registrant.h create mode 100644 windows/flutter/generated_plugins.cmake create mode 100644 windows/runner/CMakeLists.txt create mode 100644 windows/runner/Runner.rc create mode 100644 windows/runner/flutter_window.cpp create mode 100644 windows/runner/flutter_window.h create mode 100644 windows/runner/main.cpp create mode 100644 windows/runner/resource.h create mode 100644 windows/runner/resources/app_icon.ico create mode 100644 windows/runner/runner.exe.manifest create mode 100644 windows/runner/utils.cpp create mode 100644 windows/runner/utils.h create mode 100644 windows/runner/win32_window.cpp create mode 100644 windows/runner/win32_window.h diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..4314849 --- /dev/null +++ b/.gitignore @@ -0,0 +1,44 @@ +# Miscellaneous +*.class +*.log +*.pyc +*.swp +.DS_Store +.atom/ +.buildlog/ +.history +.svn/ +migrate_working_dir/ + +# IntelliJ related +*.iml +*.ipr +*.iws +.idea/ + +# The .vscode folder contains launch configuration and tasks you configure in +# VS Code which you may wish to be included in version control, so this line +# is commented out by default. +#.vscode/ + +# Flutter/Dart/Pub related +**/doc/api/ +**/ios/Flutter/.last_build_id +.dart_tool/ +.flutter-plugins +.flutter-plugins-dependencies +.packages +.pub-cache/ +.pub/ +/build/ + +# Symbolication related +app.*.symbols + +# Obfuscation related +app.*.map.json + +# Android Studio will place build artifacts here +/android/app/debug +/android/app/profile +/android/app/release \ No newline at end of file diff --git a/README.md b/README.md new file mode 100644 index 0000000..e042c98 --- /dev/null +++ b/README.md @@ -0,0 +1,119 @@ +# Connect + +> Connect a zecure open-source instant-image sharing, full-featured AI app based on 5 blockchains. + +Actually there is no AI or Blockchain or any other dump hyped stuff included into this app. The +purpose of this app is first off all to create a usable, good looking and important of all +end-to-end encrypted alternative to S[redacted]chat. As I love to schare images with friends but not +a strange company. + +## Features + +This app was started because of the three main features I missed out by popular alternatives. + +### Three to rule them all. + +1. Security by design: No one except your device can access your data. +2. Privacy by design: The server only knows your username and public key. +3. User-friendliness: Decide for your own :) + +> "It's the combination that makes the difference. Only a combination of privacy, security and user-friendliness can make a application good. Focusing on just one of these three areas can mean that everyone loses out in the end." ~ Myself 2019 + +### But there is even more! + +4. Decentralized: Everyone can host an server. The usernames are like your email USERNAME@YOURSERVER +5. Simple to use: What is a Public key? If you don't know this it is okay you don't have to to use Connect! + +> "Its like when S[redacted]chat and email had a modern baby" ~ Myself 2024 + + +## Roadmap + +The development of this App has the following stages: + +1. **Working POC**: As this is my first App ever the first step is to learn App development. During +this step I try everything I can do as a non experienced App developer to make working POC App which +is by design secure meaning while I learn new things I always try to think how this could be +attacked and how I could protect it. But as I have no experience at all I depend on libraries who +look secure. This step include: + + 1. Create a working POC and an private invitation code + 2. Test the POC with friends + 3. Improve and fix bugs + 4. Repeat steps 2. and 3. until I have a usable App + +2. **Bug Bounty**: This is probably the most fun part. The GitHub Repository will become open-source +and I make public releases so others can [install](https://github.com/ImranR98/Obtainium) and test +the app as well. After I published the App the following steps will happen. + 1. I try to hack my own App using the free Android Hacking Course from + [heytree.io](https://app.hextree.io/map/android/android-continent). And if I find something will + create a nice write-up. + 2. Add the new invitation code "BUGBOUNTY" so reale smart people (not + like me) can try to hack the app. And if they find something and create a small POC there is a + small Bug Bounty of 50€. + +3. **Pre-Releasing and Scaling**: If I ever come to this point the App will be first released on +[droidy-fy](https://droidify.eu.org/) to test on a larger scale. + +4. **Release**: This will probably never happen, but if it will, I will release the App on Google +Play and maybe Apple App Store for a couple of €€ as this requires a paid developer account :/. The +version on droid-fy will be free for ever to encourage people to switch to open source apps which. + +5. **Becoming Rich**: I will add an ChatBot into the App. Then I rename the App into ConnectAI add +misleading advertisement on the website that the app is smart as it has an AI and then sell the app +for $7 trillion to become rich. + +## Decentralized + +The idea behind this idea is that the server does not know anything about the user. As the server +is not able to read the messages but only see the receiver of it the only purpose is to forward +the message. So like for emails the user can specify in his username to which server he belongs to. + + +The username is then build up with the following informations: + +`username@fqdn:port` + +The username is unique for the corresponding server. The second part contains the fully qualified +domain name where the server is reachable. It is also possible to specify a custom port. The +default port are the HTTP and TLS ports. + + +### Thoughts +When the user is adding another user they could exchange the servers public key which the user then +reports to their own home sever. The home server then can authenticate the other server. But what +is the thread here, the server are not able to see the messages nor change it as the client does an +integrity check. An attacker could drop a messages and send an ACK as this is unauthenticated. + +## Donating + +As this is currently just a stupid project which does not work or serves a real use case even I +would not donate anything to it. But there is another cool way: If you are on the search for a really +cheap hosting provider which I use for my self for over 8 years you could use the following voucher +to get 5€ off `36nc15747855300` (contact me to get a 30% off voucher). I get 10% from the affiliate program which +helps me cover my hosting costs :) + +## Self-hosting + +It is possible to host the server yourself and then modify the server in your app. But be aware it +is not planned to sync the different servers so you can only add people when their are on the same +server! As in my understanding this is not supported by the Signal protocol, but please proof me +wrong and at a PR :) + +A possible idea could be to add multiple servers in app but this would then require multiple +parallel open websocket connection to check for new messages. As before if you want that feature +create a PR :) + + +## Bug-Bounty + +This app offers a Bug Bounty as I really love the Idea of others hacking my app. Depending on the +criticality the bounty can go up to 50€ (more later when there are donation or I actually make some +money which I probably never will do :/). + +## Credits + +As this is my first Android app, I used different examples where I copied the code design decisions. +To give them credits and maybe help others they are listed below: + +- [Database handling (model, provider and usage)](https://github.com/alextekartik/flutter_app_example/blob/master/notepad_sqflite/) \ No newline at end of file diff --git a/analysis_options.yaml b/analysis_options.yaml new file mode 100644 index 0000000..0d29021 --- /dev/null +++ b/analysis_options.yaml @@ -0,0 +1,28 @@ +# This file configures the analyzer, which statically analyzes Dart code to +# check for errors, warnings, and lints. +# +# The issues identified by the analyzer are surfaced in the UI of Dart-enabled +# IDEs (https://dart.dev/tools#ides-and-editors). The analyzer can also be +# invoked from the command line by running `flutter analyze`. + +# The following line activates a set of recommended lints for Flutter apps, +# packages, and plugins designed to encourage good coding practices. +include: package:flutter_lints/flutter.yaml + +linter: + # The lint rules applied to this project can be customized in the + # section below to disable rules from the `package:flutter_lints/flutter.yaml` + # included above or to enable additional rules. A list of all available lints + # and their documentation is published at https://dart.dev/lints. + # + # Instead of disabling a lint rule for the entire project in the + # section below, it can also be suppressed for a single line of code + # or a specific dart file by using the `// ignore: name_of_lint` and + # `// ignore_for_file: name_of_lint` syntax on the line or in the file + # producing the lint. + rules: + # avoid_print: false # Uncomment to disable the `avoid_print` rule + # prefer_single_quotes: true # Uncomment to enable the `prefer_single_quotes` rule + +# Additional information about this file can be found at +# https://dart.dev/guides/language/analysis-options diff --git a/android/.gitignore b/android/.gitignore new file mode 100644 index 0000000..55afd91 --- /dev/null +++ b/android/.gitignore @@ -0,0 +1,13 @@ +gradle-wrapper.jar +/.gradle +/captures/ +/gradlew +/gradlew.bat +/local.properties +GeneratedPluginRegistrant.java + +# Remember to never publicly share your keystore. +# See https://flutter.dev/to/reference-keystore +key.properties +**/*.keystore +**/*.jks diff --git a/android/app/build.gradle b/android/app/build.gradle new file mode 100644 index 0000000..93add39 --- /dev/null +++ b/android/app/build.gradle @@ -0,0 +1,45 @@ +plugins { + id "com.android.application" + id "kotlin-android" + // The Flutter Gradle Plugin must be applied after the Android and Kotlin Gradle plugins. + id "dev.flutter.flutter-gradle-plugin" +} + +android { + namespace = "com.example.connect" + compileSdk = flutter.compileSdkVersion + //ndkVersion = flutter.ndkVersion + ndkVersion = "25.1.8937393" + + compileOptions { + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 + } + + kotlinOptions { + jvmTarget = 17 + } + + defaultConfig { + // TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html). + applicationId = "eu.tsmr.connect" + // You can update the following values to match your application needs. + // For more information, see: https://flutter.dev/to/review-gradle-config. + minSdk = flutter.minSdkVersion + targetSdk = flutter.targetSdkVersion + versionCode = flutter.versionCode + versionName = flutter.versionName + } + + buildTypes { + release { + // TODO: Add your own signing config for the release build. + // Signing with the debug keys for now, so `flutter run --release` works. + signingConfig = signingConfigs.debug + } + } +} + +flutter { + source = "../.." +} diff --git a/android/app/proguard-rules.pro b/android/app/proguard-rules.pro new file mode 100644 index 0000000..d0e0fbc --- /dev/null +++ b/android/app/proguard-rules.pro @@ -0,0 +1 @@ +-keep class net.sqlcipher.** { *; } \ No newline at end of file diff --git a/android/app/src/debug/AndroidManifest.xml b/android/app/src/debug/AndroidManifest.xml new file mode 100644 index 0000000..399f698 --- /dev/null +++ b/android/app/src/debug/AndroidManifest.xml @@ -0,0 +1,7 @@ + + + + diff --git a/android/app/src/main/AndroidManifest.xml b/android/app/src/main/AndroidManifest.xml new file mode 100644 index 0000000..42de359 --- /dev/null +++ b/android/app/src/main/AndroidManifest.xml @@ -0,0 +1,45 @@ + + + + + + + + + + + + + + + + + + + + + diff --git a/android/app/src/main/kotlin/com/example/connect/MainActivity.kt b/android/app/src/main/kotlin/com/example/connect/MainActivity.kt new file mode 100644 index 0000000..ba3d3c2 --- /dev/null +++ b/android/app/src/main/kotlin/com/example/connect/MainActivity.kt @@ -0,0 +1,5 @@ +package com.example.connect + +import io.flutter.embedding.android.FlutterActivity + +class MainActivity: FlutterActivity() diff --git a/android/app/src/main/res/drawable-v21/launch_background.xml b/android/app/src/main/res/drawable-v21/launch_background.xml new file mode 100644 index 0000000..f74085f --- /dev/null +++ b/android/app/src/main/res/drawable-v21/launch_background.xml @@ -0,0 +1,12 @@ + + + + + + + + diff --git a/android/app/src/main/res/drawable/launch_background.xml b/android/app/src/main/res/drawable/launch_background.xml new file mode 100644 index 0000000..304732f --- /dev/null +++ b/android/app/src/main/res/drawable/launch_background.xml @@ -0,0 +1,12 @@ + + + + + + + + diff --git a/android/app/src/main/res/mipmap-hdpi/ic_launcher.png b/android/app/src/main/res/mipmap-hdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..db77bb4b7b0906d62b1847e87f15cdcacf6a4f29 GIT binary patch literal 544 zcmeAS@N?(olHy`uVBq!ia0vp^9w5xY3?!3`olAj~WQl7;NpOBzNqJ&XDuZK6ep0G} zXKrG8YEWuoN@d~6R2!h8bpbvhu0Wd6uZuB!w&u2PAxD2eNXD>P5D~Wn-+_Wa#27Xc zC?Zj|6r#X(-D3u$NCt}(Ms06KgJ4FxJVv{GM)!I~&n8Bnc94O7-Hd)cjDZswgC;Qs zO=b+9!WcT8F?0rF7!Uys2bs@gozCP?z~o%U|N3vA*22NaGQG zlg@K`O_XuxvZ&Ks^m&R!`&1=spLvfx7oGDKDwpwW`#iqdw@AL`7MR}m`rwr|mZgU`8P7SBkL78fFf!WnuYWm$5Z0 zNXhDbCv&49sM544K|?c)WrFfiZvCi9h0O)B3Pgg&ebxsLQ05GG~ AQ2+n{ literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/mipmap-hdpi/launcher_icon.png b/android/app/src/main/res/mipmap-hdpi/launcher_icon.png new file mode 100644 index 0000000000000000000000000000000000000000..06a81f53394c1f6e63a75631cb1b1bb26c928cd3 GIT binary patch literal 1357 zcmeAS@N?(olHy`uVBq!ia0vp^9w5xY3?!3`ol6-QnEnR%gt!8^4FCT({BHe95(V{-yePKg96 zJ~uD+;`GQ9vqMi!jX5(j;@sTO3)7=d%#JuU6{tAs+?(?d_rjygRp9H{v0oT&3N z!cWc$Jv|MmH~j4E&~q~)Pt6KHJsqex^6c#Jb2CCu&5AfZ9jthE#JL&ar+|v5N5B+E zoSGE|RvdA5b{I@?7+5b*aoFiuk*8+>^@g3D6?t|>_-UZx8DPD$!p_c!I1RLD22gRt z*;(OdL5d?_iX%uci^9*$iZ~16hMxgjbOvbh%m^?SWD%Gfb{fb4y9%Zl zs2Aj_GeB42Qw%f;*&?7~Fc+i|CS+nQNoi~5M!bOXhEM2yI z#mZHy*Q{N)e#6F1o40J;wtdIWUAy<}-M9b1!9$0S96fgY#K}{q&zwDX{=&sem#&lpTB(l_Wj4tU%&tS{rCU>xBf%R z7#J8CJY5_^Dj45hU(0(aK&0)V@Wbr6|;1AOR`dA6 z^qAI}xUzRV6A&yKv4lk&=6tEO>k!9M>;llv=>}s%2VYI%8e$ALA{2 zR@y&K?{61)!+g_OLn-jQ;(nL?O?xg)Z*F!|I6iYqvrW*ogN_UA|5vdu-uzf0Tj=$H zJa@B|mlrO+Wm)R{OXZ+rtn1ZDhZ^s0GM#iuP<5-a2U~l_F{9$ihutG3{faCsPaVIa lE&S|V*`*a6mlrKb=ASPbW8dz%zzb9^db;|#taD0e0szLd!*Kur literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/mipmap-mdpi/ic_launcher.png b/android/app/src/main/res/mipmap-mdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..17987b79bb8a35cc66c3c1fd44f5a5526c1b78be GIT binary patch literal 442 zcmeAS@N?(olHy`uVBq!ia0vp^1|ZDA3?vioaBc-sk|nMYCBgY=CFO}lsSJ)O`AMk? zp1FzXsX?iUDV2pMQ*D5Xx&nMcT!A!W`0S9QKQy;}1Cl^CgaH=;G9cpY;r$Q>i*pfB zP2drbID<_#qf;rPZx^FqH)F_D#*k@@q03KywUtLX8Ua?`H+NMzkczFPK3lFz@i_kW%1NOn0|D2I9n9wzH8m|-tHjsw|9>@K=iMBhxvkv6m8Y-l zytQ?X=U+MF$@3 zt`~i=@j|6y)RWMK--}M|=T`o&^Ni>IoWKHEbBXz7?A@mgWoL>!*SXo`SZH-*HSdS+ yn*9;$7;m`l>wYBC5bq;=U}IMqLzqbYCidGC!)_gkIk_C@U+6viv1YEg!`aHD`51SdG57PX4CAX!DUt^$f1Cn^<1oS+CaNeguk+ygh_ zK!he~LBzd995@lT5dVpXhsWuidYAED@_XO+W*o^SAu1WnB8(0);h2#`C@p|7Mu(Vi$Vj4;mWOqy2}g_o)}oa#Y9wJEMj0Jk z3B&v>fMJTnC>+ef42dx~LID`(XGxgBQ3@F007e-SVK^AAgwel)34|hGnlnOZ5@om+ zp?M=3C=)2(az=a$Q=s5eRl;DFOGSfJe}aKjRU-iNEjI{W0a@OZtHJXh7JtYC(*DTv z6NY)6>J~s2gs2v^GZM*gzI(F*p>ej{GqieVB zJ$m-?^y=NGZ@>NnynQ4CrM`m(50MQW<~LkELg61UG7y3h6jKI`3LZU1HFn(i2@};J zp<$CIhfkS0ZTgIvvm$2CnLBU(g2;u77Ds88L@!+yvpjai%2lh^tc{CbpRge@NsAMt zPM?x$*tlu)maW^i@7TF3ZTFtN`}Q9=c~I}^!dxz zZ{-y%`yu}PcCd;AGO17Cyc#bHJ#3=A?P4Bu2y^Y{Ft^n5ssdYgJyH}enX>g}R=9IX zb_%g*+FG%wpfswk7_;+GA9UMU5bIg1yRD)1ER9~`C0zK}M@TbDEz~}5a7US!24ok=eC5)85>@nf DJS3en literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png b/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..09d4391482be68e9e4a07fab769b5de337d16eb1 GIT binary patch literal 721 zcmeAS@N?(olHy`uVBq!ia0vp^2_VeD3?#3*wSy!iOI#yLg7ec#$`gxH85~pclTsBt za}(23gHjVyDhp4h+5i=O3-AeX1=1l$e`s#|#^}+&7(N@w0CIr{$Oe+Uk^K-ZP~83C zcc@hG6rikF&NPT(23>y!y&wkt5C($~2D>~)O*cj@FGjOCM)M>_ixfudOh)?xMu#Fs z#}Y=@YDTwOM)x{K_j*Q;dPdJ?Mz0n|pLRx{4n|)f>SXlmV)XB04CrSJn#dS5nK2lM zrZ9#~WelCp7&e13Y$jvaEXHskn$2V!!DN-nWS__6T*l;H&Fopn?A6HZ-6WRLFP=R` zqG+CE#d4|IbyAI+rJJ`&x9*T`+a=p|0O(+s{UBcyZdkhj=yS1>AirP+0R;mf2uMgM zC}@~JfByORAh4SyRgi&!(cja>F(l*O+nd+@4m$|6K6KDn_&uvCpV23&>G9HJp{xgg zoq1^2_p9@|WEo z*X_Uko@K)qYYv~>43eQGMdbiGbo>E~Q& zrYBH{QP^@Sti!`2)uG{irBBq@y*$B zi#&(U-*=fp74j)RyIw49+0MRPMRU)+a2r*PJ$L5roHt2$UjExCTZSbq%V!HeS7J$N zdG@vOZB4v_lF7Plrx+hxo7(fCV&}fHq)$ literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/mipmap-xhdpi/launcher_icon.png b/android/app/src/main/res/mipmap-xhdpi/launcher_icon.png new file mode 100644 index 0000000000000000000000000000000000000000..ea0ca0fd712fb6877be0a04ef8c16ebae29bc567 GIT binary patch literal 1527 zcmeAS@N?(olHy`uVBq!ia0vp^2_VeD3?#3*wF4!X{s#DjxB|Hh|Nl4qZwOtr%3*&) z+L@W5S66x7o|LeEe(142-!n5~FD?qbI@RyU+~^aNLeI<$I6pt?(zMWHa{^CJi3BP> zH!t?$^vDylLr+bOIWsfj+}zL$)1yz!jyN?Hs5t7}oQU(&Lr>0*Iz25MsQB!hsPi+z zPtFQGJq@Tg{Os(|b2B1O%?dv~9jG|+?CkJ!GeS?zia0$Ttax_Bxf$W7fQqL_z!XQE zniU3C9C3Db7))^(ST9g<*y&l3r)L25hMk=id3HwlX`td6V7;@#&d!K94YX(mP;tcB zS>b0viX&i(BS=#`GyL?-urnZw!q3c#I1A#2p8;ER259ok2rw695ttix8pr^<3Z@vS z7v!olKv&^Y3^WSaBA{Y07o-s=1vD0HDToaehggBfJwVq&+yhq}1~v!N3ZSt-$0OSU z3Q`QkxIB((5zrh;5!f*xLogZOU?kK0|NsAgy3zhDMNCT12^Hg*n9E^Z!P zK7Ii~Az=|wF>wh=DQOv5Ie7&|C1n*=HFXV5Eo~iLJ$(a1BV!X&Gjj_|D{C8DJ9`I5 zCubK|H+K(DFK-`TKmUNhpx}_uu<(e;sOXs3xcG#`q~w&;wDgS3tn8fJy!?W~qT-U$ zvhs?`s_L5By84F3rskH`w)T$BuI`@RzW#}mCQq3l-L8f4FPe#!yipAGry6aK6+ z_}XY(_MlZ(ViR-un*)Z{8&30;+-Q7RzxXUuy}}2#Px1SiY=agUZ|px4sUR1z=!dQ1 ze1-p71uoxy#^3+h=)U8>!V}??OO3@F>ZAA<_-Fk1bAa_G`}_~uj420Se`em{)P0_R zLEXfx&xz_=*bQ16^pzXzxmX3%S!yLG)E?m6=#Z!Q>U7w&{lffD=1zE!E;{K?kJBRk z>2CECq&Cc(@J5=O>wZYU&$gyZ;o?{9e)n6Y9($yK4t!A0@UFAZJ?!gDEUH*o5Jg{S!HDl+$uRR}@fJ$&rS3j3^ HP6{( zJaZG%Q-e|yQz{EjrrIztFa`(sgt!6~Yi|1%a`XoT0ojZ}lNrNjb9xjc(B0U1_% zz5^97Xt*%oq$rQy4?0GKNfJ44uvxI)gC`h-NZ|&0-7(qS@?b!5r36oQ}zyZrNO3 zMO=Or+<~>+A&uN&E!^Sl+>xE!QC-|oJv`ApDhqC^EWD|@=#J`=d#Xzxs4ah}w&Jnc z$|q_opQ^2TrnVZ0o~wh<3t%W&flvYGe#$xqda2bR_R zvPYgMcHgjZ5nSA^lJr%;<&0do;O^tDDh~=pIxA#coaCY>&N%M2^tq^U%3DB@ynvKo}b?yu-bFc-u0JHzced$sg7S3zqI(2 z#Km{dPr7I=pQ5>FuK#)QwK?Y`E`B?nP+}U)I#c1+FM*1kNvWG|a(TpksZQ3B@sD~b zpQ2)*V*TdwjFOtHvV|;OsiDqHi=6%)o4b!)x$)%9pGTsE z-JL={-Ffv+T87W(Xpooq<`r*VzWQcgBN$$`u}f>-ZQI1BB8ykN*=e4rIsJx9>z}*o zo~|9I;xof literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/mipmap-xxhdpi/launcher_icon.png b/android/app/src/main/res/mipmap-xxhdpi/launcher_icon.png new file mode 100644 index 0000000000000000000000000000000000000000..c72472a55b27b6d4759dcf693bbadf3f0cc95899 GIT binary patch literal 1903 zcmbuA3pA8@7{*8A&KSuh(yZL3qKn89vzd&TRhF0=k#d)!(7IH{HO8$*=5Ab4G@&+D zZq<+#W`;2vMK_g86iFo&JNwOa>}gMDJ7;&#`7ZDK{eSQCJm3F(=X_c2Zq5*8J!KFG z1VOu?_5k->_+qaKO=wxEL3-|Kr_?{w+km}RP z#CI10uy+p&-%G`GF}-;d8~_Vg-n}$j7X!ni0JAs&6VpQ@bTe=~DgYA%Ok58Q)6Ky1 zs8X1T@1fzk0ho$kg7Mu9tQ5uznAjy4E1d;kERR9p(STX3fI$$@a6AB}NoN^Y0S(Us zjA#Ii7cg)F35;KY@&68{<9Ku|Ut)ygGw=dQi{nd;_<%AUFKs18(iY1D3Tdh(7?_o$ z;sdF^1p`uF8Ue7hl?(z)fUMM1QUlLFTYMuAkoI$)zhJCX=W7c<76|{Pi)2f`g8%8o z|84~6{NFGFRs4o_aUqehZB;S9`9yd>r%rda7oVR2rSZWEHWCOG?Ymm7l**QF)Pbsj9l> z@|9n%*4F)6f32ahsk!C)jho!owp;DLb=>ak>gMqUJ-xy{(eHQq2kzb*9J>GD;iJdH zPo6#-866vcJ~8>?<<#`6nb)&#-oBfAKmXz5r-j8o#NxU9whJH-*bt3Edd101J+M2d z>7mJey#kq)lDsljOEw)JS~?GjNV6iPtZi*;+Y!+&8rWIqX=I8-uqIQ&+urAFv?43(5e|?75~ZBCMn03a7W(` zvUP$Cc8<-?i0(ggt|_;M@T|0JRr^TQo3To3|05K48&2d(R&S_&;j0tViX78dRkgu( z$)>#m$BrY02!qkeu?U-{5EYi6UijWf^^H?^qIc@ra;^(lclr95=2j!Fhg`=+6QzWY zBow0S4QagEd@VuspaVLnuiO@$A6ignddT>SOl-c(5E(P8iuSphp)7=lxelD-Vyjw$ zMdT!>(>01BEo76S3r;57)${5j&60J%deO2NuOV`51E`u>A6S^AU05H8lno;p_##uW z=Pkm_f`koqrc*Yu^}*^$MiVky#G1WzDx6veAMAsW_gQ9^h*!t>-HWc#F-DY;;3-W^ zPRe0Y3Wq&&EVT_RP)gu5d$t)(zQ{7z@Vt%|(z4y zJSqb=-#S9*^Ne#2e3`7B9m2HD3_)qbC{&U45OLV7@%Efh$+lAjE@)>f`KY(R-?h}v zr5zI*Pk~B9id8bBP!%luG(%@7y>k$(V$8-(8_-N=_;GPA+5(=V!R*_T>=wl4lu6_V zupA01uQ0647~i6%I3+vkZ4BjFYWA+Mf^q|7dyP;~ZrZhqlVa|M$JJ$)ov@jOxo6QJ zd3$@Xra``LUlhy9H4sKjRbxA*!H59^?1FOG6+i26x1k)l5JoFl+wtiW;za2JA_BHq zPXn&-);adtmPFAu2n%yEZ!!Q<5%!qbp#FnBVsWx>fihZtXks>kGB%PcxIh`S$Z=hi YJ5U#C-iWiPlKeT*PHw209sVhQ0`U{caR2}S literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png b/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..4d6372eebdb28e45604e46eeda8dd24651419bc0 GIT binary patch literal 1443 zcmb`G{WsKk6vsdJTdFg%tJav9_E4vzrOaqkWF|A724Nly!y+?N9`YV6wZ}5(X(D_N(?!*n3`|_r0Hc?=PQw&*vnU?QTFY zB_MsH|!j$PP;I}?dppoE_gA(4uc!jV&0!l7_;&p2^pxNo>PEcNJv za5_RT$o2Mf!<+r?&EbHH6nMoTsDOa;mN(wv8RNsHpG)`^ymG-S5By8=l9iVXzN_eG%Xg2@Xeq76tTZ*dGh~Lo9vl;Zfs+W#BydUw zCkZ$o1LqWQO$FC9aKlLl*7x9^0q%0}$OMlp@Kk_jHXOjofdePND+j!A{q!8~Jn+s3 z?~~w@4?egS02}8NuulUA=L~QQfm;MzCGd)XhiftT;+zFO&JVyp2mBww?;QByS_1w! zrQlx%{^cMj0|Bo1FjwY@Q8?Hx0cIPF*@-ZRFpPc#bBw{5@tD(5%sClzIfl8WU~V#u zm5Q;_F!wa$BSpqhN>W@2De?TKWR*!ujY;Yylk_X5#~V!L*Gw~;$%4Q8~Mad z@`-kG?yb$a9cHIApZDVZ^U6Xkp<*4rU82O7%}0jjHlK{id@?-wpN*fCHXyXh(bLt* zPc}H-x0e4E&nQ>y%B-(EL=9}RyC%MyX=upHuFhAk&MLbsF0LP-q`XnH78@fT+pKPW zu72MW`|?8ht^tz$iC}ZwLp4tB;Q49K!QCF3@!iB1qOI=?w z7In!}F~ij(18UYUjnbmC!qKhPo%24?8U1x{7o(+?^Zu0Hx81|FuS?bJ0jgBhEMzf< zCgUq7r2OCB(`XkKcN-TL>u5y#dD6D!)5W?`O5)V^>jb)P)GBdy%t$uUMpf$SNV31$ zb||OojAbvMP?T@$h_ZiFLFVHDmbyMhJF|-_)HX3%m=CDI+ID$0^C>kzxprBW)hw(v zr!Gmda);ICoQyhV_oP5+C%?jcG8v+D@9f?Dk*!BxY}dazmrT@64UrP3hlslANK)bq z$67n83eh}OeW&SV@HG95P|bjfqJ7gw$e+`Hxo!4cx`jdK1bJ>YDSpGKLPZ^1cv$ek zIB?0S<#tX?SJCLWdMd{-ME?$hc7A$zBOdIJ)4!KcAwb=VMov)nK;9z>x~rfT1>dS+ zZ6#`2v@`jgbqq)P22H)Tx2CpmM^o1$B+xT6`(v%5xJ(?j#>Q$+rx_R|7TzDZe{J6q zG1*EcU%tE?!kO%^M;3aM6JN*LAKUVb^xz8-Pxo#jR5(-KBeLJvA@-gxNHx0M-ZJLl z;#JwQoh~9V?`UVo#}{6ka@II>++D@%KqGpMdlQ}?9E*wFcf5(#XQnP$Dk5~%iX^>f z%$y;?M0BLp{O3a(-4A?ewryHrrD%cx#Q^%KY1H zNre$ve+vceSLZcNY4U(RBX&)oZn*Py()h)XkE?PL$!bNb{N5FVI2Y%LKEm%yvpyTP z(1P?z~7YxD~Rf<(a@_y` literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/mipmap-xxxhdpi/launcher_icon.png b/android/app/src/main/res/mipmap-xxxhdpi/launcher_icon.png new file mode 100644 index 0000000000000000000000000000000000000000..b509cebd654660962e401f5cdd2c6751b1bd0049 GIT binary patch literal 2376 zcmbuBc~BE+8pacY$Q3|9lw&v)1(8z&ctJuqBytF14lZ$Yz=(`S(H&PLgd2uaQON;D zF3|uU=z@S6M8rT25;fi&qggSckjP<3fNUpIZq1gpQ?)x)-EV*I*T469p6=>Dx*$Ak z8&t|xT;y(OU>N}QkuEj$<2Qx(HHgXU1e2k6m{&!c-QBl^xp0Wj}EoS-6#MML+Wi{(&o zyec%mB8El7^`8UaXkI05paR`Ti)Nq40x-8SdVq}WqoUd8fmtkZ^-A~1_E7ULz$0K9=0k{J94aW6TF=`mcrD49o81*awW7yOvHW`@3aH&yTGL{X% zWc4f+!zJU`fDsvhaa<~vtAcUgVBG%(Q?P6bhNCjVa;P}2s>O2DMjSwyf>XCDBXx^m z0}FMkZ!j>cO2q+E{TU2M{m}@3)vam}xCO|nO;u}P|96W&$pfVQJkj9TY=3qTeK z|3??qEBy}sZx8;TMu5&=J=9@TBHu66ukruXS1OfK=xQU?_kV0>SR@F%2%@oAbBUI= zj;*pBs6SCc*M@gU1$sz7Zn{78@D@t&yRce{gjZnAAca}VDit0 z4ikJXl!b}dhPm+mYcW!(b{&qy`%Ha-FwWg``r(E9`-(B_4TtkT;2d*@c7A7 z;j`y2UcP$$W^ibDQ$)!Vsa#dx>D-6$eI0(P=`Zqs672NLG}p_<_{ zm;z%uFNJ@w36Gz)cZcIW4IWGgY6hnGK1}o~_~i!-VrODnhj_46R=!3i)=ZW}xlT_f z$ZM**FZ(>vPnnxAmH9>{%B-EGS<$z~xEE%dTJcX0TixUt$g9~(oo<7Z4ZZ_RmPbsB zE`9yNa<}0V?T$>Fm%(XiSK?s)cemuAW~z$Nc(+=kBg7#mbM~iuBRQopqxy08NY+1# zdfrVSAngwo3c=P4s~*{K%@Je(v+G3GC2frPZ-5k|eMaGsIvE;PUJVWKQ9-rX4(T6v9t1AO~jI(KuFw z#m;9w9i1VqycN_UX~6PV_8}MEfI0_f(z+HTAnS!)_#4;h$$qrDy?T-{%jokEmx~cb zRr{b0fsJ;Kd!Z7smP%sODQhbHdZ zjzDi0Y99S4f|lJDF1K3z=cV&P^;<9%bJ1_bGYH-$Hb4Zn<98g&S=c`-Z0VLcO5 zwuTl2V{TDXXfmlY55b>Mk|21zzrugX#*HtDiZ1~#8BTO2(vYB-)=KLi$C zNJytAGCz;8nXl&0GogC2=Ap>f*>v1i&D=Rr!D{8cNQjd+YJY<}+;-Y@t^q1%ihA*EHnXS3*AJeaXr-meOlxmFvFF(&6P3 zL}5(bCh1xEtQBf9Pata2w3}~@@6?8^yq})Y+hUwHI&Nle{?fx%iH2>sn&iT?3Ka>> z*~3Ne3ryxaD>uPHVKaw&m++k^-K9$+iM$OAYQ4Nbmb!LhYydjvrK`jsF@GxZVg_5G P`XxdIg!x}Z?#cWY({|4* literal 0 HcmV?d00001 diff --git a/android/app/src/main/res/values-night/styles.xml b/android/app/src/main/res/values-night/styles.xml new file mode 100644 index 0000000..06952be --- /dev/null +++ b/android/app/src/main/res/values-night/styles.xml @@ -0,0 +1,18 @@ + + + + + + + diff --git a/android/app/src/main/res/values/styles.xml b/android/app/src/main/res/values/styles.xml new file mode 100644 index 0000000..cb1ef88 --- /dev/null +++ b/android/app/src/main/res/values/styles.xml @@ -0,0 +1,18 @@ + + + + + + + diff --git a/android/app/src/profile/AndroidManifest.xml b/android/app/src/profile/AndroidManifest.xml new file mode 100644 index 0000000..399f698 --- /dev/null +++ b/android/app/src/profile/AndroidManifest.xml @@ -0,0 +1,7 @@ + + + + diff --git a/android/build.gradle b/android/build.gradle new file mode 100644 index 0000000..d2ffbff --- /dev/null +++ b/android/build.gradle @@ -0,0 +1,18 @@ +allprojects { + repositories { + google() + mavenCentral() + } +} + +rootProject.buildDir = "../build" +subprojects { + project.buildDir = "${rootProject.buildDir}/${project.name}" +} +subprojects { + project.evaluationDependsOn(":app") +} + +tasks.register("clean", Delete) { + delete rootProject.buildDir +} diff --git a/android/gradle.properties b/android/gradle.properties new file mode 100644 index 0000000..2597170 --- /dev/null +++ b/android/gradle.properties @@ -0,0 +1,3 @@ +org.gradle.jvmargs=-Xmx4G -XX:MaxMetaspaceSize=2G -XX:+HeapDumpOnOutOfMemoryError +android.useAndroidX=true +android.enableJetifier=true diff --git a/android/gradle/wrapper/gradle-wrapper.properties b/android/gradle/wrapper/gradle-wrapper.properties new file mode 100644 index 0000000..22041e5 --- /dev/null +++ b/android/gradle/wrapper/gradle-wrapper.properties @@ -0,0 +1,5 @@ +distributionBase=GRADLE_USER_HOME +distributionPath=wrapper/dists +zipStoreBase=GRADLE_USER_HOME +zipStorePath=wrapper/dists +distributionUrl=https\://services.gradle.org/distributions/gradle-8.10.2-all.zip \ No newline at end of file diff --git a/android/settings.gradle b/android/settings.gradle new file mode 100644 index 0000000..b5e1b3f --- /dev/null +++ b/android/settings.gradle @@ -0,0 +1,25 @@ +pluginManagement { + def flutterSdkPath = { + def properties = new Properties() + file("local.properties").withInputStream { properties.load(it) } + def flutterSdkPath = properties.getProperty("flutter.sdk") + assert flutterSdkPath != null, "flutter.sdk not set in local.properties" + return flutterSdkPath + }() + + includeBuild("$flutterSdkPath/packages/flutter_tools/gradle") + + repositories { + google() + mavenCentral() + gradlePluginPortal() + } +} + +plugins { + id "dev.flutter.flutter-plugin-loader" version "1.0.0" + id "com.android.application" version "8.3.2" apply false + id "org.jetbrains.kotlin.android" version "2.0.20" apply false +} + +include ":app" diff --git a/assets/images/2.0x/flutter_logo.png b/assets/images/2.0x/flutter_logo.png new file mode 100644 index 0000000000000000000000000000000000000000..b65164de707ffeaf0adfca5fca65532bf97e6903 GIT binary patch literal 619 zcmeAS@N?(olHy`uVBq!ia0vp^4Is?H3?#oinD`S&H3s;ExB}^b{r?#vrgK>I2kif@ zvH816@%GSTKN!MhbHpsw+WI}@_)o2^Ujq(*4>|fhmwB2f9E#&lh@dHUo7LNZ{xgp@r+-ynauvLPwNoN4|Z_>tNAZ;@h5j(?S79JcUYfB`=#qy r6fZFpo3n_4Rl|XiE8s&sR~^H;NW15^d4qg`5ys%@>gTe~DWM4f{@o*g literal 0 HcmV?d00001 diff --git a/assets/images/3.0x/flutter_logo.png b/assets/images/3.0x/flutter_logo.png new file mode 100644 index 0000000000000000000000000000000000000000..97e5dc9af6e1093966c5cd42d608fd6fbb6a0c59 GIT binary patch literal 810 zcmeAS@N?(olHy`uVBq!ia0vp^2SAvE8Azrw%`pX16#+gWu0UF2`*(-^-y@EH58eMI z^w{s z-$IW5@LT%57HGFUA^wwrfyu|y#WAGf*4wMk zgAN-AxF%k#KCURBVA1=%-ucp;9Uj}ZG#l?Wes0(B%({NdIoXW<{g3WiupaK0x3By2 zO4s)_FGS)mJr|)n_%@ z)kihD)q6Gi)z>tJ)#o(E)yFiZ)%!H&)t5Jx)rUK-{vXl2fA4~;^_xE>GN_~ps{eO!b9`tLyxW8Xh;HNSd-@|xOj=ytR+do>D zt9>mOkvaAL$-iq%!vCf*DgR4ol&oKHV8Z?Agj4S|4W8wT%=mnri|3a%tJ>eCOpE`; zHb(y6c3?w&Y{ISmIsp&Mrw9G7`Sv8_P1LLTesVhEI)8;vvu5vq*tGV3&cSo}TNXSq zj|})It+V3iSy7We$GB|jf?4DCFKlYK@8ftOf60QQ_A~Fi*3bCZZ_jpf?zg4|^)^x| zt2OmGe$>0=M;cybjjOklN_(oQ_u}uL;@3elyf)C=)PemO(7H=26jVtWmubrDh3}(04)hM&xSK7O%X|>Mc j1|}|z1*pUejUUWgK0Q%uH(H?zOn3~Qu6{1-oD!M<&k2w@ literal 0 HcmV?d00001 diff --git a/assets/images/flutter_logo.png b/assets/images/flutter_logo.png new file mode 100644 index 0000000000000000000000000000000000000000..b5c6ca710c937527ca8d2d344214243d6db33832 GIT binary patch literal 419 zcmeAS@N?(olHy`uVBq!ia0vp^4j|0I3?%1nZ+ru!@&kNAT!FN~`u7^!zegPZ&Ja3_ z)pe?NNpCL!ThaUauw)u_bwr{%Izl9$A!5B7M$govP zxh~|$561A>Od+#a0;aQjP2sie<+JJ*(`u4bZve_F*PR4v(b@jZ=Md1SAK%^B{{yWQ zFA4GsW)M(NFaUyj5NMdc{{H>@?}1?b(XAk7pYe2Y42d}W_VP)gCIbQ2ix!U>4q9?~ zIsEybZ^G7cAu^%-PQ=yx*;eIK#gYnUFW+9QvQNJH+nbx4)6dKOIC(3+3g6;V=GFge(48{@_RM&lLju^uE+^au+>tK7OIONyesA;#Zub zQs3&YevL0~GuE6t~Fo%7BFztX3q{1RVU;;PiN_-8qleWA`_& zw({X*ef?P{^t~Y0vFF>PCUdo}=4?%^3QRb0$VpT0kLyEL`Hh?APM literal 0 HcmV?d00001 diff --git a/assets/images/logo.png b/assets/images/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..c685be212d3cdc66a90f61413f8f21eaf63bf3e8 GIT binary patch literal 5327 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 TdQ|@RpGhNqGrbxe$IyQOOcy0@ literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/play_store_512.png b/assets/images/logo/android/play_store_512.png new file mode 100644 index 0000000000000000000000000000000000000000..22131921f6df0f3b0ecc46d99ade045baa33dd98 GIT binary patch literal 14021 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
>Fu-Equb1_& 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 + + + + + \ No newline at end of file diff --git a/assets/images/logo/android/res/mipmap-hdpi/ic_launcher.png b/assets/images/logo/android/res/mipmap-hdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..92b6c053e7e2f5b0a1602bacf9c1417923e254cd GIT binary patch literal 4540 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 aKmHF?{f)cSsfES>0000BsH> literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-hdpi/ic_launcher_background.png b/assets/images/logo/android/res/mipmap-hdpi/ic_launcher_background.png new file mode 100644 index 0000000000000000000000000000000000000000..f60a087891bbff35612082d9eb2ecf24c60d0e5f GIT binary patch literal 1914 zcmV-=2Zi{FP)Px+G)Y83RCr$Pol$ZlHw;AMQ|{H0JMEn|rLrSC(nuu82G9U|f0qLS50BtjcG(}l ze*g35FYe6(4RQdKcpzf77g;!?X76+Ebfl!XEb%5tiarAU5dp z`OL3$1xOd%B;pVv`ILH3e^?z|^ExGD60uX^47Eu8?=C<@d<9gX8Fa6a14P6crCPF# zIYKeJSnAGOD-liXrH%=gVX;Isz-qlT`3p^n*xIh-;tX>0hT=>J0qG#2ssG-J;3N-m_=Uu{*Qn}q!J={dZm9i>$_gKh->c+!4062 zPs!W}z(u6Rntu9e$)qIqIC{qqwXWCd z_9FIbSKn%QL~Q;to}o~s+ki*Juiqce_e+ruUU>ed(`d`^Bn?L5u=N7?6pEW6L1yLId_F`L_i`oYG&n9 zB;s=S^y0CM?&3j-h@{yfR?Y#Fh%MxKS456j(^$Vg`e`g8c>^9gRV&+R&88PN7IB(E z=)%*5`}~XK&p%Nh5$_sGk+l9|)e`2hMF9?>uI5ARVZWm!;vpikmq{)n+c{>-$Ep`^{^TNBL2G?g0?kD9 zJMn&ztEz*|J5fZn7Te0&(Go@U1Lv){cYHrGypi9F2>5)6w{+jkB&&^Y%ZX@1pw$cn zBqBo>sB*}e<@ay#QL(6!j9y(}o%)=JhXc)-0hS*6W#|{#Qr}5`6w<~;tAh!ozaz4o z$YAb)+tnbPE@EIuv=uP{iAda>lTr&4vBm{)QtP>D4HJ>8>>}BCf12SP-+=ipq9&Gs znwG)|giS<=4)0y7fMFs=QoEF%=o*S-QDv`|B36MvljkWniA0>SL2KOqQldnZWE2Fj zBI-SC*i@dYmM4=NG^~ijHeeT+Q0kCi;e(@<77@%s;g$%P#=*-SB%&3*Caaa$)Ov|H zg{i_K%w)={R3c`PFS@Un?mfQOtn0F<*57GsA_80JH7$TC(uR_Vw5>TSF^Gs^lK^rB zhh>{+QoR}>A|?`VymdX9cA6m(cj)O^7=aiOAy+D_=Dk3jYS|+JeL6-&XvzxKkwA~n z5j%F~u$nXx4{JDUxeyU^zrK6kJvSeQRwoize20dJ7>_;?bbPT#>{wJp&fe5I9$Ys` zu850coKr(kR);dl6%o`sg{e1kB!#o+PiJcwAknEG?!+zJ9FqU1hTuldTc zB9^||=AnhHbmhr4Ah05abx0d^BOnoXI_f&Hb`q=iY>J3nmqNX!b<8+L#Eu|U(-(oo zTS6krAPNE!k)jPvlXx>7A79TdKhXAjhue(2IQE;ixm8*E&PuCx@)a{Xdh};MK)=lf~9zj*y>-hELU5$zu?+R`;0~OO1Xaa`SJM9g9pmP$l9Hy`RszzJ7F2?LBB( z5#i`vMM2rzBhE_iXhrPNlK3iCB#6)Qc}H>)t72tnEo%1E@EWw_NAYU0Bq9aj*%EC_9`u+m7pZB5{p}Zl!&jeO3*mro_6}WZ6xAy z4{GVlo~=Y&7O}^JVS?(nf%Ookb`@jYH4%p$9zz_4(1Ia>NfFhIAxZdxvzSkc2&e29 z5crv&Uy_RaNMJ$4vrej%nIo`k#e#@)iKVU5L`*}!vvEHWcW4AWyE{1oQcT(6Qbaf` zO{tXTR@zh((W6^BcxI|?L_|$-R2*|B4u7DHh?jkAFquv{7`;V2WXg1qHCV(B$Qs#A zbYldI7~e!T_1W@?@5uFz?L}k(tvp^6xE;=a0dBpf7S1>%-T(jq07*qoM6N<$f~hcm A;{X5v literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-hdpi/ic_launcher_foreground.png b/assets/images/logo/android/res/mipmap-hdpi/ic_launcher_foreground.png new file mode 100644 index 0000000000000000000000000000000000000000..5756a0768c909ba859ab4a5c9349a572daca10e9 GIT binary patch literal 2633 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 literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-mdpi/ic_launcher.png b/assets/images/logo/android/res/mipmap-mdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..b98fd2d2b601dbd4f22b3eb853bd15e2a91913ce GIT binary patch literal 3005 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 literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-mdpi/ic_launcher_background.png b/assets/images/logo/android/res/mipmap-mdpi/ic_launcher_background.png new file mode 100644 index 0000000000000000000000000000000000000000..5ac52b84f8e68f6798519c72c32dd38b86116a02 GIT binary patch literal 1360 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 YMdzLir%&!+ZTtY}5Y7`@;R4Y917O7GUH||9 literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-mdpi/ic_launcher_monochrome.png b/assets/images/logo/android/res/mipmap-mdpi/ic_launcher_monochrome.png new file mode 100644 index 0000000000000000000000000000000000000000..4f71405f54be15731e8f28336cfe43c0a039e582 GIT binary patch literal 1607 zcmcJQ`9G8i0LI@r8sivN#*uTWl$B#0AuKTxGvr7l?2DoqXBasKW4p6-F;YsYrZ#4b zW*WKQ*u}b1<0vv-g)%mit6@Z|KcXL==ljd^`8>~W&jlZEcbuH28~^|~kNpI{4aR;K z7PH}(q5^w1fJpXpcLCVF+S34lL3j}M9!v}SRC=T%%3q^BM{GN3d)?q%h%LcVvoO+5 zU3NU8t;m9D-buQ$(}hrbS!1#^62CnjtFG~{Ey<{GA^&QKt%4nHiu-MW^-|K)FeYI) zN`}SRx2vK@NrKA8FF9*DV(#E@jAIOjaAFdIiiUq80?A*tVnIZA395Hu-|0=}(TcX$ zw3OALQahLwPY42%r|6co%HcmEkU<4)U;_N?{yRrF4lWK0P^GPeT;PP#^TIi3!vb`w zx9%E-hI)%~2=1#9-k4X2-2s}x+HeLqrfiyxbHF*s(qz60Z_b#6{fB$)06M`wumdQ| zIncA7gJ@7_@O{1xEbG1w;^qqq)<=rm1#Ho#wvwRPT2J#14#9; zriI>g?vb&=GhVSer1Hx~ZnviD4z#_awH6nO(prad0uM{opidysipy0H^{qfAhi^`59WR5=YE&mehk%ny+5rOkHet>|Jz*e9Y0-t}l!6hd4jjHuSsi8SG-dB% zd|>_uzP$|HTD~~s6tiC*^zZIVTp*)V+E+TN$;L6I;jSi+f$(fDLjw`QNv}DkyVZS`Zy(8?y z?s<``TF=h<*Iu$&9a}Ei!JvD*@POV2Lu&)Ufy;}!=muJRV9E`cyiX!yKHH#b3W%<=nUzR?m)>IBlZ@n5$H%w* zkoa-K%?ZqlPvuCOW}fOAnx=E^zn096eXE>Tu6lAch5Nv>3rdYn`sb0hG(EDrJDu5C z)7&Cb-QESI%#HIFiQ?n+l!`aRz-xu^lE(w`n;E%etG>jv$WGSS-MOEOC3ohP5>T_1 zY%_A}(9vo|5_1|KY$OPdFc#JAti#Xw4YyleV>njc)1`aVn9eu`e3~i~Zemev)~VoM zXG-&Z*A|eZwZ8NcMP+Kg?~{-F-Rq4Fd+Ya6yH(6_=iDE-b-cW{hp{4_d1c@lm>2T4 zWf2`~d8##cwIas3Q|*v<_O){D^kZ|Bm3S$#?4g+R#`(B@`AyS0BLAdUgy+Ld{ZKWl zM(A_HM-66Z-=Z&TcXKvXax) zCT`Qy#JETC?lwab+jBkrLube**9udN61Spun?G+KND3uWq=KvxB7}CW*O!(hS`jE8 zT#k4JBieF8C)OW|c&KEPmePohVjXC{(Zbh~UIJY-E?4=}_<7j7WB(PwGOh+SjGD%Pm$vI;8($e^Y`Lkh-RMPuF#&7oD1`V~M!^NBnx nxDrn?Vjg{(Mt;~4-CH*W&l1^nZG2Gjiv literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-xhdpi/ic_launcher.png b/assets/images/logo/android/res/mipmap-xhdpi/ic_launcher.png new file mode 100644 index 0000000000000000000000000000000000000000..0e2bec245f56663d424c0804790571d00d33d1a7 GIT binary patch literal 6392 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 literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-xhdpi/ic_launcher_foreground.png b/assets/images/logo/android/res/mipmap-xhdpi/ic_launcher_foreground.png new file mode 100644 index 0000000000000000000000000000000000000000..ce3ad26d24ed4bceaf0b6e2b3fdeb3702b814426 GIT binary patch literal 3808 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 f!%+Zg{3cETpTAVb>m00000NkvXXu0mjfn&sak literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher_background.png b/assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher_background.png new file mode 100644 index 0000000000000000000000000000000000000000..72222b96a7819ded4af5b3ac99cc3caa32f4719a GIT binary patch literal 4219 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 literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher_foreground.png b/assets/images/logo/android/res/mipmap-xxhdpi/ic_launcher_foreground.png new file mode 100644 index 0000000000000000000000000000000000000000..2d1f04c9b8c426a94ed33864253c48181d993f81 GIT binary patch literal 6563 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 H>F)mkKWY~Z literal 0 HcmV?d00001 diff --git a/assets/images/logo/android/res/mipmap-xxxhdpi/ic_launcher_monochrome.png b/assets/images/logo/android/res/mipmap-xxxhdpi/ic_launcher_monochrome.png new file mode 100644 index 0000000000000000000000000000000000000000..58861acc3c337505197e50eaf3f29c8d0ed057f0 GIT binary patch literal 9222 zcmeHtX*ksF`#00j;6|lTcE-3vmSkT`(%7}xVw6gmkY!9`8`S9y!=q3i2P} z=i=fLM4ml;j*E-CWcLN*1>dyUX()p??x1s)r?`r{Bxks|WVw*1PhPm|F+ak$gh9H< zjA#8N3*GlFN>xsePchBWr8!Ual>F2CQQQ-LFpJ{ihM4oiO6174pLbWt(hIqFmx`Y=ixSlL z{RgqTg8PQxt^xfC1aiCW*7*~=D_|PvU0Z0(!F`_Qc4;}gTbf0=?D@~nyo}OB5i|d{&2Am2f@xT3?@l#EI_njLVdMf6O7<#Mk{;dop63 z0NWa+BH5VBa+x8>pfuSmZn1_H^<>csRp{X?~35#j0wt_5kL zv4Q~E1zhek(8;j`ssOUI=+#(8mAn+8(f!g~Qy_;j}J+A8!d=q+zG zKDOL7AaJzqbiz@Z5f|@P!gZbh{^~}e-Ce!-ld6Q9EKmD&UZCir3-pHAKF>0dShs&e_g!A6xUem&Gq&n` zmCIDdkpf%kim$mk5xqYX4YqQ1qN`wqm&~GyLVN^o4=s2MkIrTmh1oU)bXN03@=arQ zoFn8ZzH1dy4GGl1pydNM&Ioq$K%Ilm396Z8*B>bS#CZ*`%+$Hwt5kB#{m?ax`Lf08 zv%dH*ehH&r_y_6EJcGOloR@iFZU*xq*?^g!5MGd*^)|eZOf|@1;uY5)!Mn$f$COg7 zfeUDpO1&2~Sc=f+qNZROBdOJLi`b@wYCF!_(;1EL4QE-UP4%B=VXC%fQOA7G^aeQ- zI95x~k=s9(hcC^me&djfnuhvjN7EVlJuQhfr!jkKEo~K$kRVP1m_8 zol2SM!~_NV)>6klMEYecgi1}{n} zV)I@3Om4kvp=Xf2i&FTAq=#9Q)aVD54Op*jD=NHntg`;f16`@rr$#vS-MyQ3l18Ep zQ6z@%y*Wmn>rEwD`jCsy%r!`|J*%%a)?hSpHF(0%c6i*)Sc7#f3AeiUbyGB6y}gV) z){(bwur`Woc;n#h`Y406rJuDu^3s}81sgoIL0cyH-^w4MYt6w=me3@lW9>LlAJwoq zK#k@fMEuUUWY)LnhT-4LC36iMeTd@1T)XJY$)k#mO=Z5}_P(=3Utl=1CN%TY*nOEY9XOPsPp9qWG{F8s~tc&@IbB{->NXIO%=gRayV zj?<84OTK=4^YtVrcXcM$Ky96k>AE^%zG8@s^fGX$%9Ng$*GP-vN{heLge*>HoJ2BP zCd*z^1&gXN>hV@TYRGf*$jsx$cX~QM&u0Fvi|;}q!g5i*t(fRvf>`^%>Me;icuHpD zkD+3-5zCe3TdP;M7Kc7h%YQm;7Nvcqw{7{_B%WpnUzrVYE8eLXe}hnybI5w<@peOS zIhjc7`Wn}7DZtI$e=1d>8KaX;n#^X1Ks&=t!Q? z;~C8?h+N3I559G%C|`8F+vAnFk!S@O1)8ga&*W7I#$l<6xG8@K5_@Q$XKWIy=0M*0 ziEjHqZAs{jeR-34%;4vo(?8|!WJhrsK4}v`5Nh_XS-1b1}>6hk-Hco_2g;KM2P>L-<#5GvC#@Hw>9W|Dea>YE{Lc; zsW*+eM_1$lL_R>7phem|Nt~6FFR>(G5!Eh4fmP?|Vlib|x~PGsz~7V*d|fzJCX!I?Gb3%i<1UDA!$?hu||`WQiQPY#Ot&V6Z`B(NEWQDt`DV&{tZyrj7&ce?(1o-5 z_mqpX_s!+%+OeyP+UB({E)&4UjqonL`$~$qw#W167xa@5_Svjh>1Fwy$TX0xX}==} z9Zikey@WTeQWZ3!>A6Is8!;i;)evy6_mJrUurVUT+xs@E2P$;nE`8xdinrwdWjm(d zzGE~OSC>Hl3xY~!T-Pe6v>yV*S5kmK%| zF`oO=?Lbb+?B&yopOlr`iBuyv%}4Ik%wLX2W5aoBmSPI;qP>45${1v-jjxJ z-t<;le{jb4Rt(({y6}SWz!Dcd;0JmufR041p)`2DNTWJFT{lda;Kd)V+TKarT=c3R z8`c5LMMtAuNpb>1qN%mB?FJJnMfComXCbQHi9?U3mmZSI9eQHqpg6N=m1wPHa@> z%Scicjw-}1yG0nwiVWJywN(+{Bmkr}lUF|**m;!BT=!Ii1PRdY@|R${N1m><0*>m{ zjiNGV1C&iu8N)`duf*0vIr$NTWRwQT^r0*f<87 zAh+}#o@m2r_M#2A=^#Kjb-pW!FBD-dH)yi$+IF8>6h}jwcXa#*e&xHldLoTu>atDL zYyh?OsLy`!?2QA++fR>NJYCp^gR@dcE9j{%PRK=@KmnyYh3IorN8-8CtV1H^`(1G! z#M&bNn;*rW3gfd<7@*a9`*>!$M3XPf2TF(X*mx)FL~{%ow+RskX;s+n&N(Q5FeKzOC

nYqDKUb!VL;KcoSMm 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 literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/AppIcon-20@2x.png b/assets/images/logo/ios/AppIcon-20@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..947f94bed6234ba53917b26dd6fb1a8669688b9e GIT binary patch literal 1155 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 literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/AppIcon-20~ipad.png b/assets/images/logo/ios/AppIcon-20~ipad.png new file mode 100644 index 0000000000000000000000000000000000000000..4d161826703652402174ab3155c04388995be31d GIT binary patch literal 661 zcmV;G0&4wPx%Pf0{UR5(v{RljQ#Q4szfNz5f2XXBaV3{eqLIR!CR20JYbRvNRVU|}y<*w{)+ zvAS#1W-V;4@ehc_t_mSdf~4>gqk<_kD2DK4=FPkx=Vm$By|-_^`DVWF&6=#}TIgi} zSpM;Yfh_P{E?x2q7BKRj9R9ftVq^a+e*E2+ z=$NGfDnqI%x*pBU;dZkPN=5QGmadZg%X{QI1@UmLi&O}r$eT;`Q+RUj78=7fk=#Xb zn^Y3%&eCQNAAj~mu$W=QY+-5^_gk}-x(^DqvR&f!Zs`?vJ!IQRK?Ycuyp9L0Yi@}= zDP>jpD&HxQ6QHQf%}I<6;A&$U&(6n(pSynl%=|8Xl>*@Yp8i(u^5#iC=$w9J@o zXweuR!>e|N+R$h)T7*hIeDSFl*oA4JJ(O`^42*TYdpLaq^CvGyh8NRVp!aBYAp?x0wi>00000NkvXXu0mjf+k-b# literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/AppIcon-29.png b/assets/images/logo/ios/AppIcon-29.png new file mode 100644 index 0000000000000000000000000000000000000000..8fa6ef409827761ab0e8dbdef3d92be4324b016a GIT binary patch literal 900 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 QP5=M^07*qoM6N<$f?;!+kN^Mx literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/AppIcon-40@2x~ipad.png b/assets/images/logo/ios/AppIcon-40@2x~ipad.png new file mode 100644 index 0000000000000000000000000000000000000000..b0fe379f30084dbbfb0449cec42d824193b1dd66 GIT binary patch literal 1930 zcmV;52X**~P)Px+L`g(JRCr$9TuW#kRTMry)ih0PATe!BiH}ATYP43#LPZn`LD4D&ZA~|dx=^T_ z3f)vNi)?gJ(7G~(RuL4TK@?w53W8LskccHT#uOrkn3BFCX=7uw{Br(BX6B#!IOoo} zGh^?jrT@9-eCNC0ecx%Je`Kf#Rxw)xpj6&2Uds2RzW+2@R|2U~+K|zMdN^{i!S!pY*gjWSVXD z1ga7(6ak9%Es<*?J!?0>p3XjKx~@Kk8h!q;G!H+_Pr>l)sD%Mn1bku>DNq7t$C_r? zwth2gY-oks8d?n*1ko-oFP4b>aOMO*W6>H#;(4HG(6Tcm>#=n`u(fqlBJW7#x92C| zk54oL=Sg77RegtN&%qMCPZe<>Uj;)Fl!?w1~ z@Ni2Pw5@L9Vr1FREX|il#O{q<-FK-WFuB62fUhsCg09B(u)Y00*wWPDI}fFQ?Al+Q z9fJ$Yi*V)YvKI_71xir(U~?xt)7}d>LFAkVXi3){Uh%cDaYM5Wg=<&x*mrc>uy-VW~(DE2ZF;3%a`HJ z)87D&mBF0qj?_tks&M=7+DTKMJ5~Zc6%%cY@(<&e&cNX07j%CHOD6(V{yyn_Sp-lT zPW~xgg?+z#DzfAeArSYhxCP6u@MZnZ)G_l|NK8hAz#SWUVMlu}F{ENSPp|1@siJrI z%qU?`Z4bvIP_vNc63Ew!JrS-2m%u3IL`VAZ^zjsBp!-Q~4kY_U}Eyn zfrtXp5fT_Z2(28xR?c5_V~9u=OeeUEdG4n}%vx%5j|7U~^Wp?|A$w09G5aQ-Jc$uF z(ESwjtZio{tm=@~PHHu$`$STVe{tv%md4JA*7GT1AGln3vsSABmk-izyIM4sO~G z-HmOY(w1?Hcgq74pDUcXwK(ZsnCcq$!`PK&3NkK){y=lVWQb{46EYuI+7bJljpHfu zh~}Qa*t4x}<%p|pibJ${|K1l$YP1&~0d{|S3%n!7*;l#*3e=IP{C9KWcsh-z)GmcY zDaj}rJy<+DRIW)xzY`HsVr)(5!lZDWoZkz_vvu3r3A0vlhxfpE2jZiM&cb1U`1J}neB7;*vD{j`Ldy2xl_7yZm*Bbea^_yZ1v|lK4#ucA)Xs;L9Ign=nxJ-xhlAKzG-z+ z=>r}7NCvy>Z-1SKxxW{3g)_xTgqn96osNp7)-LfFNKLNBE`@I7M2Rb|ntG07V2Gru zLsvj6*;mIA`v=`D!eY4WLa=n9#}Q zZW#ErY&94J+FX%yzXl8wDv-O~l4HzoBf5BJD3D5n35M%$60yTRT&T*!PK3%s0y{Zs zbRWY;BRD9K2r+LnYl22GRdpax0tvAZBtj{D=+~TPWZ_@Sf6s`(a#mT>80FT0#_4@v z23^ojsNKSwXf=*ARbbl5`iK`HklwyjORAlZ)cpAjXLU^|kkd>gTgLG9A9@iC?aPEQ QP5=M^07*qoM6N<$f?;!+kN^Mx literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/AppIcon-40@3x.png b/assets/images/logo/ios/AppIcon-40@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..07fafe4768a76d1789e32e653c003d1c58250224 GIT binary patch literal 2602 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 FV1lBLsfGXm literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/AppIcon@3x.png b/assets/images/logo/ios/AppIcon@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..06e300f1800d4b255dd2b1be4f1c7794ec8a2356 GIT binary patch literal 3937 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 W>Z>VM@o6;tEn8$|achCg-hTs?olGwP literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/AppIcon~ipad.png b/assets/images/logo/ios/AppIcon~ipad.png new file mode 100644 index 0000000000000000000000000000000000000000..42aeac70549e887c4286ef9c048e0dab98833dcf GIT binary patch literal 1966 zcmV;f2T}NmP)Px+Xh}ptRCr#^TuW$NRT%z<)TC+Jv9XD1!;sp6gfxAmkcF{IpjNstN84^LC?*S$7Ex#w7gj-oT_~hV2AW3F(BRa^BqcU+Ff~mH%E-C%x{q`3 z`Of3c&4tp%{EzSd{{OuGdv0O_lcPD>AP)l)L$NSH7jmyY&!UtU51Lq%gy}&?nFZxI z3E*ie61Jg21sO3Tra)MQ$pSNPh7Pe61;WHeHZ)q!=ezSXe&+@!q^QvOR2T*alk!WTT{}@*Psew4(Vi_0)Kn99sQk6QN>{UKnp<6@ ziELW39zb!4DI&5V8Q)ZE5!7A3hmJI~Ly=uy$EdGrdBd^A#;_M*Z+}> zU(G3pFf~ICw1qk0fmju_Zf&BzrbE>EU_vsWqBw@<$86e~>#nV2h!Gjq6MJEDG^dbU zAs#m5*wBmO8A*@(ED#v^L70sU$s&v$)my1==OOB@Pf~o-X5(BHTWUyxGxxK!yuM1G zEu`q?>Y_0$5MfAOjyHEv@52YEwyN3~I1`50w&c6zS?LABFF6olJm7W`JGM2`>9%J~ z#OJkvWDD?o=H{0)b9Vud3>I+_riSkQ1257;)pgon%o=dU!Yb{R>5m02#PKUvSkZG^ zT@#&Y?=u@~NY-ATxk#C{td@0c!XB$n(rd}5v_Mo!*?;vcBjDDU?dW8Pu%l`_PZ_3U zmPn3Wrv9$)b|ZgH!*BJq|E5J4Gj!NiVd5D;h9M?v*5XL|Tbjt;k_F+A4M-5Six{92Y+h3P&e!Vu_18Mo}4txwazxN0{-Hv~+dbu->cj~9fI zX!&-*3JV6++jNjlB)UC9>aZ{pAgKZf)-$`jcs;*&(3rE09F6j4$zFIb76p+(XGy=! zD(}6e_O^m$d1pSml~2mv5s|~45bGK4LgC*%D?w%XzIKP zQ*wj_d33gTA}S*vfERD4tVW`V2dFSCc-CPZ**^$05dG|7eq@7Y{r#7&eZ*B0d-O{9 zz622)D`P0io^E@VI=1bSjmeli5A)pWpY+!37qAae+!kRaAofUt;#WVaRI4w>DV80$Qt-ck@Fhb5HvUIDQxRhS5|iMtbu%UVf| zy#*gGogGDp@!tao(;F~si{ZYygu_yoWT=0;w?uE;_*~8iID$f`usqR~e>qZ4u<4ai zxJudubn5Ko-97N#FT5Or5jop9xK&g#xWd3P^&^K)9nK*R@Z%#NpD=86*}3@upxo~>s`E4}*25p^TJnq?B+`}GQa zzdWbs11JKBFfcbxuy*G$vW`sbAO3K>`T&u+zR66m2e~rE!>V`#QEiAm-`qw0zN9Io zg=EOWljSc7RhXZ;N{CN3wA0Y;9*)UiYwlm!`S6p4pYp>H7)soQNm9?M%qad01G^f< z-ZUjPJ73MAT@JPy4*xPv?0@$eOeKjjmB%NH!+aP(&h6`Wk_I^W=FSX#`1=o@7y(ro zUih-mC(Qb80xhunu6!K~sNcLPq2=uf456$2}@nz;`lnn7X#N zc+Q`(kUcc2bT|FIwsvA$=Z^Y*P>8b*|)-iU~lA*!p0Wfkc8$s z=>(foP{b!D%+Ii*Lvs-Wme`8J{Tfug4kfOgt2+TgGa%x`7uE_bt}t#WQO|G^$rFtP z(eLiF_`u``3V(ry!=j{P10@xS3B?Li#Oh0`!HPklDJD3ESD0&#(0Gv`+fqh3KyJYB zzGjg~7i&>-hNL3OV literal 0 HcmV?d00001 diff --git a/assets/images/logo/ios/Contents.json b/assets/images/logo/ios/Contents.json new file mode 100644 index 0000000..bd04914 --- /dev/null +++ b/assets/images/logo/ios/Contents.json @@ -0,0 +1,134 @@ +{ + "images": [ + { + "filename": "AppIcon@2x.png", + "idiom": "iphone", + "scale": "2x", + "size": "60x60" + }, + { + "filename": "AppIcon@3x.png", + "idiom": "iphone", + "scale": "3x", + "size": "60x60" + }, + { + "filename": "AppIcon~ipad.png", + "idiom": "ipad", + "scale": "1x", + "size": "76x76" + }, + { + "filename": "AppIcon@2x~ipad.png", + "idiom": "ipad", + "scale": "2x", + "size": "76x76" + }, + { + "filename": "AppIcon-83.5@2x~ipad.png", + "idiom": "ipad", + "scale": "2x", + "size": "83.5x83.5" + }, + { + "filename": "AppIcon-40@2x.png", + "idiom": "iphone", + "scale": "2x", + "size": "40x40" + }, + { + "filename": "AppIcon-40@3x.png", + "idiom": "iphone", + "scale": "3x", + "size": "40x40" + }, + { + "filename": "AppIcon-40~ipad.png", + "idiom": "ipad", + "scale": "1x", + "size": "40x40" + }, + { + "filename": "AppIcon-40@2x~ipad.png", + "idiom": "ipad", + "scale": "2x", + "size": "40x40" + }, + { + "filename": "AppIcon-20@2x.png", + "idiom": "iphone", + "scale": "2x", + "size": "20x20" + }, + { + "filename": "AppIcon-20@3x.png", + "idiom": "iphone", + "scale": "3x", + "size": "20x20" + }, + { + "filename": "AppIcon-20~ipad.png", + "idiom": "ipad", + "scale": "1x", + "size": "20x20" + }, + { + "filename": "AppIcon-20@2x~ipad.png", + "idiom": "ipad", + "scale": "2x", + "size": "20x20" + }, + { + "filename": "AppIcon-29.png", + "idiom": "iphone", + "scale": "1x", + "size": "29x29" + }, + { + "filename": "AppIcon-29@2x.png", + "idiom": "iphone", + "scale": "2x", + "size": "29x29" + }, + { + "filename": "AppIcon-29@3x.png", + "idiom": "iphone", + "scale": "3x", + "size": "29x29" + }, + { + "filename": "AppIcon-29~ipad.png", + "idiom": "ipad", + "scale": "1x", + "size": "29x29" + }, + { + "filename": "AppIcon-29@2x~ipad.png", + "idiom": "ipad", + "scale": "2x", + "size": "29x29" + }, + { + "filename": "AppIcon-60@2x~car.png", + "idiom": "car", + "scale": "2x", + "size": "60x60" + }, + { + "filename": "AppIcon-60@3x~car.png", + "idiom": "car", + "scale": "3x", + "size": "60x60" + }, + { + "filename": "AppIcon~ios-marketing.png", + "idiom": "ios-marketing", + "scale": "1x", + "size": "1024x1024" + } + ], + "info": { + "author": "iconkitchen", + "version": 1 + } +} \ No newline at end of file diff --git a/assets/images/logo/logo.png b/assets/images/logo/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..22131921f6df0f3b0ecc46d99ade045baa33dd98 GIT binary patch literal 14021 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
>Fu-Equb1_& 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: + + + + +Add this to your app's manifest.json: + + ... + { + "icons": [ + { "src": "/favicon.ico", "type": "image/x-icon", "sizes": "16x16 32x32" }, + { "src": "/icon-192.png", "type": "image/png", "sizes": "192x192" }, + { "src": "/icon-512.png", "type": "image/png", "sizes": "512x512" }, + { "src": "/icon-192-maskable.png", "type": "image/png", "sizes": "192x192", "purpose": "maskable" }, + { "src": "/icon-512-maskable.png", "type": "image/png", "sizes": "512x512", "purpose": "maskable" } + ] + } + ... diff --git a/assets/images/logo/web/apple-touch-icon.png b/assets/images/logo/web/apple-touch-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..06e300f1800d4b255dd2b1be4f1c7794ec8a2356 GIT binary patch literal 3937 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 hMGa2H&T2g2<`_pCS#97O$_CFf#W48bR literal 0 HcmV?d00001 diff --git a/assets/images/logo/web/icon-192-maskable.png b/assets/images/logo/web/icon-192-maskable.png new file mode 100644 index 0000000000000000000000000000000000000000..ff700c5adc25c15d32b8cca8dc1369e8e870f130 GIT binary patch literal 4243 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 literal 0 HcmV?d00001 diff --git a/assets/images/logo/web/icon-512-maskable.png b/assets/images/logo/web/icon-512-maskable.png new file mode 100644 index 0000000000000000000000000000000000000000..22131921f6df0f3b0ecc46d99ade045baa33dd98 GIT binary patch literal 14021 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
>Fu-Equb1_& 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 g3{`9G0d?M5X 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 literal 0 HcmV?d00001 diff --git a/assets/images/shield-solid.svg b/assets/images/shield-solid.svg new file mode 100644 index 0000000..c6e82e1 --- /dev/null +++ b/assets/images/shield-solid.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/ios/.gitignore b/ios/.gitignore new file mode 100644 index 0000000..7a7f987 --- /dev/null +++ b/ios/.gitignore @@ -0,0 +1,34 @@ +**/dgph +*.mode1v3 +*.mode2v3 +*.moved-aside +*.pbxuser +*.perspectivev3 +**/*sync/ +.sconsign.dblite +.tags* +**/.vagrant/ +**/DerivedData/ +Icon? +**/Pods/ +**/.symlinks/ +profile +xcuserdata +**/.generated/ +Flutter/App.framework +Flutter/Flutter.framework +Flutter/Flutter.podspec +Flutter/Generated.xcconfig +Flutter/ephemeral/ +Flutter/app.flx +Flutter/app.zip +Flutter/flutter_assets/ +Flutter/flutter_export_environment.sh +ServiceDefinitions.json +Runner/GeneratedPluginRegistrant.* + +# Exceptions to above rules. +!default.mode1v3 +!default.mode2v3 +!default.pbxuser +!default.perspectivev3 diff --git a/ios/Flutter/AppFrameworkInfo.plist b/ios/Flutter/AppFrameworkInfo.plist new file mode 100644 index 0000000..7c56964 --- /dev/null +++ b/ios/Flutter/AppFrameworkInfo.plist @@ -0,0 +1,26 @@ + + + + + CFBundleDevelopmentRegion + en + CFBundleExecutable + App + CFBundleIdentifier + io.flutter.flutter.app + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + App + CFBundlePackageType + FMWK + CFBundleShortVersionString + 1.0 + CFBundleSignature + ???? + CFBundleVersion + 1.0 + MinimumOSVersion + 12.0 + + diff --git a/ios/Flutter/Debug.xcconfig b/ios/Flutter/Debug.xcconfig new file mode 100644 index 0000000..ec97fc6 --- /dev/null +++ b/ios/Flutter/Debug.xcconfig @@ -0,0 +1,2 @@ +#include? "Pods/Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig" +#include "Generated.xcconfig" diff --git a/ios/Flutter/Release.xcconfig b/ios/Flutter/Release.xcconfig new file mode 100644 index 0000000..c4855bf --- /dev/null +++ b/ios/Flutter/Release.xcconfig @@ -0,0 +1,2 @@ +#include? "Pods/Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig" +#include "Generated.xcconfig" diff --git a/ios/Podfile b/ios/Podfile new file mode 100644 index 0000000..c9339a0 --- /dev/null +++ b/ios/Podfile @@ -0,0 +1,41 @@ +# Uncomment this line to define a global platform for your project +# platform :ios, '12.0' + +# CocoaPods analytics sends network stats synchronously affecting flutter build latency. +ENV['COCOAPODS_DISABLE_STATS'] = 'true' + +project 'Runner', { + 'Debug' => :debug, + 'Profile' => :release, + 'Release' => :release, +} + +def flutter_root + generated_xcode_build_settings_path = File.expand_path(File.join('..', 'Flutter', 'Generated.xcconfig'), __FILE__) + unless File.exist?(generated_xcode_build_settings_path) + raise "#{generated_xcode_build_settings_path} must exist. If you're running pod install manually, make sure flutter pub get is executed first" + end + + File.foreach(generated_xcode_build_settings_path) do |line| + matches = line.match(/FLUTTER_ROOT\=(.*)/) + return matches[1].strip if matches + end + raise "FLUTTER_ROOT not found in #{generated_xcode_build_settings_path}. Try deleting Generated.xcconfig, then run flutter pub get" +end + +require File.expand_path(File.join('packages', 'flutter_tools', 'bin', 'podhelper'), flutter_root) + +flutter_ios_podfile_setup + +target 'Runner' do + flutter_install_all_ios_pods File.dirname(File.realpath(__FILE__)) + target 'RunnerTests' do + inherit! :search_paths + end +end + +post_install do |installer| + installer.pods_project.targets.each do |target| + flutter_additional_ios_build_settings(target) + end +end diff --git a/ios/Runner.xcodeproj/project.pbxproj b/ios/Runner.xcodeproj/project.pbxproj new file mode 100644 index 0000000..b485680 --- /dev/null +++ b/ios/Runner.xcodeproj/project.pbxproj @@ -0,0 +1,616 @@ +// !$*UTF8*$! +{ + archiveVersion = 1; + classes = { + }; + objectVersion = 54; + objects = { + +/* Begin PBXBuildFile section */ + 1498D2341E8E89220040F4C2 /* GeneratedPluginRegistrant.m in Sources */ = {isa = PBXBuildFile; fileRef = 1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */; }; + 331C808B294A63AB00263BE5 /* RunnerTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 331C807B294A618700263BE5 /* RunnerTests.swift */; }; + 3B3967161E833CAA004F5970 /* AppFrameworkInfo.plist in Resources */ = {isa = PBXBuildFile; fileRef = 3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */; }; + 74858FAF1ED2DC5600515810 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 74858FAE1ED2DC5600515810 /* AppDelegate.swift */; }; + 97C146FC1CF9000F007C117D /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FA1CF9000F007C117D /* Main.storyboard */; }; + 97C146FE1CF9000F007C117D /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FD1CF9000F007C117D /* Assets.xcassets */; }; + 97C147011CF9000F007C117D /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FF1CF9000F007C117D /* LaunchScreen.storyboard */; }; +/* End PBXBuildFile section */ + +/* Begin PBXContainerItemProxy section */ + 331C8085294A63A400263BE5 /* PBXContainerItemProxy */ = { + isa = PBXContainerItemProxy; + containerPortal = 97C146E61CF9000F007C117D /* Project object */; + proxyType = 1; + remoteGlobalIDString = 97C146ED1CF9000F007C117D; + remoteInfo = Runner; + }; +/* End PBXContainerItemProxy section */ + +/* Begin PBXCopyFilesBuildPhase section */ + 9705A1C41CF9048500538489 /* Embed Frameworks */ = { + isa = PBXCopyFilesBuildPhase; + buildActionMask = 2147483647; + dstPath = ""; + dstSubfolderSpec = 10; + files = ( + ); + name = "Embed Frameworks"; + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXCopyFilesBuildPhase section */ + +/* Begin PBXFileReference section */ + 1498D2321E8E86230040F4C2 /* GeneratedPluginRegistrant.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GeneratedPluginRegistrant.h; sourceTree = ""; }; + 1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GeneratedPluginRegistrant.m; sourceTree = ""; }; + 331C807B294A618700263BE5 /* RunnerTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RunnerTests.swift; sourceTree = ""; }; + 331C8081294A63A400263BE5 /* RunnerTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = RunnerTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; + 3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; name = AppFrameworkInfo.plist; path = Flutter/AppFrameworkInfo.plist; sourceTree = ""; }; + 74858FAD1ED2DC5600515810 /* Runner-Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Runner-Bridging-Header.h"; sourceTree = ""; }; + 74858FAE1ED2DC5600515810 /* AppDelegate.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; + 7AFA3C8E1D35360C0083082E /* Release.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; name = Release.xcconfig; path = Flutter/Release.xcconfig; sourceTree = ""; }; + 9740EEB21CF90195004384FC /* Debug.xcconfig */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xcconfig; name = Debug.xcconfig; path = Flutter/Debug.xcconfig; sourceTree = ""; }; + 9740EEB31CF90195004384FC /* Generated.xcconfig */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xcconfig; name = Generated.xcconfig; path = Flutter/Generated.xcconfig; sourceTree = ""; }; + 97C146EE1CF9000F007C117D /* Runner.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Runner.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 97C146FB1CF9000F007C117D /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; + 97C146FD1CF9000F007C117D /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; + 97C147001CF9000F007C117D /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; + 97C147021CF9000F007C117D /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; +/* End PBXFileReference section */ + +/* Begin PBXFrameworksBuildPhase section */ + 97C146EB1CF9000F007C117D /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXFrameworksBuildPhase section */ + +/* Begin PBXGroup section */ + 331C8082294A63A400263BE5 /* RunnerTests */ = { + isa = PBXGroup; + children = ( + 331C807B294A618700263BE5 /* RunnerTests.swift */, + ); + path = RunnerTests; + sourceTree = ""; + }; + 9740EEB11CF90186004384FC /* Flutter */ = { + isa = PBXGroup; + children = ( + 3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */, + 9740EEB21CF90195004384FC /* Debug.xcconfig */, + 7AFA3C8E1D35360C0083082E /* Release.xcconfig */, + 9740EEB31CF90195004384FC /* Generated.xcconfig */, + ); + name = Flutter; + sourceTree = ""; + }; + 97C146E51CF9000F007C117D = { + isa = PBXGroup; + children = ( + 9740EEB11CF90186004384FC /* Flutter */, + 97C146F01CF9000F007C117D /* Runner */, + 97C146EF1CF9000F007C117D /* Products */, + 331C8082294A63A400263BE5 /* RunnerTests */, + ); + sourceTree = ""; + }; + 97C146EF1CF9000F007C117D /* Products */ = { + isa = PBXGroup; + children = ( + 97C146EE1CF9000F007C117D /* Runner.app */, + 331C8081294A63A400263BE5 /* RunnerTests.xctest */, + ); + name = Products; + sourceTree = ""; + }; + 97C146F01CF9000F007C117D /* Runner */ = { + isa = PBXGroup; + children = ( + 97C146FA1CF9000F007C117D /* Main.storyboard */, + 97C146FD1CF9000F007C117D /* Assets.xcassets */, + 97C146FF1CF9000F007C117D /* LaunchScreen.storyboard */, + 97C147021CF9000F007C117D /* Info.plist */, + 1498D2321E8E86230040F4C2 /* GeneratedPluginRegistrant.h */, + 1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */, + 74858FAE1ED2DC5600515810 /* AppDelegate.swift */, + 74858FAD1ED2DC5600515810 /* Runner-Bridging-Header.h */, + ); + path = Runner; + sourceTree = ""; + }; +/* End PBXGroup section */ + +/* Begin PBXNativeTarget section */ + 331C8080294A63A400263BE5 /* RunnerTests */ = { + isa = PBXNativeTarget; + buildConfigurationList = 331C8087294A63A400263BE5 /* Build configuration list for PBXNativeTarget "RunnerTests" */; + buildPhases = ( + 331C807D294A63A400263BE5 /* Sources */, + 331C807F294A63A400263BE5 /* Resources */, + ); + buildRules = ( + ); + dependencies = ( + 331C8086294A63A400263BE5 /* PBXTargetDependency */, + ); + name = RunnerTests; + productName = RunnerTests; + productReference = 331C8081294A63A400263BE5 /* RunnerTests.xctest */; + productType = "com.apple.product-type.bundle.unit-test"; + }; + 97C146ED1CF9000F007C117D /* Runner */ = { + isa = PBXNativeTarget; + buildConfigurationList = 97C147051CF9000F007C117D /* Build configuration list for PBXNativeTarget "Runner" */; + buildPhases = ( + 9740EEB61CF901F6004384FC /* Run Script */, + 97C146EA1CF9000F007C117D /* Sources */, + 97C146EB1CF9000F007C117D /* Frameworks */, + 97C146EC1CF9000F007C117D /* Resources */, + 9705A1C41CF9048500538489 /* Embed Frameworks */, + 3B06AD1E1E4923F5004D2608 /* Thin Binary */, + ); + buildRules = ( + ); + dependencies = ( + ); + name = Runner; + productName = Runner; + productReference = 97C146EE1CF9000F007C117D /* Runner.app */; + productType = "com.apple.product-type.application"; + }; +/* End PBXNativeTarget section */ + +/* Begin PBXProject section */ + 97C146E61CF9000F007C117D /* Project object */ = { + isa = PBXProject; + attributes = { + BuildIndependentTargetsInParallel = YES; + LastUpgradeCheck = 1510; + ORGANIZATIONNAME = ""; + TargetAttributes = { + 331C8080294A63A400263BE5 = { + CreatedOnToolsVersion = 14.0; + TestTargetID = 97C146ED1CF9000F007C117D; + }; + 97C146ED1CF9000F007C117D = { + CreatedOnToolsVersion = 7.3.1; + LastSwiftMigration = 1100; + }; + }; + }; + buildConfigurationList = 97C146E91CF9000F007C117D /* Build configuration list for PBXProject "Runner" */; + compatibilityVersion = "Xcode 9.3"; + developmentRegion = en; + hasScannedForEncodings = 0; + knownRegions = ( + en, + Base, + ); + mainGroup = 97C146E51CF9000F007C117D; + productRefGroup = 97C146EF1CF9000F007C117D /* Products */; + projectDirPath = ""; + projectRoot = ""; + targets = ( + 97C146ED1CF9000F007C117D /* Runner */, + 331C8080294A63A400263BE5 /* RunnerTests */, + ); + }; +/* End PBXProject section */ + +/* Begin PBXResourcesBuildPhase section */ + 331C807F294A63A400263BE5 /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; + 97C146EC1CF9000F007C117D /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 97C147011CF9000F007C117D /* LaunchScreen.storyboard in Resources */, + 3B3967161E833CAA004F5970 /* AppFrameworkInfo.plist in Resources */, + 97C146FE1CF9000F007C117D /* Assets.xcassets in Resources */, + 97C146FC1CF9000F007C117D /* Main.storyboard in Resources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXResourcesBuildPhase section */ + +/* Begin PBXShellScriptBuildPhase section */ + 3B06AD1E1E4923F5004D2608 /* Thin Binary */ = { + isa = PBXShellScriptBuildPhase; + alwaysOutOfDate = 1; + buildActionMask = 2147483647; + files = ( + ); + inputPaths = ( + "${TARGET_BUILD_DIR}/${INFOPLIST_PATH}", + ); + name = "Thin Binary"; + outputPaths = ( + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" embed_and_thin"; + }; + 9740EEB61CF901F6004384FC /* Run Script */ = { + isa = PBXShellScriptBuildPhase; + alwaysOutOfDate = 1; + buildActionMask = 2147483647; + files = ( + ); + inputPaths = ( + ); + name = "Run Script"; + outputPaths = ( + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" build"; + }; +/* End PBXShellScriptBuildPhase section */ + +/* Begin PBXSourcesBuildPhase section */ + 331C807D294A63A400263BE5 /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 331C808B294A63AB00263BE5 /* RunnerTests.swift in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + 97C146EA1CF9000F007C117D /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 74858FAF1ED2DC5600515810 /* AppDelegate.swift in Sources */, + 1498D2341E8E89220040F4C2 /* GeneratedPluginRegistrant.m in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXSourcesBuildPhase section */ + +/* Begin PBXTargetDependency section */ + 331C8086294A63A400263BE5 /* PBXTargetDependency */ = { + isa = PBXTargetDependency; + target = 97C146ED1CF9000F007C117D /* Runner */; + targetProxy = 331C8085294A63A400263BE5 /* PBXContainerItemProxy */; + }; +/* End PBXTargetDependency section */ + +/* Begin PBXVariantGroup section */ + 97C146FA1CF9000F007C117D /* Main.storyboard */ = { + isa = PBXVariantGroup; + children = ( + 97C146FB1CF9000F007C117D /* Base */, + ); + name = Main.storyboard; + sourceTree = ""; + }; + 97C146FF1CF9000F007C117D /* LaunchScreen.storyboard */ = { + isa = PBXVariantGroup; + children = ( + 97C147001CF9000F007C117D /* Base */, + ); + name = LaunchScreen.storyboard; + sourceTree = ""; + }; +/* End PBXVariantGroup section */ + +/* Begin XCBuildConfiguration section */ + 249021D3217E4FDB00AE95B9 /* Profile */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES; + CLANG_ANALYZER_NONNULL = YES; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_COMMA = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_STRICT_PROTOTYPES = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CLANG_WARN_UNREACHABLE_CODE = YES; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; + COPY_PHASE_STRIP = NO; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + ENABLE_NS_ASSERTIONS = NO; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_USER_SCRIPT_SANDBOXING = NO; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_NO_COMMON_BLOCKS = YES; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; + MTL_ENABLE_DEBUG_INFO = NO; + SDKROOT = iphoneos; + SUPPORTED_PLATFORMS = iphoneos; + TARGETED_DEVICE_FAMILY = "1,2"; + VALIDATE_PRODUCT = YES; + }; + name = Profile; + }; + 249021D4217E4FDB00AE95B9 /* Profile */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 7AFA3C8E1D35360C0083082E /* Release.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ENABLE_MODULES = YES; + CURRENT_PROJECT_VERSION = "$(FLUTTER_BUILD_NUMBER)"; + ENABLE_BITCODE = NO; + INFOPLIST_FILE = Runner/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/Frameworks", + ); + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; + SWIFT_VERSION = 5.0; + VERSIONING_SYSTEM = "apple-generic"; + }; + name = Profile; + }; + 331C8088294A63A400263BE5 /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + BUNDLE_LOADER = "$(TEST_HOST)"; + CODE_SIGN_STYLE = Automatic; + CURRENT_PROJECT_VERSION = 1; + GENERATE_INFOPLIST_FILE = YES; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect.RunnerTests; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; + SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + SWIFT_VERSION = 5.0; + TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Runner.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/Runner"; + }; + name = Debug; + }; + 331C8089294A63A400263BE5 /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + BUNDLE_LOADER = "$(TEST_HOST)"; + CODE_SIGN_STYLE = Automatic; + CURRENT_PROJECT_VERSION = 1; + GENERATE_INFOPLIST_FILE = YES; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect.RunnerTests; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_VERSION = 5.0; + TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Runner.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/Runner"; + }; + name = Release; + }; + 331C808A294A63A400263BE5 /* Profile */ = { + isa = XCBuildConfiguration; + buildSettings = { + BUNDLE_LOADER = "$(TEST_HOST)"; + CODE_SIGN_STYLE = Automatic; + CURRENT_PROJECT_VERSION = 1; + GENERATE_INFOPLIST_FILE = YES; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect.RunnerTests; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_VERSION = 5.0; + TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Runner.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/Runner"; + }; + name = Profile; + }; + 97C147031CF9000F007C117D /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = AppIcon; + CLANG_ANALYZER_NONNULL = YES; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_COMMA = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_STRICT_PROTOTYPES = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CLANG_WARN_UNREACHABLE_CODE = YES; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; + COPY_PHASE_STRIP = NO; + DEBUG_INFORMATION_FORMAT = dwarf; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_TESTABILITY = YES; + ENABLE_USER_SCRIPT_SANDBOXING = NO; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_DYNAMIC_NO_PIC = NO; + GCC_NO_COMMON_BLOCKS = YES; + GCC_OPTIMIZATION_LEVEL = 0; + GCC_PREPROCESSOR_DEFINITIONS = ( + "DEBUG=1", + "$(inherited)", + ); + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; + MTL_ENABLE_DEBUG_INFO = YES; + ONLY_ACTIVE_ARCH = YES; + SDKROOT = iphoneos; + TARGETED_DEVICE_FAMILY = "1,2"; + }; + name = Debug; + }; + 97C147041CF9000F007C117D /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = AppIcon; + CLANG_ANALYZER_NONNULL = YES; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_COMMA = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_STRICT_PROTOTYPES = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CLANG_WARN_UNREACHABLE_CODE = YES; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; + COPY_PHASE_STRIP = NO; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + ENABLE_NS_ASSERTIONS = NO; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_USER_SCRIPT_SANDBOXING = NO; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_NO_COMMON_BLOCKS = YES; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + IPHONEOS_DEPLOYMENT_TARGET = 12.0; + MTL_ENABLE_DEBUG_INFO = NO; + SDKROOT = iphoneos; + SUPPORTED_PLATFORMS = iphoneos; + SWIFT_COMPILATION_MODE = wholemodule; + SWIFT_OPTIMIZATION_LEVEL = "-O"; + TARGETED_DEVICE_FAMILY = "1,2"; + VALIDATE_PRODUCT = YES; + }; + name = Release; + }; + 97C147061CF9000F007C117D /* Debug */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 9740EEB21CF90195004384FC /* Debug.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ENABLE_MODULES = YES; + CURRENT_PROJECT_VERSION = "$(FLUTTER_BUILD_NUMBER)"; + ENABLE_BITCODE = NO; + INFOPLIST_FILE = Runner/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/Frameworks", + ); + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; + SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + SWIFT_VERSION = 5.0; + VERSIONING_SYSTEM = "apple-generic"; + }; + name = Debug; + }; + 97C147071CF9000F007C117D /* Release */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 7AFA3C8E1D35360C0083082E /* Release.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ENABLE_MODULES = YES; + CURRENT_PROJECT_VERSION = "$(FLUTTER_BUILD_NUMBER)"; + ENABLE_BITCODE = NO; + INFOPLIST_FILE = Runner/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/Frameworks", + ); + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; + SWIFT_VERSION = 5.0; + VERSIONING_SYSTEM = "apple-generic"; + }; + name = Release; + }; +/* End XCBuildConfiguration section */ + +/* Begin XCConfigurationList section */ + 331C8087294A63A400263BE5 /* Build configuration list for PBXNativeTarget "RunnerTests" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 331C8088294A63A400263BE5 /* Debug */, + 331C8089294A63A400263BE5 /* Release */, + 331C808A294A63A400263BE5 /* Profile */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + 97C146E91CF9000F007C117D /* Build configuration list for PBXProject "Runner" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 97C147031CF9000F007C117D /* Debug */, + 97C147041CF9000F007C117D /* Release */, + 249021D3217E4FDB00AE95B9 /* Profile */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + 97C147051CF9000F007C117D /* Build configuration list for PBXNativeTarget "Runner" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 97C147061CF9000F007C117D /* Debug */, + 97C147071CF9000F007C117D /* Release */, + 249021D4217E4FDB00AE95B9 /* Profile */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; +/* End XCConfigurationList section */ + }; + rootObject = 97C146E61CF9000F007C117D /* Project object */; +} diff --git a/ios/Runner.xcodeproj/project.xcworkspace/contents.xcworkspacedata b/ios/Runner.xcodeproj/project.xcworkspace/contents.xcworkspacedata new file mode 100644 index 0000000..919434a --- /dev/null +++ b/ios/Runner.xcodeproj/project.xcworkspace/contents.xcworkspacedata @@ -0,0 +1,7 @@ + + + + + diff --git a/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist b/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist new file mode 100644 index 0000000..18d9810 --- /dev/null +++ b/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist @@ -0,0 +1,8 @@ + + + + + IDEDidComputeMac32BitWarning + + + diff --git a/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings b/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings new file mode 100644 index 0000000..f9b0d7c --- /dev/null +++ b/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings @@ -0,0 +1,8 @@ + + + + + PreviewsEnabled + + + diff --git a/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme b/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme new file mode 100644 index 0000000..8e3ca5d --- /dev/null +++ b/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme @@ -0,0 +1,98 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/ios/Runner.xcworkspace/contents.xcworkspacedata b/ios/Runner.xcworkspace/contents.xcworkspacedata new file mode 100644 index 0000000..1d526a1 --- /dev/null +++ b/ios/Runner.xcworkspace/contents.xcworkspacedata @@ -0,0 +1,7 @@ + + + + + diff --git a/ios/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist b/ios/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist new file mode 100644 index 0000000..18d9810 --- /dev/null +++ b/ios/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist @@ -0,0 +1,8 @@ + + + + + IDEDidComputeMac32BitWarning + + + diff --git a/ios/Runner.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings b/ios/Runner.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings new file mode 100644 index 0000000..f9b0d7c --- /dev/null +++ b/ios/Runner.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings @@ -0,0 +1,8 @@ + + + + + PreviewsEnabled + + + diff --git a/ios/Runner/AppDelegate.swift b/ios/Runner/AppDelegate.swift new file mode 100644 index 0000000..6266644 --- /dev/null +++ b/ios/Runner/AppDelegate.swift @@ -0,0 +1,13 @@ +import Flutter +import UIKit + +@main +@objc class AppDelegate: FlutterAppDelegate { + override func application( + _ application: UIApplication, + didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]? + ) -> Bool { + GeneratedPluginRegistrant.register(with: self) + return super.application(application, didFinishLaunchingWithOptions: launchOptions) + } +} diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json new file mode 100644 index 0000000..d0d98aa --- /dev/null +++ b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json @@ -0,0 +1 @@ +{"images":[{"size":"20x20","idiom":"iphone","filename":"Icon-App-20x20@2x.png","scale":"2x"},{"size":"20x20","idiom":"iphone","filename":"Icon-App-20x20@3x.png","scale":"3x"},{"size":"29x29","idiom":"iphone","filename":"Icon-App-29x29@1x.png","scale":"1x"},{"size":"29x29","idiom":"iphone","filename":"Icon-App-29x29@2x.png","scale":"2x"},{"size":"29x29","idiom":"iphone","filename":"Icon-App-29x29@3x.png","scale":"3x"},{"size":"40x40","idiom":"iphone","filename":"Icon-App-40x40@2x.png","scale":"2x"},{"size":"40x40","idiom":"iphone","filename":"Icon-App-40x40@3x.png","scale":"3x"},{"size":"57x57","idiom":"iphone","filename":"Icon-App-57x57@1x.png","scale":"1x"},{"size":"57x57","idiom":"iphone","filename":"Icon-App-57x57@2x.png","scale":"2x"},{"size":"60x60","idiom":"iphone","filename":"Icon-App-60x60@2x.png","scale":"2x"},{"size":"60x60","idiom":"iphone","filename":"Icon-App-60x60@3x.png","scale":"3x"},{"size":"20x20","idiom":"ipad","filename":"Icon-App-20x20@1x.png","scale":"1x"},{"size":"20x20","idiom":"ipad","filename":"Icon-App-20x20@2x.png","scale":"2x"},{"size":"29x29","idiom":"ipad","filename":"Icon-App-29x29@1x.png","scale":"1x"},{"size":"29x29","idiom":"ipad","filename":"Icon-App-29x29@2x.png","scale":"2x"},{"size":"40x40","idiom":"ipad","filename":"Icon-App-40x40@1x.png","scale":"1x"},{"size":"40x40","idiom":"ipad","filename":"Icon-App-40x40@2x.png","scale":"2x"},{"size":"50x50","idiom":"ipad","filename":"Icon-App-50x50@1x.png","scale":"1x"},{"size":"50x50","idiom":"ipad","filename":"Icon-App-50x50@2x.png","scale":"2x"},{"size":"72x72","idiom":"ipad","filename":"Icon-App-72x72@1x.png","scale":"1x"},{"size":"72x72","idiom":"ipad","filename":"Icon-App-72x72@2x.png","scale":"2x"},{"size":"76x76","idiom":"ipad","filename":"Icon-App-76x76@1x.png","scale":"1x"},{"size":"76x76","idiom":"ipad","filename":"Icon-App-76x76@2x.png","scale":"2x"},{"size":"83.5x83.5","idiom":"ipad","filename":"Icon-App-83.5x83.5@2x.png","scale":"2x"},{"size":"1024x1024","idiom":"ios-marketing","filename":"Icon-App-1024x1024@1x.png","scale":"1x"}],"info":{"version":1,"author":"xcode"}} \ No newline at end of file diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-1024x1024@1x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-1024x1024@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..7030e7fb42da4ea988dfd580eb1e5993ce7d5d98 GIT binary patch literal 11537 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 literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..6155983bc3e53b3efc3a698985c4636abdd942e8 GIT binary patch literal 1221 zcmeAS@N?(olHy`uVBq!ia0vp^8X(NU3?z3ec*HX>F#Qei32_B-8UFuo_}>t^YL&zO zhO{#?L$9v#ygeyl|NPKneZFUA#$H?$dUdMbk-5<)CWW4v8E}4n)TL>m$L0i{oDvCC zd~ROs#p#hJW`~}d8gpi5#JRbl7p6y_m>qFyDo}CMxj7N%r-z=L9d&wII8gD~IZ@|l zgrA%hdU_gAZ}{2Sq332qo|+YYdOA>X@b+(FtA>r;;_@RB2Ui%>J2+PEAs4&@Y6uWGr)Rhg`J%daT;jR44~qO zv$Mj_f)q!<6i1MzcxL$NnPF!@7KNXg6>%2C4L<|6=nT;0nGs+v$RaQ|>@<)8b`?x9 zP%p?;XMnE4rx<7yvPD3}U@k}_Pzq=)*isN1C=Rg#k9&Zwg}4Wkx|hxv2pPUiAl*RscGpMnOWI6xq0~og+;|B zrDf$6l~vU>wRQCkjZMuht!?ccon75My?y-?CrzF*b^45%vu4kkJ8%Aig^Lz1S-Ncb zij}KYuUWfp{f3R3HgDOwZTpU$yLRu{yKn!2gNF_uIeP5)iIb;JpE-N({Dq5`E?>EN z?fQ+Iw{G9Ld++{(hmRgVdHU@6iqJ1UYZ?p#t^+bENfp{zV- z(v?#(?rW1aFG-DCdpb?Z$Thg!^U&N+?dKhSrS5C_VqVRdHtAmLuOiU|mFGv(_#GIl wE?KxUv8$FiSoPU1QJ$St{h%cCOkUP9*{TMaK6}2L)1dOm)78&qol`;+0LY?*KL7v# literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..9d67b0369efe9cc956baa385df1cea2bfdfceaf0 GIT binary patch literal 1316 zcmeAS@N?(olHy`uVBq!ia0vp^HXzKw3=&b&bYNg$`WxUA;tJ$4{QuwZzaezhDu?|I zX=i4JUR~vRds4#w`Ju=9e9z2`y|^g!>QuiYbE8j83OzG3;QaikOVdJ+%?Ug?B@(Fk z+`QO}(<4vJ4m~wB=FH59b8|y4OpiV>JL1$-pyH@=b0W@94?Q_M>h!d5pyIQ0qR!6< zKRGM(^faK}@Uyc+&&`NDH7oq|bfDtMv$Mm`%?Ld;E8_HYu;SSf=VpYT0xF&!0aF}t zYE~Fnam3l#VKBvEV7)-aVW($Bo}K~J8+LY9SSC{DK)6nV4Bv+1NQaxwv_F z`S=9{g@i>!#l$5frKDwK<>VC*^aCo0?l%+uA!iySjUN`}!wNnmlFd^cgc}&7L!N-uwj%7cE}0blLJ1 zD_5;vvv%G34I4LY-m-Pu_8mKS?cTF@-~Iy!4;?;o^w{weCr_O|bN1Z%3l}e4zH;^2 z^&2;D-M(}8-u(v;A3c8Z^x5+lFJHZW^Y-2Q4a!-~a#L`VTDw z2E}zx7srqa#;4b8xeghK9Qe3h<3;J7rq$*JA46j2%IujsS@hsR$LVZ2BGD_~|7KnC zBYw8LzJL_dfwJfJ#0U7 zMK_i$RN3}IU;1!WZ$!qFZ3hb;I4-`{(mM0dIn6bazEQ1dYgR;RXB^xVwPoUWv&Ere t&!f6Bn`Minb5~nencd#@%2T`QAam+Pug?9l?{z`Nou{jx%Q~loCIE)(yC(nu literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..07cff37cd67746653cb5a0e49f8e1ecb9b5371ea GIT binary patch literal 1192 zcmeAS@N?(olHy`uVBq!ia0vp^vLMXC3?vhMr`s|xF#Qei32_B-8UFuo_}>t^YL&zO zhO{#?L$9v#ygeyl|NPKneZFUA#$H?$dUdMbk-5<)CWW4v8E}4n)TL>m$L0i{oDvCC zd~ROs#p#hJW`~}d8gpi5#JRbl7p6y_m>qFyDo}CMxj7N%r-z=L9d&wII8gD~IZ@|l zgrA%hdU_gAZ}{2Sq332qo|+YYdOA>X@b+(FtA>r;;_@RB2Ui%>J2+PEAs4&@Y6uWGr)Rhg`J%daT;jR44~qO zv$Mj_f)q!<6i1MzcxL$NnPF!@7KNXg6>%2C4L<|6=nT;0nGs+v$RaQ|>@<)8b`?x9 zP%p?;XMnE4rx<7yvPD3}U@k}_Pzq=)*isN1C=Rg#k9&Zwg}4Wkx|hxv2pPUiAl*RscGpMnOWI6xq0~og+;|B zrDf$6l~vU>wRQCkjZMuht!?ccon75My?y-?CrzF*b^45%vu4kkJ8%Aig^Lz1S-Ncb zij}KYuUWfp{f3R3HgDOwZTpU$yLRu{yKn!2gNF_uIeP5)iIb;JpE-N({Dq5`E?>EN z?fQ+Iw{G9Ld++{(hmRgVdHU@6i5D#oBTygR*w7?N@{X@1!4A^jdm5m5pDwRQ2he SS_d9bk>ly==d#Wzp$Pz519r;* literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..c1c790f6ff63ad0b53007ebf8902a98a3ba2f9cc GIT binary patch literal 1308 zcmeAS@N?(olHy`uVBq!ia0vp^Rv^s53?#3m?vi3)VEP;26XFWwGW`GF@V_B+)hdVm z4QXd)hF)Fed3#dA{`sND`h3sKjJ>!h^y*ZebaG>I|bE3}A z2tPS1^z<~K-te=tL(k2KJT)u)^mL%&$g{J<&&>!uH7nxubg<&t5$9%vp8_hL9syGv zacWi=SaHPJ*Dm zXJ>_<1u2ezDUKjb@yzhkGsDh+EDAp}E8;AO8-50C(HWr0Gb6xUkVRl_*l8dG>?)XI zpk9!x&H!D7PchIaWQ%}`!Ca6=pcK$pu%#e2P#j_f9`^uU3vmxzaTwSfOe=uK0v(TR z3n)l26yx$ZszpF^C`Dk$fDFN8fP;}t^Z)<<|B+W!2$cRyg8YIR7@3$^SlQS)IJvla zc=`AR1cih}M8(7Lc_u%BBP>XV&mcy5|ffsQq$5iGPAOCa`W;F3X6(M zO3TVCDyyn%YU}D78k?G1THD$?I=i}idi(k(PMSPr>hu{iXU(27ci#L33l}Y3vUJ(< z6)RV*UbA-H`VAX5ZQinV+x8thckSM@ci;X42M--Sa`f2o6DLodK6Ccm`3n~>UA}Vl z+VvYZZ{5Cg_ul;n4<9{#^7PsB7cXDEe)IO-`wt&Keg5+G+xH(ofBpXR_uv2j-}(uQk%?v-wLZnyDv?K05qaB^7BFLUV5^_h&E z|89RMWKx_gkQsYrbe95(V{-yePKg96 zJ~uD+;`GQ9vqMi!jX5(j;@sTO3)7=d%#JuU6{tAs+?(?d_rjygRp9H{v0oT&3N z!cWc$Jv|MmH~j4E&~q~)Pt6KHJsqex^6c#Jb2CCu&5AfZ9jthE#JL&ar+|v5N5B+E zoSGE|RvdA5b{I@?7+5b*aoFiuk*8+>^@g3D6?t|>_-UZx8DPD$!p_c!I1RLD22gRt z*;(OdL5d?_iX%uci^9*$iZ~16hMxgjbOvbh%m^?SWD%Gfb{fb4y9%Zl zs2Aj_GeB42Qw%f;*&?7~Fc+i|CS+nQNoi~5M!bOXhEM2yI z#mZHy*Q{N)e#6F1o40J;wtdIWUAy<}-M9b1!9$0S96fgY#K}{q&zwDX{=&sem#&lpTB(l_Wj4tU%&tS{rCU>xBf%R z7#J9XJzX3_Dj471*z3jYD01}U><+c4n@820xTF=$>}K4EcpkV$r-pfU!}*Eo9BU>x zZICh$w*O?hx%&N`;;z=e*H8B!KD24K@}m5W1~F^i8s+Rdw(9hU`&`T0niXDrUMN-l zd6niB+h02CkLg_qwq0zxD)!ncwVwwU9ZP$$^3_H2)U2FY;r6Gm-Vp!9_U3qC|5I%d z=|deG&D@g8A8@@6o3r!wK^5_{{|?T*y>s_F?OC-y3)M5q@0@$Sqxj@I;c2xg`|n$Q z-!80jTl`!?=0@(8rC0S{R`0FVkT*wiB>t8RYY@>*_A;@*O3 zOLyw+Xj{6IZ^tyGXW$cJGzq{(YMd{?Xd^ODZ W?e!YTBC)GLMXjf+pUXO@geCyJ>HB{G literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..6155983bc3e53b3efc3a698985c4636abdd942e8 GIT binary patch literal 1221 zcmeAS@N?(olHy`uVBq!ia0vp^8X(NU3?z3ec*HX>F#Qei32_B-8UFuo_}>t^YL&zO zhO{#?L$9v#ygeyl|NPKneZFUA#$H?$dUdMbk-5<)CWW4v8E}4n)TL>m$L0i{oDvCC zd~ROs#p#hJW`~}d8gpi5#JRbl7p6y_m>qFyDo}CMxj7N%r-z=L9d&wII8gD~IZ@|l zgrA%hdU_gAZ}{2Sq332qo|+YYdOA>X@b+(FtA>r;;_@RB2Ui%>J2+PEAs4&@Y6uWGr)Rhg`J%daT;jR44~qO zv$Mj_f)q!<6i1MzcxL$NnPF!@7KNXg6>%2C4L<|6=nT;0nGs+v$RaQ|>@<)8b`?x9 zP%p?;XMnE4rx<7yvPD3}U@k}_Pzq=)*isN1C=Rg#k9&Zwg}4Wkx|hxv2pPUiAl*RscGpMnOWI6xq0~og+;|B zrDf$6l~vU>wRQCkjZMuht!?ccon75My?y-?CrzF*b^45%vu4kkJ8%Aig^Lz1S-Ncb zij}KYuUWfp{f3R3HgDOwZTpU$yLRu{yKn!2gNF_uIeP5)iIb;JpE-N({Dq5`E?>EN z?fQ+Iw{G9Ld++{(hmRgVdHU@6iqJ1UYZ?p#t^+bENfp{zV- z(v?#(?rW1aFG-DCdpb?Z$Thg!^U&N+?dKhSrS5C_VqVRdHtAmLuOiU|mFGv(_#GIl wE?KxUv8$FiSoPU1QJ$St{h%cCOkUP9*{TMaK6}2L)1dOm)78&qol`;+0LY?*KL7v# literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..baa889efc8d368af95a84c4d84782f9949fb9013 GIT binary patch literal 1433 zcmeAS@N?(olHy`uVBq!ia0vp^0U*r53?z4+XPVEz!1Oo3C&U%VW%&QU;eSKus#OmA z8`93q486L_^Y)~K{qsYQ_4%He8GCV2=+&uyN9IPKm=tqg*YRs9L5$EQHUYH(zVs^x-sX)b1=jKG5pB{R0cGT%<;XuV_=R}>K z5q@%3=;>)dz2RqPhn|}ed1_Yp>FGelk!NRzpPLbSYF5PQ>0rgPBhJkTKLu1gJp!gU z;?%4#u;Pfbv%_GD!@zohio;INiab37s5k8FtjM!7!cPMg&j9P46?S$;#A%>KGk}UC z&dv%y3sM{bQyf8>;+f&6XNH{tSrmR|R>WBlH~b9PqBB5~XGVazAdA4R5g0U3hH00$$P=Kufy|0A!e5GehZ1o;IsFfuW-u(GjpaB^|; z@bd8s2nq>{h>D3zNJ>e|$jZqpC@LwdsH&-JXliNe=<4Yk7#bOyn3|beSXx=z*xK1U zI667IxVpJ}czSvJ`1<(=1O^3%gocGjL`Fr&#Ky%ZBqk-Nq^6~3WM*aOECr+L^edg@B^A|2&x_ss8 zwd*%--nxC~?!EgD9zJ^flG{`&pr@4x^5zx5wl z#=yYn zwc(OOjOXMAN#`qP&%OEcZ;!~Nzt;}8o1cBhu&L_vybnuOJhd`%SDHWlXH6EP*m=R?sHmErNq+`=TJGJ4)1E(Z%2}@x zw8viQ^8VHSn%r-KOa2Fc6O@@~`|orkf1S`CrYD^@bS(<1 z%N6{OtUD;YynGLDm3o*>NzA=e(J#I|6%~aQYb9RHl=xbZ_U+u`1+__sjJrMi`EMPO zI+lOEo?igj9SN5|B??eWV_e#w-+CI=d=-V5YwPbE|Y4pRqn7Gm<)3qmavx(2DEjB)RQNLKRIp1N!QXfzm N>*?y}vd$@?2>^Al?U?`o literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..604603d3e0c449389bab4609fec748f201172f35 GIT binary patch literal 1672 zcmbuA2~ZPf7={B@Kp-eoL8yWvhlt_@Qj3B{K%;_y?h!~TB3Bhqxhu6&NI|fb%9YI~ zfMA=p0W4}$P^u6>nqxPJilBm+qId-g9%w;{f8x-w!pIHziMgGu0Ma<=srg`)d1VDmN~&{EXubagr;6s~DVk0iKIhmd|F zKeV9?YCYmda9QmYP)Ct}OG$_%A0oH`ZDqliilJ71ptO(yU_~jbox_muAXyQU;G&8W z=prXX!b4?601j60(KZewtIxW{^BYfk84H zm2}9B0TeFbk77gTxRyfHCbX4wD!v2Sylx zQ4&W;4UA5}=)Z%xh@1-(8Y6_jQBu<)gw}`v%3M_2YK*ikEC+=))dUP?HK_=Y>Rm99 zdeaEN+Ez0NZUI@Xsip?kUt7E*4@mnu&tEXC)p^?j$b#^1x@ea4E%=`v{O?9U=l^cn zFdC7!3+*!gM}4(gJxsMX)4czQLH=7QI=YkIo2;jAFvZZwm})Y0nyK0Q(`T4l%(S%n zVAgDFn>llB=h@jiIL>!k;Jk2=%i<+Vmo0a7TjBoU%8xu&t@iXmzwb^9u@#I2ae_@k>g}j+Iv&|Mok<_don7tgNa&@l(yo zQ>T9x{Zd!*sc5^{e(Ca+j;ozr*RJ2_?z!1}OZj`> z?K}N<@7;g!P&F|4$I$Sj$4{P)JbV7<=-7*w<7)LtUXuWP6FlhNYqzE93|#lvI4N*u zma@0rce2GCM&>>9pqvV$Y2wxy=o#IVZ{R7x^9_;>ubMk8s?MLEy3WTalcSTcEIQI5 zDpGN$VY=c*cJ>~cgOpC`t`zOI&P%Q~W5+%^MIP&1ZZl?T7Z%u?zpHkITP1WqDyoK^ zXrB#L_np>TAXY8i3A<%p7(`DBS;iv-4t1>VU^%+QTq`;EBosp8s>aPDI_pK(X#vfp zFEzi%e>gF*UCo>zPhn!E3r7#mD#x^gSoQa|Q=R9v6izTy(G1^W2 za%n)L+0e@4X@;}{Wm)som_gPo>#$7yzM3vei5J@)>lWE9Om1}0f6RP1?o7He`efqc z#)F4U`mw4cWlr~jE6qV(RD-6ZuxGYZK`H-1>o}6J-FbHLsCd&fLE&;1t?no_uRwgw zMR|J_wo#F!#9Lzfn_Ua2Ow@j_gHIwsLcqn0aSI zRxIfccec=DGt;No)rK22o93p)4A`zFO$A?QLQ=T7(6DEH zyI^aVQ&{cgk}N-uVxKrqv0}JJxQku==wy!-OQakfvcc_aqVpPdL}-2~bRU236SUBb ESCPhL>;M1& literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-50x50@1x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-50x50@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..97f65d55238f353d24169e6140517465bbcb325e GIT binary patch literal 1254 zcmeAS@N?(olHy`uVBq!ia0vp^Mj*_=3?wxlRx~p(F#Qei32_B-8UFuo_}>t^YL&zO zhO{#?L$9v#ygeyl|NPKneZFUA#$H?$dUdMbk-5<)CWW4v8E}4n)TL>m$L0i{oDvCC zd~ROs#p#hJW`~}d8gpi5#JRbl7p6y_m>qFyDo}CMxj7N%r-z=L9d&wII8gD~IZ@|l zgrA%hdU_gAZ}{2Sq332qo|+YYdOA>X@b+(FtA>r;;_@RB2Ui%>J2+PEAs4&@Y6uWGr)Rhg`J%daT;jR44~qO zv$Mj_f)q!<6i1MzcxL$NnPF!@7KNXg6>%2C4L<|6=nT;0nGs+v$RaQ|>@<)8b`?x9 zP%p?;XMnE4rx<7yvPD3}U@k}_Pzq=)*isN1C=Rg#k9&Zwg}4Wkx|hxv2pPUiAl*RscGpMnOWI6xq0~og+;|B zrDf$6l~vU>wRQCkjZMuht!?ccon75My?y-?CrzF*b^45%vu4kkJ8%Aig^Lz1S-Ncb zij}KYuUWfp{f3R3HgDOwZTpU$yLRu{yKn!2gNF_uIeP5)iIb;JpE-N({Dq5`E?>EN z?fQ+Iw{G9Ld++{(hmRgVdHU@6i@VR2RR!IcvvsId3<(rw#5qV4(A=6%bUUkyM1T<5$R(8Z))>z;S$A3 zn>vN)ZCLgtbqTgS-g9c10!y&Snn0Jnk`HET6P2_r eF3nw#o^EaXs_4wonu+e90?X6Y&t;ucLK6Va?2YgM literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-50x50@2x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-50x50@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..9e5aaeae547ffbe81ca461bc6b52576cc427fbe1 GIT binary patch literal 1543 zcmeAS@N?(olHy`uVBq!ia0vp^DIme95(V{-yePKg96 zJ~uD+;`GQ9vqMi!jX5(j;@sTO3)7=d%#JuU6{tAs+?(?d_rjygRp9H{v0oT&3N z!cWc$Jv|MmH~j4E&~q~)Pt6KHJsqex^6c#Jb2CCu&5AfZ9jthE#JL&ar+|v5N5B+E zoSGE|RvdA5b{I@?7+5b*aoFiuk*8+>^@g3D6?t|>_-UZx8DPD$!p_c!I1RLD22gRt z*;(OdL5d?_iX%uci^9*$iZ~16hMxgjbOvbh%m^?SWD%Gfb{fb4y9%Zl zs2Aj_GeB42Qw%f;*&?7~Fc+i|CS+nQNoi~5M!bOXhEM2yI z#mZHy*Q{N)e#6F1o40J;wtdIWUAy<}-M9b1!9$0S96fgY#K}{q&zwDX{=&sem#&lpTB(l_Wj4tU%&tS{rCU>xBf%R z7#J9LdAc};R4~51Y3Rl5D01xM`G%yG8Oh1Xs!EGmr-pkd-{=w$u;!njcB6ttn%lN9 zW3>X?LGF$Uw%!FE8%{P!il0oId-B}u%J-}(|NcHZZmua*#*lS(z1mO7DC5X`i)0Gt z^Hxn$+*HKHVtsj&&@y4YLz*AXu2hhiq04`0i?GfWo7O!q1s?Ud%y<>D$XU%NmP=6O zNhQ~A!IqaBX6@)v@yXp-EOky(XQSYfi2`wrrijQ6RSbE!D=_fm7oLD{MBU7uUhlj={&6G9HiCkYMZtEyyZq<}v zza(m4ce>-q6#HZLPCrDu7dF2!maaBysqVUZfPMAHJok#_7Cf>o!G%&4DaP~ebR6nF zS9jd!*hP(&>{A}io+}MX1o)O-y5RUolwUdOqtOPb)HOd93xjQVdtWcpXiZ?zR$(r7 zJf_3TxodHDNPUjxFVnj!HyPG-9?NZDoHMECvjX!9;hwh+%ricjHR+wI|7?=P5wCiQ z;hq-f_5E={myB&h)R<=!2$`BOughO{*mH)8f7XSX&Ikd6Uu#7=cqJb#U(o!EEm(5@ UnGG!a4}eN^Pgg&ebxsLQ03)6WNB{r; literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-57x57@1x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-57x57@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..e09f1bcc47d2ac6b9507a59f77b583afc3c3abbe GIT binary patch literal 1308 zcmeAS@N?(olHy`uVBq!ia0vp^mLSZ*3?z3SE8fn)!1Oo3C&U%VW%&QU;eSKus#OmA z8`93q486L_^Y)~K{qsYQ_4%He8GCV2=+&uyN9IPKm=tqg*YRs9L5$EQHUYH(zVs^x-sX)b1=jKG5pB{R0cGT%<;XuV_=R}>K z5q@%3=;>)dz2RqPhn|}ed1_Yp>FGelk!NRzpPLbSYF5PQ>0rgPBhJkTKLu1gJp!gU z;?%4#u;Pfbv%_GD!@zohio;INiab37s5k8FtjM!7!cPMg&j9P46?S$;#A%>KGk}UC z&dv%y3sM{bQyf8>;+f&6XNH{tSrmR|R>WBlH~b9PqBB5~XGVazAdA4R5g0U3hH00$$P=Kufy|0A!e5GehZ1o;IsFfuW-u(GjpaB^|; z@bd8s2nq>{h>D3zNJ>e|$jZqpC@LwdsH&-JXliNe=<4Yk7#bOyn3|beSXx=z*xK1U zI667IxVpJ}czSvJ`1<(=1O^3%gocGjL`Fr&#Ky%ZBqk-Nq^6~3WM*aOECr+L^edg@B^A|2&x_ss8 zwd*%--nxC~?!EgD9zJ^flG{`&pr@4x^5zx5wl z1`LYxo-U3d6^u`>*>W9n5IFjAXXDiLjT^U!=Im*n8~%~Q$>GSM=!ir+__pcuU>h%#hfp-_NzVqS%YzdQ&-Z?(&xVgiVsJ1f&9jc&W&ePS;Wt~$(69CyWweF#Qei32_B-8UFuo_}>t^YL&zO zhO{#?L$9v#ygeyl|NPKneZFUA#$H?$dUdMbk-5<)CWW4v8E}4n)TL>m$L0i{oDvCC zd~ROs#p#hJW`~}d8gpi5#JRbl7p6y_m>qFyDo}CMxj7N%r-z=L9d&wII8gD~IZ@|l zgrA%hdU_gAZ}{2Sq332qo|+YYdOA>X@b+(FtA>r;;_@RB2Ui%>J2+PEAs4&@Y6uWGr)Rhg`J%daT;jR44~qO zv$Mj_f)q!<6i1MzcxL$NnPF!@7KNXg6>%2C4L<|6=nT;0nGs+v$RaQ|>@<)8b`?x9 zP%p?;XMnE4rx<7yvPD3}U@k}_Pzq=)*isN1C=Rg#k9&Zwg}4Wkx|hxv2pPUiAl*RscGpMnOWI6xq0~og+;|B zrDf$6l~vU>wRQCkjZMuht!?ccon75My?y-?CrzF*b^45%vu4kkJ8%Aig^Lz1S-Ncb zij}KYuUWfp{f3R3HgDOwZTpU$yLRu{yKn!2gNF_uIeP5)iIb;JpE-N({Dq5`E?>EN z?fQ+Iw{G9Ld++{(hmRgVdHU@6i&m>#`+uqQ?Qh3r+%oZ&;+|9R;Pmqq(KI75fEv zSSBh&bR~!fzmU#Yn6O%dt!WZ-esM-pk-YV8Op4q5TF0x>{69oFR?T`6r+DSF)nb2{}9sQh~D)(8BgbTWfQxX1ZRwTRJLxX8eM#t$TN*OYG zrZ3E7xy~7N@p8nLXYZwm?RzY)at+-mK&=sebREf{*R&f WXz}%SpRjaLwc+XN=d#Wzp$Py`6*=<& literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..604603d3e0c449389bab4609fec748f201172f35 GIT binary patch literal 1672 zcmbuA2~ZPf7={B@Kp-eoL8yWvhlt_@Qj3B{K%;_y?h!~TB3Bhqxhu6&NI|fb%9YI~ zfMA=p0W4}$P^u6>nqxPJilBm+qId-g9%w;{f8x-w!pIHziMgGu0Ma<=srg`)d1VDmN~&{EXubagr;6s~DVk0iKIhmd|F zKeV9?YCYmda9QmYP)Ct}OG$_%A0oH`ZDqliilJ71ptO(yU_~jbox_muAXyQU;G&8W z=prXX!b4?601j60(KZewtIxW{^BYfk84H zm2}9B0TeFbk77gTxRyfHCbX4wD!v2Sylx zQ4&W;4UA5}=)Z%xh@1-(8Y6_jQBu<)gw}`v%3M_2YK*ikEC+=))dUP?HK_=Y>Rm99 zdeaEN+Ez0NZUI@Xsip?kUt7E*4@mnu&tEXC)p^?j$b#^1x@ea4E%=`v{O?9U=l^cn zFdC7!3+*!gM}4(gJxsMX)4czQLH=7QI=YkIo2;jAFvZZwm})Y0nyK0Q(`T4l%(S%n zVAgDFn>llB=h@jiIL>!k;Jk2=%i<+Vmo0a7TjBoU%8xu&t@iXmzwb^9u@#I2ae_@k>g}j+Iv&|Mok<_don7tgNa&@l(yo zQ>T9x{Zd!*sc5^{e(Ca+j;ozr*RJ2_?z!1}OZj`> z?K}N<@7;g!P&F|4$I$Sj$4{P)JbV7<=-7*w<7)LtUXuWP6FlhNYqzE93|#lvI4N*u zma@0rce2GCM&>>9pqvV$Y2wxy=o#IVZ{R7x^9_;>ubMk8s?MLEy3WTalcSTcEIQI5 zDpGN$VY=c*cJ>~cgOpC`t`zOI&P%Q~W5+%^MIP&1ZZl?T7Z%u?zpHkITP1WqDyoK^ zXrB#L_np>TAXY8i3A<%p7(`DBS;iv-4t1>VU^%+QTq`;EBosp8s>aPDI_pK(X#vfp zFEzi%e>gF*UCo>zPhn!E3r7#mD#x^gSoQa|Q=R9v6izTy(G1^W2 za%n)L+0e@4X@;}{Wm)som_gPo>#$7yzM3vei5J@)>lWE9Om1}0f6RP1?o7He`efqc z#)F4U`mw4cWlr~jE6qV(RD-6ZuxGYZK`H-1>o}6J-FbHLsCd&fLE&;1t?no_uRwgw zMR|J_wo#F!#9Lzfn_Ua2Ow@j_gHIwsLcqn0aSI zRxIfccec=DGt;No)rK22o93p)4A`zFO$A?QLQ=T7(6DEH zyI^aVQ&{cgk}N-uVxKrqv0}JJxQku==wy!-OQakfvcc_aqVpPdL}-2~bRU236SUBb ESCPhL>;M1& literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..29535b16f5c5a063e57303b10a2f50a5961806e2 GIT binary patch literal 2207 zcmbuBc~leE9>)_?&;WxVs>JkG2lrnMg<(N0QCJn)N5}9g z!ayosP=gt)I@(9a^D1DNAgIOXE8jfED z!=VrzC!k<>G(5jb3DfZc3XTWERrrrEo=3wfVLU{~euS~gUKqymX`y@y+>3>1p%4Yf zhhd7cmxhHXcs^`IfnhvE!$Ard{}IOjZ!i_dr(!{c5e}r`A;lC2Dvdx`nTl6V6-LS_ zmJb)oR3BluSCI;YQ~enXOa0LZhLuxABm4@MRhlYlc>Q;aKgk29{XNgWVXRW;QwvxY z4*y3N#g={o|F;kSPa|08uU^V93Xx9>h&{Ra-Zx*c-&@bvQb@%8f$2s|7Vj6M>A!Q$|tgri}^@QBE$=$K<)kz#@4aVO#v z5|d7zN=`X_CN(WRBlGOJtn9CI&gbS`xcE(e!KK2Y%U6m^$YteME2=0|8oj!vmchJM zSKn~Gv8nk+OKV#@>*n8Yb#$_CbN+FM+jaNbd-oqa{O6;`-95ce`ucf%5E2Xw3PnTW z;in_dB%@>Bjer0A#SardPQILaCH-l7MmGEU=U?XD%rCrMeD~{bOUv&+tjOhyC65|a zRMwz<++9P`SIv&|{q&*?p3GTT?HO+dHk~i!SQhC2u&WTeiK8>hUcXaS!z7GTDpmCm z_SUS`6V%dMC&~|K*k8YP)&CwIS+{jwtI|w|n%pvC0JQHmlL=-!K)DmOiu+6(xtjxN zOfYMJ=!TV$lxur0cvhZvb2AhdH?GXKBDv2Tk!h^;z7xzq>x{6xuy|eb#KA3Uv#zBh zUVF0Qt|UyFGaR<4ojFptwSB@MX#?PZfBrmWE8&JweowvY@4zo$l6vf&88?Xb3?aYr_LKjB|vkoN=DZ7 zBrI}=0t*@8MQxq&R#nwXNfR&8IIn!FfdbL4={-sCKM7C!KJ?iv&f~kbO zw`(KZ>2O)Vi!gZ!H2Mm6*Sg$_kmwJcVSBY$T?d{!Hs$dcZ3oXb)EPn{#ZxVYS!!Bk zQmk_(im)Sip~wOtyKhPA0mG-OMGj}aF&_A zV1u->5k95^xMQC3ykh4T0AZmO?};DJaN{nWHDB( zNt!+s^J)g?x@;R~mIBU|7pxl|%)U$z`j-s8;J$9H%QCp#LA_t!e^KKMGFyxw-68P( zf4(-Qoe9XA?IEN(Qd?R_u7Bz<nvOPaO1`E|&lj`jCp;jt*>{Qe|dG5VU#CUE1 literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-72x72@1x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-72x72@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..06a81f53394c1f6e63a75631cb1b1bb26c928cd3 GIT binary patch literal 1357 zcmeAS@N?(olHy`uVBq!ia0vp^9w5xY3?!3`ol6-QnEnR%gt!8^4FCT({BHe95(V{-yePKg96 zJ~uD+;`GQ9vqMi!jX5(j;@sTO3)7=d%#JuU6{tAs+?(?d_rjygRp9H{v0oT&3N z!cWc$Jv|MmH~j4E&~q~)Pt6KHJsqex^6c#Jb2CCu&5AfZ9jthE#JL&ar+|v5N5B+E zoSGE|RvdA5b{I@?7+5b*aoFiuk*8+>^@g3D6?t|>_-UZx8DPD$!p_c!I1RLD22gRt z*;(OdL5d?_iX%uci^9*$iZ~16hMxgjbOvbh%m^?SWD%Gfb{fb4y9%Zl zs2Aj_GeB42Qw%f;*&?7~Fc+i|CS+nQNoi~5M!bOXhEM2yI z#mZHy*Q{N)e#6F1o40J;wtdIWUAy<}-M9b1!9$0S96fgY#K}{q&zwDX{=&sem#&lpTB(l_Wj4tU%&tS{rCU>xBf%R z7#J8CJY5_^Dj45hU(0(aK&0)V@Wbr6|;1AOR`dA6 z^qAI}xUzRV6A&yKv4lk&=6tEO>k!9M>;llv=>}s%2VYI%8e$ALA{2 zR@y&K?{61)!+g_OLn-jQ;(nL?O?xg)Z*F!|I6iYqvrW*ogN_UA|5vdu-uzf0Tj=$H zJa@B|mlrO+Wm)R{OXZ+rtn1ZDhZ^s0GM#iuP<5-a2U~l_F{9$ihutG3{faCsPaVIa lE&S|V*`*a6mlrKb=ASPbW8dz%zzb9^db;|#taD0e0szLd!*Kur literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-72x72@2x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-72x72@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..c72472a55b27b6d4759dcf693bbadf3f0cc95899 GIT binary patch literal 1903 zcmbuA3pA8@7{*8A&KSuh(yZL3qKn89vzd&TRhF0=k#d)!(7IH{HO8$*=5Ab4G@&+D zZq<+#W`;2vMK_g86iFo&JNwOa>}gMDJ7;&#`7ZDK{eSQCJm3F(=X_c2Zq5*8J!KFG z1VOu?_5k->_+qaKO=wxEL3-|Kr_?{w+km}RP z#CI10uy+p&-%G`GF}-;d8~_Vg-n}$j7X!ni0JAs&6VpQ@bTe=~DgYA%Ok58Q)6Ky1 zs8X1T@1fzk0ho$kg7Mu9tQ5uznAjy4E1d;kERR9p(STX3fI$$@a6AB}NoN^Y0S(Us zjA#Ii7cg)F35;KY@&68{<9Ku|Ut)ygGw=dQi{nd;_<%AUFKs18(iY1D3Tdh(7?_o$ z;sdF^1p`uF8Ue7hl?(z)fUMM1QUlLFTYMuAkoI$)zhJCX=W7c<76|{Pi)2f`g8%8o z|84~6{NFGFRs4o_aUqehZB;S9`9yd>r%rda7oVR2rSZWEHWCOG?Ymm7l**QF)Pbsj9l> z@|9n%*4F)6f32ahsk!C)jho!owp;DLb=>ak>gMqUJ-xy{(eHQq2kzb*9J>GD;iJdH zPo6#-866vcJ~8>?<<#`6nb)&#-oBfAKmXz5r-j8o#NxU9whJH-*bt3Edd101J+M2d z>7mJey#kq)lDsljOEw)JS~?GjNV6iPtZi*;+Y!+&8rWIqX=I8-uqIQ&+urAFv?43(5e|?75~ZBCMn03a7W(` zvUP$Cc8<-?i0(ggt|_;M@T|0JRr^TQo3To3|05K48&2d(R&S_&;j0tViX78dRkgu( z$)>#m$BrY02!qkeu?U-{5EYi6UijWf^^H?^qIc@ra;^(lclr95=2j!Fhg`=+6QzWY zBow0S4QagEd@VuspaVLnuiO@$A6ignddT>SOl-c(5E(P8iuSphp)7=lxelD-Vyjw$ zMdT!>(>01BEo76S3r;57)${5j&60J%deO2NuOV`51E`u>A6S^AU05H8lno;p_##uW z=Pkm_f`koqrc*Yu^}*^$MiVky#G1WzDx6veAMAsW_gQ9^h*!t>-HWc#F-DY;;3-W^ zPRe0Y3Wq&&EVT_RP)gu5d$t)(zQ{7z@Vt%|(z4y zJSqb=-#S9*^Ne#2e3`7B9m2HD3_)qbC{&U45OLV7@%Efh$+lAjE@)>f`KY(R-?h}v zr5zI*Pk~B9id8bBP!%luG(%@7y>k$(V$8-(8_-N=_;GPA+5(=V!R*_T>=wl4lu6_V zupA01uQ0647~i6%I3+vkZ4BjFYWA+Mf^q|7dyP;~ZrZhqlVa|M$JJ$)ov@jOxo6QJ zd3$@Xra``LUlhy9H4sKjRbxA*!H59^?1FOG6+i26x1k)l5JoFl+wtiW;za2JA_BHq zPXn&-);adtmPFAu2n%yEZ!!Q<5%!qbp#FnBVsWx>fihZtXks>kGB%PcxIh`S$Z=hi YJ5U#C-iWiPlKeT*PHw209sVhQ0`U{caR2}S literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..a7a6f67cd8af0ca823d012d54a006edbb1e518da GIT binary patch literal 1391 zcmeAS@N?(olHy`uVBq!ia0vp^J|N7&3?x5zE|g?oVEP;26XFWwGW`GF@V_B+)hdVm z4QXd)hF)Fed3#dA{`sND`h3sKjJ>!h^y*ZebaG>I|bE3}A z2tPS1^z<~K-te=tL(k2KJT)u)^mL%&$g{J<&&>!uH7nxubg<&t5$9%vp8_hL9syGv zacWi=SaHPJ*Dm zXJ>_<1u2ezDUKjb@yzhkGsDh+EDAp}E8;AO8-50C(HWr0Gb6xUkVRl_*l8dG>?)XI zpk9!x&H!D7PchIaWQ%}`!Ca6=pcK$pu%#e2P#j_f9`^uU3vmxzaTwSfOe=uK0v(TR z3n)l26yx$ZszpF^C`Dk$fDFN8fP;}t^Z)<<|B+W!2$cRyg8YIR7@3$^SlQS)IJvla zc=`AR1cih}M8(7Lc_u%BBP>XV&mcy5|ffsQq$5iGPAOCa`W;F3X6(M zO3TVCDyyn%YU}D78k?G1THD$?I=i}idi(k(PMSPr>hu{iXU(27ci#L33l}Y3vUJ(< z6)RV*UbA-H`VAX5ZQinV+x8thckSM@ci;X42M--Sa`f2o6DLodK6Ccm`3n~>UA}Vl z+VvYZZ{5Cg_ul;n4<9{#^7PsB7cXDEe)IO-`wt&Keg5+G+xH(ofBpXR_uv2j-}(@_8fN!bsrj_9VeM=ia0?3C_}h+RC6+#dxE7JKxZ zOL_O0rKRH4hmZb~4HO^g*e+f3T*CTUUO3Ct>CG-vcfVL!{BQ5eydkj;o84W zRe?31U$0*ve{8}1hHVM4o2LpG^v*go%}rZ5LCUn9*Y{dOL#DjgTApiMT8zKDv#3aopJ23$64p>?m74I`~C0d_x*nF|J-x#J|Ay)Ep;Px z6bhx~vBuRGxw91K)Je$Ic2syXc5xA{5K+2>xbAi@Ex`Yk39R)g= z{>@ylwGe@6Z9K4@3AAu&;vxzH!#r9$i_*dY#6`#~1?B>6ENUx1D7i?ouS`nBDeucqS4p|95dte)#USzskyV;1YGnP3#SiizX}{$83nnXdzPCVRk?`NTD7N%F_@7?< z??#Bu|2>pp6e8aj%5D6Q`f|Dajh6W|#rL1!>+Oe9`DxN*)t{$KRa4i{)Y8_`)tjbo zfHuTTpJ6m})@9SuOmakapxXQ`dWwk58 z&3%o>TB4_y_d1{TzJ4TtOaZAhe|kXRhM?e$n?gdv!Xq|EMn%VL*%}-7Ykb1C#O+Bt zl6US(*}W%~k(RzUBQq;|Urz4+yaNXh=NB9)WU|;CF7Ie@$+6@7(i3InCr_OgRGc|m zc@C;NUoE_F@i$RTZQZ5%%U2q%HeS1aqv>XIORHD{x3zajZ*|_5b=|q!eXr;KgNMIA zdi9fA)FJAT!3=X||{l}ZP?}kT4-+%b{X>9!Sgj_y)u(2G4nzYBm)tQu}GIXC9 zW#DX(`M4n0g>IGYk1?^b66vFDb)Pth-sy;RO>;izxW@LjWz6rlnyHH3n~IsHIwfFw z$Mx)EbD!j$GINfPiH%I=z2dxNSN1!cysSQ4XUxg+TREe)cDZY`7P-$leOFd*q(u(b zef4l3|HLyJVc(v1eqVWqnJh_zIARR9l5VH~@v}jJxn|V7EMUy!LpaU|B3Z9=1h#4d zaV05Lj$jpO!-`W|z=|hsA=GQC)J7qC3K^#-bEg2f(dr?6L?^dkBt5U}6MUjpEXbJ| zAD%ZABH8jt&ofAI%-r)fIp;}~9B6k=HE9nP@C_%E4a0l<4q|1*MP1hISXmEUrt5^> zE-2M#^1ToqlU2))pk(*vh!g7FD)@u8D)&g|ZpbnWWl`OSozso%Ys#g?Zk-J6Gn+%& zr5sWzL)&xCjC=eGMnRTR!?XHo(V8*RWL`tq+f_qVw^iS)xW^w^%6PLyMKp?Icpb;l z3e*PGkTpCbz};V1X#vGY(PMQ?-&i-}jB)7Ipvt8`!pDjPUviJ=xpOn@Qr3ohNP$o0%x@|+vGW;G

w~Q3VxEmJ zcbr9(y#gwzSR(q7uzx5bc!ykHdeMJ@%xiJ^X~sUQ$c?E3v2v7#Xm22I6@jVvEqf5W KT`OIJ(*6Vi$^Ml9 literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png b/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..9539c828845a1f5a6c1281f255ea58a9e450da51 GIT binary patch literal 2069 zcmbuA2~ZPf7=}|R)`Or@1O>%{XdqIg9M*6YP*8#)lE7vYC`Vh4h^=ykdKII9913Vi z$Yv9+0CFg(90C?Wv2rBY1(c(WKs^8(sanC(VyWpS9Xstf?M&O5-G9Gt_xaxU-G6pw zGySPM@k>mW;BYuR*~g2HT`M%_A{}hq-rYKe!!7vLpAzVewK%n!tL6gL)gJBKD1`_Z ztR~;#g|`<0ojHCAQAocO7!**yDhTf80Sb|SZ&A>#e4tZ8>*2F77%dFx7qYs=fK2eA zLc~N1fIeYxx0optU~mvBVfG4v9&wO7AH-lp64VQUJuo28$7Vr944@E827_`T2D1<` zh(dr2X3B+HSj)m<|~*fgBe_(TKcWXt(h{>Z{f2XZQ^Un(sf6P7T1lu|Vfd-Gy&0TD)Yb9$tUh z@)ZVe8?H1mUbWi9bj@0`b?=y4thd~-kzi#_++_2v?Pk08>>V7Pw!FWU-93Emyv5z1r4(?Rv+JuWojBb@#~R3Iy%#>%Vn-U~p*o>u;2I zMn=cJy?gKegYk*Uhu^6lO@06P$|kMifc#ITzPu5?bh`P(HYHq%^=u> z9i?VYCJ(BcxcOy?&1R~t%Jolu+-NRJ{-<_ThS|j-XJU56PxzYlT^UpcoZiHdrb$7T zZ@;Nse5t-YdlR*V6=ogNVdaAGrJ-us;)L?=#Nar3q`TOyjem8EFRgvqL_-bT@#(6A zr*&2*4y>*_vut%kPujFi6Mf)j%^FUL;nirbeQ{}eO0@L*q;rO&m%-$u3x>$o))n(s z-tO`1gXhgt^e1Suzc8{E`Uw&im3NO{35!pgazLhDnxCgT@@wX~TNe67+4Z+I-r`eH zr|GjF?DUl17o=8krL;Or#Y1-9dEo>UU~gqoM(i9pF^I@8m~?8`5we>! zc}hR)av4B6cuvv^P{)Xb{erwESx@l9cuoAYQBqFvdyhiX3xs_p9OD}(hn?-5l{!?3 zv4Y!krU=c+m^0>eI4~sF8NZJ|6Fgr_Y1p|Epbp(fce78o=EgnT)8G?2ofC(x$62Hr zU+1S%a@`9ax~-5%5Z!eBAu_4Wqm<_+APtuSJth(80<#0w^^T}1o6&04QXiW_gv#UE zyl+Uet0j0gs{xj=F6vx}xU~Q_vVGh{WCu4JM(vU0_BS`0m6Mh_vWeKN1A8oHtqSeX zgRk3UC+OkzOyu!K5q%U4tYJ$lH{4-mcsfA?DLaOyz(k4es=$+(>fvd!8{vq*-^PM2 z`(Bmv^^_O~6_Iz4_3h%d16(p8R`JP3>fPcU6lL1SPqrj7?B1rXO?j`CE+FviL{|wnt<+~?g)_iY2 zJ|R=2dem3%FzT_^F2tk2ZmuK;8u5>&gjR0fNEoorTlNU*(dD3)@FkFXINV^gK631* z4ohWp*T_^RIVp^O)VJ=y303k1ip-^I|3rJCXj2gmA|dsDq?w}l`74gBmgDgXcg literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/LaunchImage.imageset/Contents.json b/ios/Runner/Assets.xcassets/LaunchImage.imageset/Contents.json new file mode 100644 index 0000000..0bedcf2 --- /dev/null +++ b/ios/Runner/Assets.xcassets/LaunchImage.imageset/Contents.json @@ -0,0 +1,23 @@ +{ + "images" : [ + { + "idiom" : "universal", + "filename" : "LaunchImage.png", + "scale" : "1x" + }, + { + "idiom" : "universal", + "filename" : "LaunchImage@2x.png", + "scale" : "2x" + }, + { + "idiom" : "universal", + "filename" : "LaunchImage@3x.png", + "scale" : "3x" + } + ], + "info" : { + "version" : 1, + "author" : "xcode" + } +} diff --git a/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage.png b/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage.png new file mode 100644 index 0000000000000000000000000000000000000000..9da19eacad3b03bb08bbddbbf4ac48dd78b3d838 GIT binary patch literal 68 zcmeAS@N?(olHy`uVBq!ia0vp^j3CUx0wlM}@Gt=>Zci7-kcv6Uzs@r-FtIZ-&5|)J Q1PU{Fy85}Sb4q9e0B4a5jsO4v literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@2x.png b/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..9da19eacad3b03bb08bbddbbf4ac48dd78b3d838 GIT binary patch literal 68 zcmeAS@N?(olHy`uVBq!ia0vp^j3CUx0wlM}@Gt=>Zci7-kcv6Uzs@r-FtIZ-&5|)J Q1PU{Fy85}Sb4q9e0B4a5jsO4v literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@3x.png b/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..9da19eacad3b03bb08bbddbbf4ac48dd78b3d838 GIT binary patch literal 68 zcmeAS@N?(olHy`uVBq!ia0vp^j3CUx0wlM}@Gt=>Zci7-kcv6Uzs@r-FtIZ-&5|)J Q1PU{Fy85}Sb4q9e0B4a5jsO4v literal 0 HcmV?d00001 diff --git a/ios/Runner/Assets.xcassets/LaunchImage.imageset/README.md b/ios/Runner/Assets.xcassets/LaunchImage.imageset/README.md new file mode 100644 index 0000000..89c2725 --- /dev/null +++ b/ios/Runner/Assets.xcassets/LaunchImage.imageset/README.md @@ -0,0 +1,5 @@ +# Launch Screen Assets + +You can customize the launch screen with your own desired assets by replacing the image files in this directory. + +You can also do it by opening your Flutter project's Xcode project with `open ios/Runner.xcworkspace`, selecting `Runner/Assets.xcassets` in the Project Navigator and dropping in the desired images. \ No newline at end of file diff --git a/ios/Runner/Base.lproj/LaunchScreen.storyboard b/ios/Runner/Base.lproj/LaunchScreen.storyboard new file mode 100644 index 0000000..f2e259c --- /dev/null +++ b/ios/Runner/Base.lproj/LaunchScreen.storyboard @@ -0,0 +1,37 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/ios/Runner/Base.lproj/Main.storyboard b/ios/Runner/Base.lproj/Main.storyboard new file mode 100644 index 0000000..f3c2851 --- /dev/null +++ b/ios/Runner/Base.lproj/Main.storyboard @@ -0,0 +1,26 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/ios/Runner/Info.plist b/ios/Runner/Info.plist new file mode 100644 index 0000000..78131c2 --- /dev/null +++ b/ios/Runner/Info.plist @@ -0,0 +1,53 @@ + + + + + CFBundleDevelopmentRegion + $(DEVELOPMENT_LANGUAGE) + CFBundleDisplayName + Connect + CFBundleExecutable + $(EXECUTABLE_NAME) + CFBundleIdentifier + $(PRODUCT_BUNDLE_IDENTIFIER) + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + connect + CFBundlePackageType + APPL + CFBundleShortVersionString + $(FLUTTER_BUILD_NAME) + CFBundleSignature + ???? + CFBundleVersion + $(FLUTTER_BUILD_NUMBER) + LSRequiresIPhoneOS + + UILaunchStoryboardName + LaunchScreen + UIMainStoryboardFile + Main + UISupportedInterfaceOrientations + + UIInterfaceOrientationPortrait + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + + UISupportedInterfaceOrientations~ipad + + UIInterfaceOrientationPortrait + UIInterfaceOrientationPortraitUpsideDown + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + + CADisableMinimumFrameDurationOnPhone + + UIApplicationSupportsIndirectInputEvents + + NSCameraUsageDescription + Why? What is the purpose of the app? + NSMicrophoneUsageDescription + Explanation on why the microphone access is needed. + + diff --git a/ios/Runner/Runner-Bridging-Header.h b/ios/Runner/Runner-Bridging-Header.h new file mode 100644 index 0000000..308a2a5 --- /dev/null +++ b/ios/Runner/Runner-Bridging-Header.h @@ -0,0 +1 @@ +#import "GeneratedPluginRegistrant.h" diff --git a/ios/RunnerTests/RunnerTests.swift b/ios/RunnerTests/RunnerTests.swift new file mode 100644 index 0000000..86a7c3b --- /dev/null +++ b/ios/RunnerTests/RunnerTests.swift @@ -0,0 +1,12 @@ +import Flutter +import UIKit +import XCTest + +class RunnerTests: XCTestCase { + + func testExample() { + // If you add code to the Runner application, consider adding tests here. + // See https://developer.apple.com/documentation/xctest for more information about using XCTest. + } + +} diff --git a/l10n.yaml b/l10n.yaml new file mode 100644 index 0000000..d480072 --- /dev/null +++ b/l10n.yaml @@ -0,0 +1,3 @@ +arb-dir: lib/src/localization +template-arb-file: app_en.arb +output-localization-file: app_localizations.dart diff --git a/lib/main.dart b/lib/main.dart new file mode 100644 index 0000000..4bfc817 --- /dev/null +++ b/lib/main.dart @@ -0,0 +1,66 @@ +import 'package:camera/camera.dart'; +import 'package:connect/src/providers/api_provider.dart'; +import 'package:connect/src/providers/db_provider.dart'; +import 'package:flutter/material.dart'; +import 'package:logging/logging.dart'; + +import 'src/app.dart'; +import 'src/settings/settings_controller.dart'; +import 'src/settings/settings_service.dart'; + +late DbProvider dbProvider; +late ApiProvider apiProvider; + +void main() async { + // Set up the SettingsController, which will glue user settings to multiple + // Flutter Widgets. + final settingsController = SettingsController(SettingsService()); + + // Load the user's preferred theme while the splash screen is displayed. + // This prevents a sudden theme change when the app is first displayed. + await settingsController.loadSettings(); + + // Ensure that plugin services are initialized so that `availableCameras()` + // can be called before `runApp()` + WidgetsFlutterBinding.ensureInitialized(); + + // check if release build or debug build + final kDebugMode = true; + + Logger.root.level = Level.ALL; // defaults to Level.INFO + Logger.root.onRecord.listen((record) { + if (kDebugMode) { + // ignore: avoid_print + print('${record.level.name}: ${record.time}: ${record.message}'); + } + }); + + var cameras = await availableCameras(); + + // Create or open the database + dbProvider = DbProvider(); + await dbProvider.ready; + + // Create an option to select different servers. + var apiUrl = "ws://api.theconnectapp.de/v0/"; + if (kDebugMode) { + // Overwrite the domain in your local network so you can test the app locally + apiUrl = "ws://debug.theconnectapp.de:3030/v0/"; + } + + apiProvider = ApiProvider(apiUrl: apiUrl); + + // TODO: Open the connection in the background so the app launch is not delayed. + await apiProvider.connect(); + + // Workmanager.executeTask((task, inputData) async { + // await _HomeState().manager(); + // print('Background Services are Working!');//This is Working + // return true; + // }); + + // Run the app and pass in the SettingsController. The app listens to the + // SettingsController for changes, then passes it further down to the + // SettingsView. + runApp(MyApp(settingsController: settingsController, cameras: cameras)); +} diff --git a/lib/src/app.dart b/lib/src/app.dart new file mode 100644 index 0000000..1bcd956 --- /dev/null +++ b/lib/src/app.dart @@ -0,0 +1,85 @@ +import 'package:camera/camera.dart'; +import 'views/home_view.dart'; +import 'views/register_view.dart'; +import 'utils.dart'; +import 'package:flutter/material.dart'; +// import 'package:flutter_gen/gen_l10n/app_localizations.dart'; +// import 'package:flutter_localizations/flutter_localizations.dart'; + +import 'settings/settings_controller.dart'; + +/// The Widget that configures your application. +class MyApp extends StatefulWidget { + const MyApp( + {super.key, required this.settingsController, required this.cameras}); + + final SettingsController settingsController; + final List cameras; + + @override + State createState() => _MyAppState(); +} + +class _MyAppState extends State { + Future _isUserCreated = isUserCreated(); + + @override + Widget build(BuildContext context) { + // Glue the SettingsController to the MaterialApp. + // + // The ListenableBuilder Widget listens to the SettingsController for changes. + // Whenever the user updates their settings, the MaterialApp is rebuilt. + return ListenableBuilder( + listenable: widget.settingsController, + builder: (BuildContext context, Widget? child) { + return MaterialApp( + restorationScopeId: 'app', + // localizationsDelegates: const [ + // AppLocalizations.delegate, + // GlobalMaterialLocalizations.delegate, + // GlobalWidgetsLocalizations.delegate, + // GlobalCupertinoLocalizations.delegate, + // ], + supportedLocales: const [ + Locale('en', ''), // English, no country code + ], + onGenerateTitle: (BuildContext context) => "Connect!", + theme: ThemeData( + colorScheme: + ColorScheme.fromSeed(seedColor: const Color(0xFF57CC99)), + inputDecorationTheme: + const InputDecorationTheme(border: OutlineInputBorder())), + darkTheme: ThemeData.dark().copyWith( + colorScheme: ColorScheme.fromSeed( + brightness: Brightness.dark, // <-- the only line added + seedColor: const Color(0xFF57CC99)), + inputDecorationTheme: + const InputDecorationTheme(border: OutlineInputBorder()), + ), + themeMode: widget.settingsController.themeMode, + home: FutureBuilder( + future: _isUserCreated, + builder: (context, snapshot) { + if (snapshot.hasData) { + return snapshot.data! + ? HomeView( + settingsController: widget.settingsController, + cameras: widget.cameras) + : RegisterView(callbackOnSuccess: () { + _isUserCreated = isUserCreated(); + setState(() {}); + }); + } else { + return Center( + child: SizedBox( + width: 60, + height: 60, + child: CircularProgressIndicator(), + )); + } + }), + ); + }, + ); + } +} diff --git a/lib/src/localization/app_en.arb b/lib/src/localization/app_en.arb new file mode 100644 index 0000000..241eb64 --- /dev/null +++ b/lib/src/localization/app_en.arb @@ -0,0 +1,7 @@ +{ + "appTitle": "connect", + "@@locale": "en", + "@appTitle": { + "description": "The title of the application" + } +} \ No newline at end of file diff --git a/lib/src/model/identity_key_store_model.dart b/lib/src/model/identity_key_store_model.dart new file mode 100644 index 0000000..313c2be --- /dev/null +++ b/lib/src/model/identity_key_store_model.dart @@ -0,0 +1,34 @@ +import 'dart:typed_data'; + +import 'package:cv/cv.dart'; + +class DbSignalIdentityKeyStore extends CvModelBase { + static const tableName = "signal_identity_key_store"; + + static const columnDeviceId = "device_id"; + final deviceId = CvField(columnDeviceId); + + static const columnName = "name"; + final name = CvField(columnName); + + static const columnIdentityKey = "identity_key"; + final identityKey = CvField(columnIdentityKey); + + static const columnCreatedAt = "created_at"; + final createdAt = CvField(columnCreatedAt); + + static String getCreateTableString() { + return """ + CREATE TABLE $tableName ( + $columnDeviceId INTEGER NOT NULL, + $columnName TEXT NOT NULL, + $columnIdentityKey BLOB NOT NULL, + $columnCreatedAt DATETIME DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY ($columnDeviceId, $columnName) + ) + """; + } + + @override + List get fields => [deviceId, name, identityKey, createdAt]; +} diff --git a/lib/src/model/model_constants.dart b/lib/src/model/model_constants.dart new file mode 100644 index 0000000..ad5aa79 --- /dev/null +++ b/lib/src/model/model_constants.dart @@ -0,0 +1,5 @@ +const String dbName = 'connect.db'; + +const int kVersion1 = 1; + +String tableLibSignal = 'LibSignal'; diff --git a/lib/src/model/pre_key_model.dart b/lib/src/model/pre_key_model.dart new file mode 100644 index 0000000..2f66de4 --- /dev/null +++ b/lib/src/model/pre_key_model.dart @@ -0,0 +1,29 @@ +import 'dart:typed_data'; +import 'package:cv/cv.dart'; + +class DbSignalPreKeyStore extends CvModelBase { + static const tableName = "signal_pre_key_store"; + + static const columnPreKeyId = "pre_key_id"; + final preKeyId = CvField(columnPreKeyId); + + static const columnPreKey = "pre_key"; + final preKey = CvField(columnPreKey); + + static const columnCreatedAt = "created_at"; + final createdAt = CvField(columnCreatedAt); + + static String getCreateTableString() { + return """ + CREATE TABLE $tableName ( + $columnPreKeyId INTEGER NOT NULL, + $columnPreKey BLOB NOT NULL, + $columnCreatedAt DATETIME DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY ($columnPreKeyId) + ) + """; + } + + @override + List get fields => [preKeyId, preKey, createdAt]; +} diff --git a/lib/src/model/sender_key_store_model.dart b/lib/src/model/sender_key_store_model.dart new file mode 100644 index 0000000..792bce8 --- /dev/null +++ b/lib/src/model/sender_key_store_model.dart @@ -0,0 +1,29 @@ +import 'dart:typed_data'; +import 'package:cv/cv.dart'; + +class DbSignalSenderKeyStore extends CvModelBase { + static const tableName = "signal_sender_key_store"; + + static const columnSenderKeyName = "sender_key_name"; + final senderKeyName = CvField(columnSenderKeyName); + + static const columnSenderKey = "sender_key"; + final senderKey = CvField(columnSenderKey); + + static const columnCreatedAt = "created_at"; + final createdAt = CvField(columnCreatedAt); + + static String getCreateTableString() { + return """ + CREATE TABLE $tableName ( + $columnSenderKeyName TEXT NOT NULL, + $columnSenderKey BLOB NOT NULL, + $columnCreatedAt DATETIME DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY ($columnSenderKeyName) + ) + """; + } + + @override + List get fields => [senderKeyName, senderKey, createdAt]; +} diff --git a/lib/src/model/session_store_model.dart b/lib/src/model/session_store_model.dart new file mode 100644 index 0000000..8e05417 --- /dev/null +++ b/lib/src/model/session_store_model.dart @@ -0,0 +1,33 @@ +import 'dart:typed_data'; +import 'package:cv/cv.dart'; + +class DbSignalSessionStore extends CvModelBase { + static const tableName = "signal_session_store"; + + static const columnDeviceId = "device_id"; + final deviceId = CvField(columnDeviceId); + + static const columnName = "name"; + final name = CvField(columnName); + + static const columnSessionRecord = "session_record"; + final sessionRecord = CvField(columnSessionRecord); + + static const columnCreatedAt = "created_at"; + final createdAt = CvField(columnCreatedAt); + + static String getCreateTableString() { + return """ + CREATE TABLE $tableName ( + $columnDeviceId INTEGER NOT NULL, + $columnName TEXT NOT NULL, + $columnSessionRecord BLOB NOT NULL, + $columnCreatedAt DATETIME DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY ($columnDeviceId, $columnName) + ) + """; + } + + @override + List get fields => [deviceId, name, sessionRecord, createdAt]; +} diff --git a/lib/src/model/user.dart b/lib/src/model/user.dart new file mode 100644 index 0000000..2655eaf --- /dev/null +++ b/lib/src/model/user.dart @@ -0,0 +1,27 @@ +import 'dart:typed_data'; +import 'package:json_annotation/json_annotation.dart'; +part 'user.g.dart'; + +class Uint8ListConverter implements JsonConverter> { + const Uint8ListConverter(); + @override + Uint8List fromJson(List json) { + return Uint8List.fromList(json); + } + + @override + List toJson(Uint8List object) { + return object.toList(); + } +} + +@JsonSerializable() +class User { + const User({required this.username, required this.identityKeyPairU8List, required this.registrationId}); + final String username; + final int registrationId; + @Uint8ListConverter() + final Uint8List identityKeyPairU8List; + factory User.fromJson(Map json) => _$UserFromJson(json); + Map toJson() => _$UserToJson(this); +} diff --git a/lib/src/model/user.g.dart b/lib/src/model/user.g.dart new file mode 100644 index 0000000..4662cb0 --- /dev/null +++ b/lib/src/model/user.g.dart @@ -0,0 +1,21 @@ +// GENERATED CODE - DO NOT MODIFY BY HAND + +part of 'user.dart'; + +// ************************************************************************** +// JsonSerializableGenerator +// ************************************************************************** + +User _$UserFromJson(Map json) => User( + username: json['username'] as String, + identityKeyPairU8List: const Uint8ListConverter() + .fromJson(json['identityKeyPairU8List'] as List), + registrationId: (json['registrationId'] as num).toInt(), + ); + +Map _$UserToJson(User instance) => { + 'username': instance.username, + 'registrationId': instance.registrationId, + 'identityKeyPairU8List': + const Uint8ListConverter().toJson(instance.identityKeyPairU8List), + }; diff --git a/lib/src/providers/api_provider.dart b/lib/src/providers/api_provider.dart new file mode 100644 index 0000000..4f0e282 --- /dev/null +++ b/lib/src/providers/api_provider.dart @@ -0,0 +1,144 @@ +import 'dart:collection'; +import 'dart:convert'; +import 'dart:ffi'; +import 'dart:math'; + +import 'package:logging/logging.dart'; +import 'package:web_socket_channel/web_socket_channel.dart'; + +class ApiProvider { + ApiProvider({required this.apiUrl}); + + final String apiUrl; + final log = Logger("connect::ApiProvider"); + final HashMap> _callbacks = HashMap(); + + final HashMap?> messagesV0 = HashMap(); + + WebSocketChannel? _channel; + + Future connect() async { + if (_channel != null && _channel!.closeCode != null) { + return true; + } + log.info("Trying to connect to the backend!"); + try { + var channel = WebSocketChannel.connect( + Uri.parse(apiUrl), + ); + _channel = channel; + _channel!.stream.listen(_onData); + await _channel!.ready; + log.info("Websocket is connected!"); + return true; + } on WebSocketChannelException catch (e) { + log.shout("Error: $e"); + return false; + } + } + + void _onData(dynamic msgJson) { + try { + Map msg = jsonDecode(msgJson); + if (!msg.containsKey("v")) { + log.shout("Got invalid data from server!"); + return; + } + if (msg["v"] != "0") { + log.shout("Server msg not supported by client!\n $msgJson"); + return; + } + if (!msg.containsKey("seq") || !msg.containsKey("kind")) { + log.shout("Invalid server msg. No seq number or kind given: $msgJson!"); + return; + } + if (msg["kind"] == "Response") { + if (messagesV0[msg["seq"]] != null) { + log.shout("Seq no unknown: $msgJson!"); + return; + } + messagesV0[msg["seq"]] = msg; + } + } catch (e) { + log.shout("Error parsing the servers message: $e"); + } + } + + // void _reconnect() {} + + void addNotifier(String messageType, Function callBackFunction) { + if (!_callbacks.containsKey(messageType)) { + _callbacks[messageType] = []; + } + _callbacks[messageType]!.add(callBackFunction); + } + + // TODO: There must be a smarter move to do that :/ + Future?> _waitForResponse(Uint64 seq) async { + final startTime = DateTime.now(); + + final timeout = Duration(seconds: 5); + + while (true) { + if (messagesV0[seq] != null) { + final tmp = messagesV0[seq]; + messagesV0.remove(seq); + return tmp; + } + if (DateTime.now().difference(startTime) > timeout) { + log.shout("Timeout for message $seq"); + return null; + } + await Future.delayed(Duration(milliseconds: 1)); + } + } + + Future?> _sendRequestV0( + Map request) async { + var seq = Random().nextInt(0xFFFFFFFFFFFFFF) as Uint64; + while (!messagesV0.containsKey(seq)) { + seq = Random().nextInt(0xFFFFFFFFFFFFFF) as Uint64; + } + request["v"] = "0"; + request["seq"] = seq; + final requestJson = jsonEncode(request); + + // check if it is connected to the backend. if not try to reconnect. + if (!await connect()) { + return null; + } + + // reserve seq no + messagesV0[seq] = null; + _channel!.sink.add(requestJson); + + return await _waitForResponse(seq); + } + + String? _getErrorMsg(Map msg) { + if (msg.containsKey("Ok")) { + return null; + } + if (msg.containsKey("Error")) { + if (msg["Error"] != null) { + if (msg["Error"].containsKey("AlertUser")) { + return msg["Error"]["AlertUser"]; + } + } + return "There was an unknown error :/"; + } + return null; + } + + Future handshakeCheckRegister( + String username, String inviteCode) async { + final resp = await _sendRequestV0({ + "kind": "Handshake", + "CheckRegister": {"username": username, "inviteCode": inviteCode} + }); + if (resp == null) { + return "Server is not reachable!"; + } + return _getErrorMsg(resp); + } +} diff --git a/lib/src/providers/db_provider.dart b/lib/src/providers/db_provider.dart new file mode 100644 index 0000000..a07812e --- /dev/null +++ b/lib/src/providers/db_provider.dart @@ -0,0 +1,83 @@ +import 'dart:async'; +import 'dart:math'; +import 'package:connect/src/model/identity_key_store_model.dart'; +import 'package:connect/src/model/model_constants.dart'; +import 'package:connect/src/model/pre_key_model.dart'; +import 'package:connect/src/model/sender_key_store_model.dart'; +import 'package:connect/src/model/session_store_model.dart'; +import 'package:connect/src/utils.dart'; +import 'package:sqflite_sqlcipher/sqflite.dart'; + +class DbProvider { + Database? db; + + Future openPath(String path) async { + // Read the password for the database from the secure storage. If there is no, then create a + // new cryptographically secure random password with 32 bytes and store them in the secure storage. + // So if someone dumps the app for example using a tool like Cellebrite including the apps + // content he is not able to access the databases content. + // (https://signal.org/blog/cellebrite-and-clickbait/) + // + // CHECK: Does this actually improve the security or is this just security through obscurity and + // can be removed as it does increase complexity? + // Current thoughts: As the database password is at some point in the memory the attacker could + // just dump it. Questions here: What capabilities must the attacker have to do that? + + final storage = getSecureStorage(); + var password = await storage.read(key: "sqflite_database_password"); + if (password == null) { + var secureRandom = Random.secure(); + password = ""; + for (var i = 0; i < 32; i++) { + password = "$password${String.fromCharCode(secureRandom.nextInt(256))}"; + } + await storage.write(key: "sqflite_database_password", value: password); + } + + db = await openDatabase(path, password: password, version: kVersion1, + onCreate: (db, version) async { + await _createDb(db); + }, onUpgrade: (db, oldVersion, newVersion) async { + if (oldVersion < kVersion1) { + await _createDb(db); + } + }); + } + + Future get ready async { + if (db == null) { + await open(); + } + return db; + } + + Future _createDb(Database db) async { + await db.execute('DROP TABLE If EXISTS ${DbSignalSessionStore.tableName}'); + await db.execute(DbSignalSessionStore.getCreateTableString()); + + await db.execute('DROP TABLE If EXISTS ${DbSignalPreKeyStore.tableName}'); + await db.execute(DbSignalPreKeyStore.getCreateTableString()); + + await db + .execute('DROP TABLE If EXISTS ${DbSignalSenderKeyStore.tableName}'); + await db.execute(DbSignalSenderKeyStore.getCreateTableString()); + + await db + .execute('DROP TABLE If EXISTS ${DbSignalIdentityKeyStore.tableName}'); + await db.execute(DbSignalIdentityKeyStore.getCreateTableString()); + } + + Future open() async { + await openPath(await fixPath(dbName)); + } + + Future fixPath(String path) async => path; + + Future close() async { + await db!.close(); + } + + // Future deleteDb() async { + // await deleteDatabase(await fixPath(dbName)); + // } +} diff --git a/lib/src/settings/settings_controller.dart b/lib/src/settings/settings_controller.dart new file mode 100644 index 0000000..e32c0df --- /dev/null +++ b/lib/src/settings/settings_controller.dart @@ -0,0 +1,50 @@ +import 'package:flutter/material.dart'; + +import 'settings_service.dart'; + +/// A class that many Widgets can interact with to read user settings, update +/// user settings, or listen to user settings changes. +/// +/// Controllers glue Data Services to Flutter Widgets. The SettingsController +/// uses the SettingsService to store and retrieve user settings. +class SettingsController with ChangeNotifier { + SettingsController(this._settingsService); + + // Make SettingsService a private variable so it is not used directly. + final SettingsService _settingsService; + + // Make ThemeMode a private variable so it is not updated directly without + // also persisting the changes with the SettingsService. + late ThemeMode _themeMode; + + // Allow Widgets to read the user's preferred ThemeMode. + ThemeMode get themeMode => _themeMode; + + /// Load the user's settings from the SettingsService. It may load from a + /// local database or the internet. The controller only knows it can load the + /// settings from the service. + Future loadSettings() async { + _themeMode = await _settingsService.themeMode(); + + // Important! Inform listeners a change has occurred. + notifyListeners(); + } + + /// Update and persist the ThemeMode based on the user's selection. + Future updateThemeMode(ThemeMode? newThemeMode) async { + if (newThemeMode == null) return; + + // Do not perform any work if new and old ThemeMode are identical + if (newThemeMode == _themeMode) return; + + // Otherwise, store the new ThemeMode in memory + _themeMode = newThemeMode; + + // Important! Inform listeners a change has occurred. + notifyListeners(); + + // Persist the changes to a local database or the internet using the + // SettingService. + await _settingsService.updateThemeMode(newThemeMode); + } +} diff --git a/lib/src/settings/settings_service.dart b/lib/src/settings/settings_service.dart new file mode 100644 index 0000000..6f94dc3 --- /dev/null +++ b/lib/src/settings/settings_service.dart @@ -0,0 +1,17 @@ +import 'package:flutter/material.dart'; + +/// A service that stores and retrieves user settings. +/// +/// By default, this class does not persist user settings. If you'd like to +/// persist the user settings locally, use the shared_preferences package. If +/// you'd like to store settings on a web server, use the http package. +class SettingsService { + /// Loads the User's preferred ThemeMode from local or remote storage. + Future themeMode() async => ThemeMode.system; + + /// Persists the user's preferred ThemeMode to local or remote storage. + Future updateThemeMode(ThemeMode theme) async { + // Use the shared_preferences package to persist settings locally or the + // http package to persist settings over the network. + } +} diff --git a/lib/src/settings/settings_view.dart b/lib/src/settings/settings_view.dart new file mode 100644 index 0000000..9dd36bd --- /dev/null +++ b/lib/src/settings/settings_view.dart @@ -0,0 +1,49 @@ +import 'package:flutter/material.dart'; + +import 'settings_controller.dart'; + +/// Displays the various settings that can be customized by the user. +/// +/// When a user changes a setting, the SettingsController is updated and +/// Widgets that listen to the SettingsController are rebuilt. +class SettingsView extends StatelessWidget { + const SettingsView({required this.controller}); + + final SettingsController controller; + + @override + Widget build(BuildContext context) { + return Scaffold( + appBar: AppBar( + title: const Text('Settings'), + ), + body: Padding( + padding: const EdgeInsets.all(16), + // Glue the SettingsController to the theme selection DropdownButton. + // + // When a user selects a theme from the dropdown list, the + // SettingsController is updated, which rebuilds the MaterialApp. + child: DropdownButton( + // Read the selected themeMode from the controller + value: controller.themeMode, + // Call the updateThemeMode method any time the user selects a theme. + onChanged: controller.updateThemeMode, + items: const [ + DropdownMenuItem( + value: ThemeMode.system, + child: Text('System Theme'), + ), + DropdownMenuItem( + value: ThemeMode.light, + child: Text('Light Theme'), + ), + DropdownMenuItem( + value: ThemeMode.dark, + child: Text('Dark Theme'), + ) + ], + ), + ), + ); + } +} diff --git a/lib/src/signal/connect_identitiy_key_store.dart b/lib/src/signal/connect_identitiy_key_store.dart new file mode 100644 index 0000000..7a7ab9e --- /dev/null +++ b/lib/src/signal/connect_identitiy_key_store.dart @@ -0,0 +1,68 @@ +import 'dart:typed_data'; +import 'package:collection/collection.dart'; +import 'package:connect/main.dart'; +import 'package:connect/src/model/identity_key_store_model.dart'; +import 'package:libsignal_protocol_dart/libsignal_protocol_dart.dart'; + +bool eq(List? list1, List? list2) => + ListEquality().equals(list1, list2); + +// make it easier to read +typedef DB = DbSignalIdentityKeyStore; + +class ConnectIdentityKeyStore extends IdentityKeyStore { + ConnectIdentityKeyStore(this.identityKeyPair, this.localRegistrationId); + + final IdentityKeyPair identityKeyPair; + final int localRegistrationId; + + @override + Future getIdentity(SignalProtocolAddress address) async { + var dbIdentityKey = (await dbProvider.db!.query(DB.tableName, + columns: [DB.columnIdentityKey], + where: '${DB.columnDeviceId} = ? AND ${DB.columnName} = ?', + whereArgs: [address.getDeviceId(), address.getName()])); + if (dbIdentityKey.isEmpty) { + return null; + } + Uint8List identityKey = dbIdentityKey.first.cast()[DB.columnIdentityKey]; + return IdentityKey.fromBytes(identityKey, 0); + } + + @override + Future getIdentityKeyPair() async => identityKeyPair; + + @override + Future getLocalRegistrationId() async => localRegistrationId; + + @override + Future isTrustedIdentity(SignalProtocolAddress address, + IdentityKey? identityKey, Direction? direction) async { + final trusted = await getIdentity(address); + if (identityKey == null) { + return false; + } + return trusted == null || eq(trusted.serialize(), identityKey.serialize()); + } + + @override + Future saveIdentity( + SignalProtocolAddress address, IdentityKey? identityKey) async { + if (identityKey == null) { + return false; + } + if (await getIdentity(address) == null) { + await dbProvider.db!.insert(DB.tableName, { + DB.columnDeviceId: address.getDeviceId(), + DB.columnName: address.getName(), + DB.columnIdentityKey: identityKey.serialize() + }); + } else { + await dbProvider.db!.update( + DB.tableName, {DB.columnIdentityKey: identityKey.serialize()}, + where: '${DB.columnDeviceId} = ? AND ${DB.columnName} = ?', + whereArgs: [address.getDeviceId(), address.getName()]); + } + return true; + } +} diff --git a/lib/src/signal/connect_pre_key_store.dart b/lib/src/signal/connect_pre_key_store.dart new file mode 100644 index 0000000..9f982b1 --- /dev/null +++ b/lib/src/signal/connect_pre_key_store.dart @@ -0,0 +1,49 @@ +import 'dart:typed_data'; +import 'package:connect/main.dart'; +import 'package:connect/src/model/pre_key_model.dart'; +import 'package:libsignal_protocol_dart/libsignal_protocol_dart.dart'; + +typedef DB = DbSignalPreKeyStore; + +class ConnectPreKeyStore extends PreKeyStore { + @override + Future containsPreKey(int preKeyId) async { + final dbPreKey = await dbProvider.db!.query(DB.tableName, + columns: [DB.columnPreKey], + where: '${DB.columnPreKeyId} = ?', + whereArgs: [preKeyId]); + return dbPreKey.isNotEmpty; + } + + @override + Future loadPreKey(int preKeyId) async { + final dbPreKey = await dbProvider.db!.query(DB.tableName, + columns: [DB.columnPreKey], + where: '${DB.columnPreKeyId} = ?', + whereArgs: [preKeyId]); + if (dbPreKey.isEmpty) { + throw InvalidKeyIdException('No such preKey record! - $preKeyId'); + } + Uint8List preKey = dbPreKey.first.cast()[DB.columnPreKey]; + return PreKeyRecord.fromBuffer(preKey); + } + + @override + Future removePreKey(int preKeyId) async { + await dbProvider.db!.delete(DB.tableName, + where: '${DB.columnPreKeyId} = ?', + whereArgs: [DB.columnPreKeyId]); + } + + @override + Future storePreKey(int preKeyId, PreKeyRecord record) async { + if (await containsPreKey(preKeyId)) { + await dbProvider.db!.insert(DB.tableName, + {DB.columnPreKeyId: preKeyId, DB.columnPreKey: record.serialize()}); + } else { + await dbProvider.db!.update( + DB.tableName, {DB.columnPreKey: record.serialize()}, + where: '${DB.columnPreKeyId} = ?', whereArgs: [preKeyId]); + } + } +} diff --git a/lib/src/signal/connect_sender_key_store.dart b/lib/src/signal/connect_sender_key_store.dart new file mode 100644 index 0000000..9671f78 --- /dev/null +++ b/lib/src/signal/connect_sender_key_store.dart @@ -0,0 +1,31 @@ +import 'dart:typed_data'; +import 'package:connect/main.dart'; +import 'package:connect/src/model/sender_key_store_model.dart'; +import 'package:libsignal_protocol_dart/libsignal_protocol_dart.dart'; + +typedef DB = DbSignalSenderKeyStore; + +class ConnectSenderKeyStore extends SenderKeyStore { + @override + Future loadSenderKey(SenderKeyName senderKeyName) async { + final dbSenderKey = await dbProvider.db!.query(DB.tableName, + columns: [DB.columnSenderKey], + where: '${DB.columnSenderKeyName} = ?', + whereArgs: [senderKeyName.serialize()]); + if (dbSenderKey.isEmpty) { + throw InvalidKeyIdException( + 'No such sender key record! - $senderKeyName'); + } + Uint8List preKey = dbSenderKey.first.cast()[DB.columnSenderKey]; + return SenderKeyRecord.fromSerialized(preKey); + } + + @override + Future storeSenderKey( + SenderKeyName senderKeyName, SenderKeyRecord record) async { + await dbProvider.db!.insert(DB.tableName, { + DB.columnSenderKeyName: senderKeyName.serialize(), + DB.columnSenderKey: record.serialize() + }); + } +} diff --git a/lib/src/signal/connect_session_store.dart b/lib/src/signal/connect_session_store.dart new file mode 100644 index 0000000..1ece6ee --- /dev/null +++ b/lib/src/signal/connect_session_store.dart @@ -0,0 +1,73 @@ +import 'dart:typed_data'; +import 'package:connect/main.dart'; +import 'package:connect/src/model/session_store_model.dart'; +import 'package:libsignal_protocol_dart/libsignal_protocol_dart.dart'; + +// make it easier to read +typedef DB = DbSignalSessionStore; + +class ConnectSessionStore extends SessionStore { + ConnectSessionStore(); + + @override + Future containsSession(SignalProtocolAddress address) async { + var list = (await dbProvider.db!.query(DB.tableName, + columns: [], + where: '${DB.columnDeviceId} = ? AND ${DB.columnName} = ?', + whereArgs: [address.getDeviceId(), address.getName()])); + return list.isNotEmpty; + } + + @override + Future deleteAllSessions(String name) async { + await dbProvider.db!.delete(DB.tableName, + where: '${DB.columnName} = ?', whereArgs: [name]); + } + + @override + Future deleteSession(SignalProtocolAddress address) async { + await dbProvider.db!.delete(DB.tableName, + where: '${DB.columnDeviceId} = ? AND ${DB.columnName} = ?', + whereArgs: [address.getDeviceId(), address.getName()]); + } + + @override + Future> getSubDeviceSessions(String name) async { + var deviceIds = (await dbProvider.db!.query(DB.tableName, + columns: [DB.columnDeviceId], + where: '${DB.columnDeviceId} != 1 AND ${DB.columnName} = ?', + whereArgs: [name])); + return deviceIds.cast(); + } + + @override + Future loadSession(SignalProtocolAddress address) async { + var dbSession = (await dbProvider.db!.query(DB.tableName, + columns: [DB.columnSessionRecord], + where: '${DB.columnDeviceId} = ? AND ${DB.columnName} = ?', + whereArgs: [address.getDeviceId(), address.getName()])); + + if (dbSession.isEmpty) { + return SessionRecord(); + } + Uint8List session = dbSession.first.cast()[DB.columnSessionRecord]; + return SessionRecord.fromSerialized(session); + } + + @override + Future storeSession( + SignalProtocolAddress address, SessionRecord record) async { + if (await containsSession(address)) { + await dbProvider.db!.insert(DB.tableName, { + DB.columnDeviceId: address.getDeviceId(), + DB.columnName: address.getName(), + DB.columnSessionRecord: record.serialize() + }); + } else { + await dbProvider.db!.update( + DB.tableName, {DB.columnSessionRecord: record.serialize()}, + where: '${DB.columnDeviceId} = ? AND ${DB.columnName} = ?', + whereArgs: [address.getDeviceId(), address.getName()]); + } + } +} diff --git a/lib/src/signal/connect_signal_protocol_store.dart b/lib/src/signal/connect_signal_protocol_store.dart new file mode 100644 index 0000000..07980a6 --- /dev/null +++ b/lib/src/signal/connect_signal_protocol_store.dart @@ -0,0 +1,110 @@ +import 'package:connect/src/signal/connect_identitiy_key_store.dart'; +import 'package:connect/src/signal/connect_pre_key_store.dart'; +import 'package:connect/src/signal/connect_session_store.dart'; +import 'package:connect/src/signal/connect_signed_pre_key_store.dart'; +import 'package:libsignal_protocol_dart/libsignal_protocol_dart.dart'; + +class ConnectSignalProtocolStore implements SignalProtocolStore { + ConnectSignalProtocolStore( + IdentityKeyPair identityKeyPair, int registrationId) { + _identityKeyStore = + ConnectIdentityKeyStore(identityKeyPair, registrationId); + } + + final preKeyStore = ConnectPreKeyStore(); + final sessionStore = ConnectSessionStore(); + final signedPreKeyStore = ConnectSignedPreKeyStore(); + + late IdentityKeyStore _identityKeyStore; + + @override + Future getIdentityKeyPair() async => + _identityKeyStore.getIdentityKeyPair(); + + @override + Future getLocalRegistrationId() async => + _identityKeyStore.getLocalRegistrationId(); + + @override + Future saveIdentity( + SignalProtocolAddress address, IdentityKey? identityKey) async => + _identityKeyStore.saveIdentity(address, identityKey); + + @override + Future isTrustedIdentity(SignalProtocolAddress address, + IdentityKey? identityKey, Direction direction) async => + _identityKeyStore.isTrustedIdentity(address, identityKey, direction); + + @override + Future getIdentity(SignalProtocolAddress address) async => + _identityKeyStore.getIdentity(address); + + @override + Future loadPreKey(int preKeyId) async => + preKeyStore.loadPreKey(preKeyId); + + @override + Future storePreKey(int preKeyId, PreKeyRecord record) async { + await preKeyStore.storePreKey(preKeyId, record); + } + + @override + Future containsPreKey(int preKeyId) async => + preKeyStore.containsPreKey(preKeyId); + + @override + Future removePreKey(int preKeyId) async { + await preKeyStore.removePreKey(preKeyId); + } + + @override + Future loadSession(SignalProtocolAddress address) async => + sessionStore.loadSession(address); + + @override + Future> getSubDeviceSessions(String name) async => + sessionStore.getSubDeviceSessions(name); + + @override + Future storeSession( + SignalProtocolAddress address, SessionRecord record) async { + await sessionStore.storeSession(address, record); + } + + @override + Future containsSession(SignalProtocolAddress address) async => + sessionStore.containsSession(address); + + @override + Future deleteSession(SignalProtocolAddress address) async { + await sessionStore.deleteSession(address); + } + + @override + Future deleteAllSessions(String name) async { + await sessionStore.deleteAllSessions(name); + } + + @override + Future loadSignedPreKey(int signedPreKeyId) async => + signedPreKeyStore.loadSignedPreKey(signedPreKeyId); + + @override + Future> loadSignedPreKeys() async => + signedPreKeyStore.loadSignedPreKeys(); + + @override + Future storeSignedPreKey( + int signedPreKeyId, SignedPreKeyRecord record) async { + await signedPreKeyStore.storeSignedPreKey(signedPreKeyId, record); + } + + @override + Future containsSignedPreKey(int signedPreKeyId) async => + signedPreKeyStore.containsSignedPreKey(signedPreKeyId); + + @override + Future removeSignedPreKey(int signedPreKeyId) async { + await signedPreKeyStore.removeSignedPreKey(signedPreKeyId); + } +} diff --git a/lib/src/signal/connect_signed_pre_key_store.dart b/lib/src/signal/connect_signed_pre_key_store.dart new file mode 100644 index 0000000..4463612 --- /dev/null +++ b/lib/src/signal/connect_signed_pre_key_store.dart @@ -0,0 +1,69 @@ +import 'dart:collection'; +import 'dart:convert'; +import 'dart:typed_data'; + +import 'package:connect/src/utils.dart'; +import 'package:libsignal_protocol_dart/libsignal_protocol_dart.dart'; + +class ConnectSignedPreKeyStore extends SignedPreKeyStore { + // final store = HashMap(); + + Future> getStore() async { + final storage = getSecureStorage(); + final storeSerialized = await storage.read(key: "signed_pre_key_store"); + var store = HashMap(); + if (storeSerialized == null) { + return store; + } + final storeHashMap = json.decode(storeSerialized); + // for (final item in storeHashMap) { + // store[item[0]] = Uint8List.fromList(item[1].codeUnits); + // } + return storeHashMap; + } + + Future safeStore(HashMap store) async { + final storage = getSecureStorage(); + final storeSerialized = json.encode(store); + await storage.write(key: "signed_pre_key_store", value: storeSerialized); + } + + @override + Future loadSignedPreKey(int signedPreKeyId) async { + final store = await getStore(); + if (!store.containsKey(signedPreKeyId)) { + throw InvalidKeyIdException( + 'No such signedprekeyrecord! $signedPreKeyId'); + } + return SignedPreKeyRecord.fromSerialized(store[signedPreKeyId]!); + } + + @override + Future> loadSignedPreKeys() async { + final store = await getStore(); + final results = []; + for (final serialized in store.values) { + results.add(SignedPreKeyRecord.fromSerialized(serialized)); + } + return results; + } + + @override + Future storeSignedPreKey( + int signedPreKeyId, SignedPreKeyRecord record) async { + final store = await getStore(); + store[signedPreKeyId] = record.serialize(); + await safeStore(store); + } + + @override + Future containsSignedPreKey(int signedPreKeyId) async => + (await getStore()).containsKey(signedPreKeyId); + + @override + Future removeSignedPreKey(int signedPreKeyId) async { + final store = await getStore(); + store.remove(signedPreKeyId); + await safeStore(store); + } +} diff --git a/lib/src/signal/signal_helper.dart b/lib/src/signal/signal_helper.dart new file mode 100644 index 0000000..9372443 --- /dev/null +++ b/lib/src/signal/signal_helper.dart @@ -0,0 +1,186 @@ +import 'dart:convert'; +import 'dart:developer'; +import 'dart:typed_data'; +import 'package:libsignal_protocol_dart/libsignal_protocol_dart.dart'; + +import 'connect_sender_key_store.dart'; +import 'connect_signal_protocol_store.dart'; + +class SignalDataModel { + String name; + ConnectSignalProtocolStore signalStore; + ConnectSenderKeyStore senderKeyStore; + Map serverKeyBundle; + SignalDataModel({ + required this.name, + required this.serverKeyBundle, + required this.senderKeyStore, + required this.signalStore, + }); + // Session validation + Future generateSessionFingerPrint(String target) async { + try { + IdentityKey? targetIdentity = await signalStore.getIdentity( + SignalProtocolAddress(target, SignalHelper.defaultDeviceId)); + if (targetIdentity != null) { + final generator = NumericFingerprintGenerator(5200); + final localFingerprint = generator.createFor( + 1, + Uint8List.fromList(utf8.encode(name)), + (await signalStore.getIdentityKeyPair()).getPublicKey(), + Uint8List.fromList(utf8.encode(target)), + targetIdentity, + ); + return localFingerprint; + } + return null; + } catch (e) { + return null; + } + } + + // one to one implementation + Future buildSession( + String target, + Map remoteBundle, + ) async { + SignalProtocolAddress targetAddress = + SignalProtocolAddress(target, SignalHelper.defaultDeviceId); + SessionBuilder sessionBuilder = + SessionBuilder.fromSignalStore(signalStore, targetAddress); + PreKeyBundle temp = preKeyBundleFromJson(remoteBundle); + await sessionBuilder.processPreKeyBundle(temp); + } + + PreKeyBundle preKeyBundleFromJson(Map remoteBundle) { + // One time pre key calculation + List tempPreKeys = remoteBundle["preKeys"]; + ECPublicKey? tempPrePublicKey; + int? tempPreKeyId; + if (tempPreKeys.isNotEmpty) { + tempPrePublicKey = Curve.decodePoint( + DjbECPublicKey(base64Decode(tempPreKeys.first['key'])).serialize(), + 1); + tempPreKeyId = remoteBundle["preKeys"].first['id']; + } + // Signed pre key calculation + int tempSignedPreKeyId = remoteBundle["signedPreKey"]['id']; + Map? tempSignedPreKey = remoteBundle["signedPreKey"]; + ECPublicKey? tempSignedPreKeyPublic; + Uint8List? tempSignedPreKeySignature; + if (tempSignedPreKey != null) { + tempSignedPreKeyPublic = Curve.decodePoint( + DjbECPublicKey(base64Decode(remoteBundle["signedPreKey"]['key'])) + .serialize(), + 1); + tempSignedPreKeySignature = + base64Decode(remoteBundle["signedPreKey"]['signature']); + } + // Identity key calculation + IdentityKey tempIdentityKey = IdentityKey(Curve.decodePoint( + DjbECPublicKey(base64Decode(remoteBundle["identityKey"])).serialize(), + 1)); + return PreKeyBundle( + remoteBundle['registrationId'], + 1, + tempPreKeyId, + tempPrePublicKey, + tempSignedPreKeyId, + tempSignedPreKeyPublic, + tempSignedPreKeySignature, + tempIdentityKey, + ); + } + + Future getEncryptedText(String text, String target) async { + try { + SessionCipher session = SessionCipher.fromStore(signalStore, + SignalProtocolAddress(target, SignalHelper.defaultDeviceId)); + final ciphertext = + await session.encrypt(Uint8List.fromList(utf8.encode(text))); + Map data = { + "msg": base64Encode(ciphertext.serialize()), + "type": ciphertext.getType(), + }; + return jsonEncode(data); + } catch (e) { + log(e.toString()); + return null; + } + } + + Future getDecryptedText(String source, String msg) async { + try { + SessionCipher session = SessionCipher.fromStore(signalStore, + SignalProtocolAddress(source, SignalHelper.defaultDeviceId)); + Map data = jsonDecode(msg); + if (data["type"] == CiphertextMessage.prekeyType) { + PreKeySignalMessage pre = + PreKeySignalMessage(base64Decode(data["msg"])); + Uint8List plaintext = await session.decrypt(pre); + String dectext = utf8.decode(plaintext); + return dectext; + } else if (data["type"] == CiphertextMessage.whisperType) { + SignalMessage signalMsg = + SignalMessage.fromSerialized(base64Decode(data["msg"])); + Uint8List plaintext = await session.decryptFromSignal(signalMsg); + String dectext = utf8.decode(plaintext); + return dectext; + } else { + return null; + } + } catch (e) { + log(e.toString()); + return null; + } + } +} + +class SignalHelper { + static const int defaultDeviceId = 1; + + static Future createNewSignalIdentity(String name) async { + final identityKeyPair = generateIdentityKeyPair(); + final registrationId = generateRegistrationId(true); + + ConnectSignalProtocolStore signalStore = + ConnectSignalProtocolStore(identityKeyPair, registrationId); + + final preKeys = generatePreKeys(0, 100); + final signedPreKey = + generateSignedPreKey(identityKeyPair, SignalHelper.defaultDeviceId); + + for (final p in preKeys) { + await signalStore.preKeyStore.storePreKey(p.id, p); + } + + await signalStore.signedPreKeyStore + .storeSignedPreKey(signedPreKey.id, signedPreKey); + + Map req = {}; + req['registrationId'] = registrationId; + req['identityKey'] = + base64Encode(identityKeyPair.getPublicKey().serialize()); + req['signedPreKey'] = { + 'id': signedPreKey.id, + 'signature': base64Encode(signedPreKey.signature), + 'key': base64Encode(signedPreKey.getKeyPair().publicKey.serialize()), + }; + List pKeysList = []; + for (PreKeyRecord pKey in preKeys) { + Map pKeys = {}; + pKeys['id'] = pKey.id; + pKeys['key'] = base64Encode(pKey.getKeyPair().publicKey.serialize()); + pKeysList.add(pKeys); + } + req['preKeys'] = pKeysList; + + SignalDataModel sm = SignalDataModel( + name: name, + serverKeyBundle: req, + senderKeyStore: ConnectSenderKeyStore(), + signalStore: signalStore, + ); + return sm; + } +} diff --git a/lib/src/utils.dart b/lib/src/utils.dart new file mode 100644 index 0000000..0df44a2 --- /dev/null +++ b/lib/src/utils.dart @@ -0,0 +1,68 @@ +import 'dart:convert'; +import 'package:connect/main.dart'; +import 'package:connect/src/signal/signal_helper.dart'; +import 'package:flutter_secure_storage/flutter_secure_storage.dart'; +import 'model/user.dart'; + +// Just a helper function to get the secure storage +FlutterSecureStorage getSecureStorage() { + AndroidOptions _getAndroidOptions() => const AndroidOptions( + encryptedSharedPreferences: true, + ); + return FlutterSecureStorage(aOptions: _getAndroidOptions()); +} + +Future isUserCreated() async { + User? user = await getUser(); + if (user == null) { + return false; + } + return true; +} + +Future getUser() async { + final storage = getSecureStorage(); + String? userJson = await storage.read(key: "user"); + if (userJson == null) { + return null; + } + try { +// Decode the JSON string + final userMap = jsonDecode(userJson) as Map; + final user = User.fromJson(userMap); + return user; + } catch (_) { + return null; + } +} + +Future deleteLocalUserData() async { + final storage = getSecureStorage(); + await storage.delete(key: "user"); + return true; +} + +Future createNewUser(String username, String inviteCode) async { + final storage = getSecureStorage(); + + // TODO: API call to server to check username and inviteCode + final check = await apiProvider.handshakeCheckRegister(username, inviteCode); + if (check != null) { + return check; + } + + final signalModel = await SignalHelper.createNewSignalIdentity(username); + + final identityKeyPair = await signalModel.signalStore.getIdentityKeyPair(); + + final user = User( + username: username, + identityKeyPairU8List: identityKeyPair.serialize(), + registrationId: await signalModel.signalStore.getLocalRegistrationId()); + + // TODO: API call to register user + + await storage.write(key: "user", value: jsonEncode(user)); + + return null; +} diff --git a/lib/src/views/add_new_user_view.dart b/lib/src/views/add_new_user_view.dart new file mode 100644 index 0000000..916ddc0 --- /dev/null +++ b/lib/src/views/add_new_user_view.dart @@ -0,0 +1,148 @@ +import 'dart:async'; + +import 'package:flutter/material.dart'; +import 'package:mobile_scanner/mobile_scanner.dart'; + +class AddNewUserView extends StatefulWidget { + const AddNewUserView({super.key}); + + @override + State createState() => _AddNewUserViewState(); +} + +class _AddNewUserViewState extends State + with WidgetsBindingObserver { + Barcode? _barcode; + final MobileScannerController controller = MobileScannerController( + // required options for the scanner + ); + void _handleBarcode(BarcodeCapture barcodes) { + if (mounted) { + setState(() { + _barcode = barcodes.barcodes.firstOrNull; + }); + } + } + + @override + void didChangeAppLifecycleState(AppLifecycleState state) { + // If the controller is not ready, do not try to start or stop it. + // Permission dialogs can trigger lifecycle changes before the controller is ready. + if (!controller.value.hasCameraPermission) { + return; + } + + switch (state) { + case AppLifecycleState.detached: + case AppLifecycleState.hidden: + case AppLifecycleState.paused: + return; + case AppLifecycleState.resumed: + // Restart the scanner when the app is resumed. + // Don't forget to resume listening to the barcode events. + _subscription = controller.barcodes.listen(_handleBarcode); + + unawaited(controller.start()); + case AppLifecycleState.inactive: + // Stop the scanner when the app is paused. + // Also stop the barcode events subscription. + unawaited(_subscription?.cancel()); + _subscription = null; + unawaited(controller.stop()); + } + } + + @override + void initState() { + super.initState(); + // Start listening to lifecycle changes. + WidgetsBinding.instance.addObserver(this); + + // Start listening to the barcode events. + _subscription = controller.barcodes.listen(_handleBarcode); + + // Finally, start the scanner itself. + unawaited(controller.start()); + } + + @override + Future dispose() async { + // Stop listening to lifecycle changes. + WidgetsBinding.instance.removeObserver(this); + // Stop listening to the barcode events. + unawaited(_subscription?.cancel()); + _subscription = null; + // Dispose the widget itself. + super.dispose(); + // Finally, dispose of the controller. + await controller.dispose(); + } + + Widget _buildBarcode(Barcode? value) { + if (value == null) { + return Text.rich( + TextSpan( + children: [ + TextSpan( + text: + "One of Connect's most important goals is data confidentiality. The Signal Protocol is therefore used to encrypt the data. The security of the Signal Protocol is based on the fact that the Signal identity is verified in a secure way (you stand next to the person and compare the public key). ", + style: TextStyle(color: Colors.white), + ), + TextSpan( + text: + "To enforce this, the only way to add a new user is to scan their QR code.", + style: TextStyle( + color: Colors.white, + fontWeight: FontWeight.bold), // Bold style + ), + ], + ), + overflow: TextOverflow.fade, + textAlign: TextAlign.center, + ); + } + + return Text( + value.displayValue ?? 'No display value.', + overflow: TextOverflow.fade, + style: const TextStyle(color: Colors.white), + ); + } + + StreamSubscription? _subscription; + @override + Widget build(BuildContext context) { + return Scaffold( + appBar: AppBar( + title: Text('Add new user'), + ), + body: Stack( + children: [ + MobileScanner( + onDetect: _handleBarcode, + ), + Align( + alignment: Alignment.bottomCenter, + child: Padding( + padding: EdgeInsets.all(20), + child: Container( + decoration: BoxDecoration( + color: Colors.black.withOpacity(0.4), + borderRadius: BorderRadius.circular(9), + ), + alignment: Alignment.bottomCenter, + height: 200, + child: Row( + mainAxisAlignment: MainAxisAlignment.spaceEvenly, + children: [ + Expanded(child: Center(child: _buildBarcode(_barcode))), + ], + ), + ), + ), + ), + ], + ), + ); + } +} diff --git a/lib/src/views/camera_editor_view.dart b/lib/src/views/camera_editor_view.dart new file mode 100644 index 0000000..5571da5 --- /dev/null +++ b/lib/src/views/camera_editor_view.dart @@ -0,0 +1,288 @@ +// Dart imports: +import 'dart:io'; +import 'dart:math'; + +// Flutter imports: +// import 'package:example/widgets/demo_build_stickers.dart'; +import 'package:flutter/foundation.dart'; +import 'package:flutter/material.dart'; +// Package imports: +import 'package:google_fonts/google_fonts.dart'; +import 'package:pro_image_editor/designs/frosted_glass/frosted_glass.dart'; +import 'package:pro_image_editor/pro_image_editor.dart'; + +// Project imports: +// import '../../utils/example_helper.dart'; + +/// The frosted glass design example +class CameraEditorView extends StatefulWidget { + /// Creates a new [CameraEditorView] widget. + const CameraEditorView({ + super.key, + required this.imagePath, + }); + + /// The URL of the image to display. + final String imagePath; + + @override + State createState() => _CameraEditorViewState(); +} + +class _CameraEditorViewState extends State { + final bool _useMaterialDesign = + platformDesignMode == ImageEditorDesignModeE.material; + + /// Opens the sticker/emoji editor. + void _openStickerEditor(ProImageEditorState editor) async { + Layer? layer = await editor.openPage(FrostedGlassStickerPage( + configs: editor.configs, + callbacks: editor.callbacks, + )); + + if (layer == null || !mounted) return; + + if (layer.runtimeType != StickerLayerData) { + layer.scale = editor.configs.emojiEditorConfigs.initScale; + } + + editor.addLayer(layer); + } + + /// Calculates the number of columns for the EmojiPicker. + int _calculateEmojiColumns(BoxConstraints constraints) => + max(1, (_useMaterialDesign ? 6 : 10) / 400 * constraints.maxWidth - 1) + .floor(); + + @override + Widget build(BuildContext context) { + return LayoutBuilder(builder: (context, constraints) { + return ProImageEditor.file( + File(widget.imagePath), + // key: editorKey, + callbacks: ProImageEditorCallbacks( + onImageEditingStarted: () {}, + onImageEditingComplete: (image) async { + Navigator.pop(context); + }, + onCloseEditor: () {}, + stickerEditorCallbacks: StickerEditorCallbacks( + onSearchChanged: (value) { + /// Filter your stickers + debugPrint(value); + }, + )), + configs: ProImageEditorConfigs( + designMode: platformDesignMode, + theme: Theme.of(context).copyWith( + iconTheme: + Theme.of(context).iconTheme.copyWith(color: Colors.white)), + icons: const ImageEditorIcons( + paintingEditor: IconsPaintingEditor( + bottomNavBar: Icons.edit, + ), + ), + imageEditorTheme: ImageEditorTheme( + textEditor: TextEditorTheme( + textFieldMargin: const EdgeInsets.only(top: kToolbarHeight), + bottomBarBackgroundColor: Colors.transparent, + bottomBarMainAxisAlignment: !_useMaterialDesign + ? MainAxisAlignment.spaceEvenly + : MainAxisAlignment.start), + paintingEditor: const PaintingEditorTheme( + initialStrokeWidth: 5, + ), + // filterEditor: const FilterEditorTheme( + // filterListSpacing: 7, + // filterListMargin: EdgeInsets.fromLTRB(8, 15, 8, 10), + // ), + emojiEditor: EmojiEditorTheme( + backgroundColor: Colors.transparent, + textStyle: DefaultEmojiTextStyle.copyWith( + fontFamily: + !kIsWeb ? null : GoogleFonts.notoColorEmoji().fontFamily, + fontSize: _useMaterialDesign ? 48 : 30, + ), + emojiViewConfig: EmojiViewConfig( + gridPadding: EdgeInsets.zero, + horizontalSpacing: 0, + verticalSpacing: 0, + recentsLimit: 40, + backgroundColor: Colors.transparent, + buttonMode: !_useMaterialDesign + ? ButtonMode.CUPERTINO + : ButtonMode.MATERIAL, + loadingIndicator: + const Center(child: CircularProgressIndicator()), + columns: _calculateEmojiColumns(constraints), + emojiSizeMax: !_useMaterialDesign ? 32 : 64, + replaceEmojiOnLimitExceed: false, + ), + bottomActionBarConfig: + const BottomActionBarConfig(enabled: false), + ), + layerInteraction: const ThemeLayerInteraction( + removeAreaBackgroundInactive: Colors.black12, + ), + ), + textEditorConfigs: TextEditorConfigs( + customTextStyles: [ + GoogleFonts.roboto(), + GoogleFonts.averiaLibre(), + GoogleFonts.lato(), + GoogleFonts.comicNeue(), + GoogleFonts.actor(), + GoogleFonts.odorMeanChey(), + GoogleFonts.nabla(), + ], + ), + emojiEditorConfigs: const EmojiEditorConfigs( + checkPlatformCompatibility: !kIsWeb, + ), + customWidgets: ImageEditorCustomWidgets( + loadingDialog: (message, configs) => FrostedGlassLoadingDialog( + message: message, + configs: configs, + ), + mainEditor: CustomWidgetsMainEditor( + closeWarningDialog: (editor) async { + if (!context.mounted) return false; + return await showDialog( + context: context, + builder: (BuildContext context) => + FrostedGlassCloseDialog(editor: editor), + ) ?? + false; + }, + appBar: (editor, rebuildStream) => null, + bottomBar: (editor, rebuildStream, key) => null, + bodyItems: _buildMainBodyWidgets, + ), + paintEditor: CustomWidgetsPaintEditor( + appBar: (paintEditor, rebuildStream) => null, + bottomBar: (paintEditor, rebuildStream) => null, + colorPicker: + (paintEditor, rebuildStream, currentColor, setColor) => null, + bodyItems: _buildPaintEditorBody, + ), + textEditor: CustomWidgetsTextEditor( + appBar: (textEditor, rebuildStream) => null, + colorPicker: + (textEditor, rebuildStream, currentColor, setColor) => null, + bottomBar: (textEditor, rebuildStream) => null, + bodyItems: _buildTextEditorBody, + ), + cropRotateEditor: CustomWidgetsCropRotateEditor(), + ), + ), + ); + }); + } + + List _buildMainBodyWidgets( + ProImageEditorState editor, + Stream rebuildStream, + ) { + return [ + if (editor.selectedLayerIndex < 0) + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) => FrostedGlassActionBar( + editor: editor, + openStickerEditor: () => _openStickerEditor(editor), + ), + ), + ]; + } + + List _buildPaintEditorBody( + PaintingEditorState paintEditor, + Stream rebuildStream, + ) { + return [ + /// Appbar + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) { + return paintEditor.activePainting + ? const SizedBox.shrink() + : FrostedGlassPaintingAppbar(paintEditor: paintEditor); + }, + ), + + /// Bottombar + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) => FrostedGlassPaintBottomBar(paintEditor: paintEditor), + ), + ]; + } + + List _buildTuneEditorBody( + TuneEditorState tuneEditor, + Stream rebuildStream, + ) { + return [ + /// Appbar + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) { + return FrostedGlassTuneAppbar(tuneEditor: tuneEditor); + }, + ), + + /// Bottombar + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) => FrostedGlassTuneBottombar(tuneEditor: tuneEditor), + ), + ]; + } + + List _buildTextEditorBody( + TextEditorState textEditor, + Stream rebuildStream, + ) { + return [ + /// Background + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) => const FrostedGlassEffect( + radius: BorderRadius.zero, + child: SizedBox.expand(), + ), + ), + + /// Slider Text size + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) => Padding( + padding: const EdgeInsets.only(top: kToolbarHeight), + child: FrostedGlassTextSizeSlider(textEditor: textEditor), + ), + ), + + /// Appbar + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) { + return FrostedGlassTextAppbar(textEditor: textEditor); + }, + ), + + /// Bottombar + ReactiveCustomWidget( + stream: rebuildStream, + builder: (_) => FrostedGlassTextBottomBar( + configs: textEditor.configs, + initColor: textEditor.primaryColor, + onColorChanged: (color) { + textEditor.primaryColor = color; + }, + selectedStyle: textEditor.selectedTextStyle, + onFontChange: textEditor.setTextStyle, + ), + ), + ]; + } +} diff --git a/lib/src/views/camera_preview_view.dart b/lib/src/views/camera_preview_view.dart new file mode 100644 index 0000000..a9a9855 --- /dev/null +++ b/lib/src/views/camera_preview_view.dart @@ -0,0 +1,357 @@ +import 'package:camera/camera.dart'; +import 'camera_editor_view.dart'; +import 'package:flutter/gestures.dart'; +import 'package:flutter/material.dart'; +import 'dart:math'; + +class CameraPreviewView extends StatefulWidget { + const CameraPreviewView({ + super.key, + required this.cameras, + }); + + final List cameras; + static const routeName = '/camera_preview'; + + @override + CameraPreviewViewState createState() => CameraPreviewViewState(); +} + +class CameraPreviewViewState extends State { + late CameraController _controller; + late Future _initializeControllerFuture; + + int _selectedCameraIdx = 0; + + double _baseScaleFactor = 1.0; + double _basePanY = 0.0; + double _scaleFactor = 1; + double _minimumScaleFactor = 1; + + @override + void initState() { + super.initState(); + // To display the current output from the Camera, + // create a CameraController. + + _controller = CameraController( + // Get a specific camera from the list of available cameras. + widget.cameras.first, + // Define the resolution to use. + ResolutionPreset.max, + ); + + final size = Size(50, 300); + + _controller.initialize().then((_) { + _controller.value = _controller.value.copyWith(previewSize: size); + setState(() {}); + }); + + // Next, initialize the controller. This returns a Future. + _initializeControllerFuture = _controller.initialize(); + } + + Future updateController() async { + await _controller.setDescription(widget.cameras[_selectedCameraIdx]); + } + + @override + void dispose() { + // Dispose of the controller when the widget is disposed. + _controller.dispose(); + super.dispose(); + } + + // function for cropping image + Future takePicture() async { + try { + await _initializeControllerFuture; + final image = await _controller.takePicture(); + + if (!context.mounted) return; + await Navigator.of(context).push( + MaterialPageRoute( + builder: (context) => CameraEditorView( + imagePath: image.path, + ), + ), + ); + } catch (e) { + // If an error occurs, log the error to the console. + print(e); + } + } + + List getImageSize(double height, double width) { + // https://github.com/flutter/flutter/issues/15953#issuecomment-855182376 + + final screenH = max(height, width); + final screenW = min(height, width); + + var ratioContainer = screenH / screenW; + + var tmp = _controller.value.previewSize!; + final previewH = max(tmp.height, tmp.width); + final previewW = min(tmp.height, tmp.width); + + var ratio = previewH / previewW; + var missing = ratioContainer - ratio; + + final maxHeight = screenH; + final maxWidth = screenH * 0.5625; + + _minimumScaleFactor = 1 + missing; + + return [maxHeight, maxWidth]; + } + + Future updateScaleFactor(double newScale) async { + var minFactor = await _controller.getMinZoomLevel(); + var maxFactor = await _controller.getMaxZoomLevel(); + if (newScale < minFactor) { + newScale = minFactor; + } + if (newScale > maxFactor) { + newScale = maxFactor; + } + + print(newScale); + if (newScale <= 1) { + await _controller.setZoomLevel(newScale); + } else { + //await _controller.setZoomLevel(1.0); + } + setState(() { + _scaleFactor = newScale; + }); + } + + @override + Widget build(BuildContext context) { + var isFront = widget.cameras[_selectedCameraIdx].lensDirection == + CameraLensDirection.front; + // Fill this out in the next steps. + // You must wait until the controller is initialized before displaying the + // camera preview. Use a FutureBuilder to display a loading spinner until the + // controller has finished initializing. + return Scaffold( + body: GestureDetector( + onPanStart: (details) async { + if (_scaleFactor <= 1) { + await updateScaleFactor(1); + } + setState(() { + _basePanY = details.localPosition.dy; + _baseScaleFactor = _scaleFactor; + }); + }, + onPanUpdate: (details) async { + final diff = details.localPosition.dy - _basePanY; + final updateScale = diff / 50; + var tmp = _baseScaleFactor - updateScale; + if (tmp <= 1) tmp = 1.00001; + updateScaleFactor(tmp); + }, + // onScaleStart: (details) { + // _baseScaleFactor = _scaleFactor; + // }, + // onScaleUpdate: (details) async { + // // print(scale.scale); + // var scaleFactor = + // ((_baseScaleFactor * details.scale * 10).round() / 10); + // var maxFactor = await _controller.getMaxZoomLevel(); + // if (scaleFactor > maxFactor) scaleFactor = maxFactor; + // if (scaleFactor != _scaleFactor) { + // await updateScaleFactor(scaleFactor); + // } + // }, + onTap: () {}, + onDoubleTap: () { + setState(() { + _selectedCameraIdx = (_selectedCameraIdx + 1) % 2; + updateController(); + }); + }, + child: Padding( + padding: const EdgeInsets.only(top: 60, bottom: 40), + child: ClipRRect( + borderRadius: BorderRadius.circular(22), + child: FutureBuilder( + future: _initializeControllerFuture, + builder: (context, snapshot) { + if (snapshot.connectionState != ConnectionState.done) { + return const Center(child: CircularProgressIndicator()); + } + return Stack( + alignment: Alignment.bottomCenter, + children: [ + LayoutBuilder( + builder: + (BuildContext context, BoxConstraints constraints) { + var height = constraints.maxHeight; + var width = constraints.maxWidth; + + return OverflowBox( + maxHeight: getImageSize(height, width)[0], + maxWidth: getImageSize(height, width)[1], + child: Transform( + alignment: Alignment.center, + transform: Matrix4.rotationY(isFront ? pi : 0), + child: Transform.scale( + scale: _minimumScaleFactor + + (_scaleFactor > 1 ? _scaleFactor : 1) - + 1, + child: CameraPreview(_controller)), + ), + ); + }, + ), + Positioned( + bottom: 50, + child: Column( + children: [ + CameraZoomButtons( + key: widget.key, + isFront: isFront, + scaleFactor: _scaleFactor, + updateScaleFactor: updateScaleFactor, + controller: _controller, + ), + SizedBox(height: 10), + GestureDetector( + onTap: () async { + await takePicture(); + }, + onLongPress: () async {}, + child: Container( + height: 100, + width: 100, + clipBehavior: Clip.antiAliasWithSaveLayer, + padding: const EdgeInsets.all(2), + decoration: BoxDecoration( + shape: BoxShape.circle, + border: Border.all( + width: 7, + color: Colors.white, + ), + ), + ), + ), + ], + ), + ), + ], + ); + }, + ), + ), + ), + ), + ); + } +} + +class CameraZoomButtons extends StatefulWidget { + const CameraZoomButtons( + {super.key, + required this.isFront, + required this.controller, + required this.updateScaleFactor, + required this.scaleFactor}); + + final bool isFront; + final CameraController controller; + final double scaleFactor; + final Function updateScaleFactor; + + @override + State createState() => _CameraZoomButtonsState(); +} + +String beautifulZoomScale(double scale) { + var tmp = scale.toStringAsFixed(1); + if (tmp[0] == "0") { + tmp = tmp.substring(1, tmp.length); + } + return tmp; +} + +class _CameraZoomButtonsState extends State { + @override + Widget build(BuildContext context) { + final zoomButtonStyle = TextButton.styleFrom( + padding: EdgeInsets.zero, + foregroundColor: Colors.white, + minimumSize: Size(40, 40), + alignment: Alignment.center, + tapTargetSize: MaterialTapTargetSize.shrinkWrap); + + final zoomTextStyle = TextStyle(fontSize: 13); + return ClipRRect( + borderRadius: BorderRadius.circular(40.0), + child: Container( + color: const Color.fromARGB(90, 0, 0, 0), + child: Row( + children: widget.isFront + ? [] + : [ + TextButton( + style: zoomButtonStyle, + onPressed: () async { + var level = await widget.controller.getMinZoomLevel(); + widget.updateScaleFactor(level); + }, + child: FutureBuilder( + future: widget.controller.getMinZoomLevel(), + builder: (context, snap) { + if (snap.hasData) { + var minLevel = + beautifulZoomScale(snap.data!.toDouble()); + var currentLevel = + beautifulZoomScale(widget.scaleFactor); + return Text( + widget.scaleFactor < 1 + ? "${currentLevel}x" + : "${minLevel}x", + style: zoomTextStyle, + ); + } else { + return Text(""); + } + }), + ), + TextButton( + style: zoomButtonStyle, + onPressed: () { + widget.updateScaleFactor(1.0); + }, + child: Text( + widget.scaleFactor >= 1 + ? "${beautifulZoomScale(widget.scaleFactor)}x" + : "1.0x", + style: zoomTextStyle, + )), + TextButton( + style: zoomButtonStyle, + onPressed: () async { + var level = await widget.controller.getMaxZoomLevel(); + widget.updateScaleFactor(level); + }, + child: FutureBuilder( + future: widget.controller.getMaxZoomLevel(), + builder: (context, snap) { + if (snap.hasData) { + var maxLevel = snap.data?.toInt(); + return Text("${maxLevel}x", style: zoomTextStyle); + } else { + return Text(""); + } + }), + ) + ], + ), + ), + ); + } +} diff --git a/lib/src/views/chat_item_details_view.dart b/lib/src/views/chat_item_details_view.dart new file mode 100644 index 0000000..a6782e8 --- /dev/null +++ b/lib/src/views/chat_item_details_view.dart @@ -0,0 +1,22 @@ +import 'package:flutter/material.dart'; + +/// Displays detailed information about a SampleItem. +class SampleItemDetailsView extends StatelessWidget { + const SampleItemDetailsView({super.key, required this.userId}); + + final int userId; + + static const routeName = '/sample_item'; + + @override + Widget build(BuildContext context) { + return Scaffold( + appBar: AppBar( + title: Text('Your Chat with $userId'), + ), + body: const Center( + child: Text('Hallo!'), + ), + ); + } +} diff --git a/lib/src/views/chat_list_view.dart b/lib/src/views/chat_list_view.dart new file mode 100644 index 0000000..b67ca37 --- /dev/null +++ b/lib/src/views/chat_list_view.dart @@ -0,0 +1,277 @@ +import 'add_new_user_view.dart'; +import 'package:flutter/material.dart'; +import 'chat_item_details_view.dart'; +import 'dart:async'; + +enum MessageSendState { sending, send, opened, received } + +class ChatItem { + const ChatItem( + {required this.username, + required this.flames, + required this.userId, + required this.state, + required this.lastMessageInSeconds}); + final String username; + final int lastMessageInSeconds; + final int flames; + final int userId; + final MessageSendState state; +} + +/// Displays a list of SampleItems. +class ChatListView extends StatefulWidget { + const ChatListView({ + super.key, + this.items = const [ + ChatItem( + userId: 0, + username: "Alisa", + lastMessageInSeconds: 10, + flames: 129, + state: MessageSendState.sending), + ChatItem( + userId: 1, + username: "Franz", + lastMessageInSeconds: 20829, + flames: 0, + state: MessageSendState.received), + ChatItem( + userId: 2, + username: "Heiner", + lastMessageInSeconds: 291829, + state: MessageSendState.opened, + flames: 38), + ], + }); + + final List items; + + @override + State createState() => _ChatListViewState(); +} + +class _ChatListViewState extends State { + int _secondsSinceOpen = 0; + late Timer _timer; + + @override + void initState() { + super.initState(); + _startTimer(); + } + + void _startTimer() { + _timer = Timer.periodic(Duration(seconds: 1), (timer) { + setState(() { + _secondsSinceOpen++; + }); + }); + } + + @override + void dispose() { + _timer.cancel(); // Cancel the timer when the widget is disposed + super.dispose(); + } + + String formatDuration(int seconds) { + if (seconds < 60) { + return '$seconds Sec.'; + } else if (seconds < 3600) { + int minutes = seconds ~/ 60; + return '$minutes Min.'; + } else if (seconds < 86400) { + int hours = seconds ~/ 3600; + return '$hours Hrs.'; // Assuming "Stu." is for hours + } else { + int days = seconds ~/ 86400; + return '$days Days'; + } + } + + Widget getMessageSateIcon(MessageSendState state) { + List children = []; + Widget icon = Placeholder(); + String text = ""; + + switch (state) { + case MessageSendState.opened: + icon = Icon( + Icons.crop_square, + size: 14, + color: Theme.of(context).colorScheme.primary, + ); + text = "Opened"; + break; + case MessageSendState.received: + icon = Icon(Icons.square_rounded, + size: 14, color: Theme.of(context).colorScheme.primary); + text = "Received"; + break; + case MessageSendState.send: + icon = Icon(Icons.send, size: 14); + text = "Send"; + break; + case MessageSendState.sending: + icon = Row(children: [ + SizedBox( + width: 10, + height: 10, + child: CircularProgressIndicator( + strokeWidth: 1, + )), + SizedBox(width: 2) + ]); + text = "Sending"; + break; + } + children.add(const SizedBox(width: 5)); + return Row( + children: [ + icon, + const SizedBox(width: 3), + Text(text, style: TextStyle(fontSize: 12)), + const SizedBox(width: 5) + ], + ); + } + + Widget getSubtitle(ChatItem item) { + return Row( + children: [ + getMessageSateIcon(item.state), + Text("•"), + const SizedBox(width: 5), + Text(formatDuration(item.lastMessageInSeconds + _secondsSinceOpen), + style: TextStyle(fontSize: 12)), + if (item.flames > 0) + Row( + children: [ + const SizedBox(width: 5), + Text("•"), + const SizedBox(width: 5), + Text(item.flames.toString(), style: TextStyle(fontSize: 12)), + Icon( + Icons.local_fire_department_sharp, + color: const Color.fromARGB(255, 215, 73, 58), + size: 16, + ), + ], + ) + ], + ); + } + + Widget createInitialsAvatar(String username) { + // Extract initials from the username + List nameParts = username.split(' '); + String initials = nameParts.map((part) => part[0]).join().toUpperCase(); + + // Generate a color based on the initials (you can customize this logic) + Color avatarColor = _getColorFromInitials(initials); + + return CircleAvatar( + backgroundColor: avatarColor, + child: Text( + initials, + style: TextStyle( + color: _getTextColor(Colors.white), fontWeight: FontWeight.bold), + ), + ); + } + + Color _getTextColor(Color backgroundColor) { + // Calculate the luminance of the background color + double luminance = backgroundColor.computeLuminance(); + // Return white for dark backgrounds and black for light backgrounds + return luminance < 0.5 ? Colors.white : Colors.black; + } + + Color _getColorFromInitials(String initials) { + // Define color lists for light and dark themes + List lightColors = [ + Colors.red, + Colors.green, + Colors.blue, + Colors.orange, + Colors.purple, + Colors.teal, + Colors.amber, + Colors.indigo, + Colors.cyan, + Colors.lime, + Colors.pink, + Colors.brown, + Colors.grey, + ]; + + List darkColors = [ + Colors.deepOrange, + Colors.deepPurple, + Colors.redAccent, + Colors.greenAccent, + Colors.blueAccent, + Colors.orangeAccent, + Colors.purpleAccent, + Colors.tealAccent, + Colors.amberAccent, + Colors.indigoAccent, + Colors.cyanAccent, + Colors.limeAccent, + Colors.pinkAccent, + ]; + + // Simple logic to generate a hash from initials + int hash = initials.codeUnits.fold(0, (prev, element) => prev + element); + + // Select the appropriate color list based on the current theme brightness + List colors = Theme.of(context).brightness == Brightness.dark + ? darkColors + : lightColors; + + // Use the hash to select a color from the list + return colors[hash % colors.length]; + } + + @override + Widget build(BuildContext context) { + return Scaffold( + appBar: AppBar( + title: const Text('Chats'), + ), + body: ListView.builder( + restorationId: 'sampleItemListView', + itemCount: widget.items.length, + itemBuilder: (BuildContext context, int index) { + final item = widget.items[index]; + return ListTile( + title: Text(item.username), + subtitle: getSubtitle(item), + leading: createInitialsAvatar(item.username), + onTap: () { + Navigator.push( + context, + MaterialPageRoute( + builder: (context) => SampleItemDetailsView( + userId: item.userId, + ), + ), + ); + }); + }, + ), + floatingActionButton: FloatingActionButton( + onPressed: () { + Navigator.push( + context, + MaterialPageRoute( + builder: (context) => AddNewUserView(), + ), + ); + }, + child: const Icon(Icons.add), + ), + ); + } +} diff --git a/lib/src/views/home_view.dart b/lib/src/views/home_view.dart new file mode 100644 index 0000000..1c1fa69 --- /dev/null +++ b/lib/src/views/home_view.dart @@ -0,0 +1,77 @@ +import 'package:camera/camera.dart'; +import 'camera_preview_view.dart'; +import 'chat_list_view.dart'; +import 'permissions_view.dart'; +import 'profile_view.dart'; +import '../settings/settings_controller.dart'; +import 'package:flutter/material.dart'; + +class HomeView extends StatefulWidget { + const HomeView( + {super.key, required this.settingsController, required this.cameras}); + final SettingsController settingsController; + final List cameras; + + @override + State createState() => HomeViewState(); +} + +class HomeViewState extends State { + int _activePageIdx = 0; + final PageController _pageController = PageController(initialPage: 0); + @override + Widget build(BuildContext context) { + return FutureBuilder( + future: checkPermissions(), + builder: (context, snap) { + if (snap.hasData) { + if (snap.data!) { + return Scaffold( + body: PageView( + controller: _pageController, + onPageChanged: (index) { + setState(() { + _activePageIdx = index; + }); + }, + children: [ + ChatListView(), + CameraPreviewView(cameras: widget.cameras), + ProfileView(settingsController: widget.settingsController) + ], + ), + bottomNavigationBar: BottomNavigationBar( + showSelectedLabels: false, + showUnselectedLabels: false, + selectedIconTheme: IconThemeData( + color: const Color.fromARGB(255, 255, 255, 255)), + items: [ + BottomNavigationBarItem(icon: Icon(Icons.chat), label: ""), + BottomNavigationBarItem( + icon: Icon(Icons.camera_alt), + label: "", + ), + BottomNavigationBarItem( + icon: Icon(Icons.verified_user), label: ""), + ], + onTap: (int index) { + setState(() { + _activePageIdx = index; + _pageController.animateToPage(_activePageIdx, + duration: const Duration(milliseconds: 100), + curve: Curves.bounceIn); + }); + }, + currentIndex: _activePageIdx, + ), + ); + } else { + return PermissionHandlerView(onSuccess: () { + setState(() {}); + }); + } + } + return const CircularProgressIndicator(); + }); + } +} diff --git a/lib/src/views/permissions_view.dart b/lib/src/views/permissions_view.dart new file mode 100644 index 0000000..fec8b7f --- /dev/null +++ b/lib/src/views/permissions_view.dart @@ -0,0 +1,85 @@ +import 'package:flutter/material.dart'; +import 'package:permission_handler/permission_handler.dart'; + +class PermissionHandlerView extends StatefulWidget { + const PermissionHandlerView({super.key, required this.onSuccess}); + + final Function onSuccess; + + @override + _PermissionHandlerViewState createState() => _PermissionHandlerViewState(); +} + +Future checkPermissions() async { + if (!await Permission.camera.isGranted) { + return false; + } + if (!await Permission.microphone.isGranted) { + return false; + } + return true; +} + +class _PermissionHandlerViewState extends State { + Future> permissionServices() async { + // You can request multiple permissions at once. + Map statuses = await [ + Permission.camera, + Permission.microphone, + //add more permission to request here. + ].request(); + + if (statuses[Permission.microphone]!.isPermanentlyDenied) { + openAppSettings(); + // setState(() {}); + } else { + // if (statuses[Permission.microphone]!.isDenied) { + // } + } + + if (statuses[Permission.camera]!.isPermanentlyDenied) { + openAppSettings(); + // setState(() {}); + } else { + // if (statuses[Permission.camera]!.isDenied) { + // } + } + /*{Permission.camera: PermissionStatus.granted, Permission.storage: PermissionStatus.granted}*/ + return statuses; + } + + @override + Widget build(BuildContext context) { + return PopScope( + onPopInvokedWithResult: (bool didPop, Object? result) async {}, + child: Scaffold( + body: Center( + child: Container( + padding: EdgeInsets.all(100), + child: Column( + mainAxisAlignment: MainAxisAlignment.center, + crossAxisAlignment: CrossAxisAlignment.center, + children: [ + Text( + "Connect needs access to the camera and microphone for obvious reasons.", + textAlign: TextAlign.center, + ), + SizedBox(height: 50), + FilledButton.icon( + label: Text("Request permissions"), + icon: const Icon(Icons.perm_camera_mic), + onPressed: () async { + permissionServices(); + if (await checkPermissions()) { + widget.onSuccess(); + } + }, + ), + ], + ), + ), + ), + ), + ); + } +} diff --git a/lib/src/views/profile_view.dart b/lib/src/views/profile_view.dart new file mode 100644 index 0000000..2892f69 --- /dev/null +++ b/lib/src/views/profile_view.dart @@ -0,0 +1,59 @@ +import '../settings/settings_controller.dart'; +import '../settings/settings_view.dart'; +import '../utils.dart'; +import 'package:restart_app/restart_app.dart'; +import 'package:flutter/material.dart'; + +class ProfileView extends StatefulWidget { + const ProfileView({super.key, required this.settingsController}); + + final SettingsController settingsController; + + @override + State createState() => _ProfileViewState(); +} + +class _ProfileViewState extends State { + @override + Widget build(BuildContext context) { + // var user = await getUser(); + return Scaffold( + appBar: AppBar( + title: FutureBuilder( + future: getUser(), + builder: (context, snap) { + if (snap.hasData) { + return Text("Hello ${snap.data!.username}!"); + } else { + return CircularProgressIndicator(); + } + }), + actions: [ + IconButton( + icon: const Icon(Icons.settings), + onPressed: () { + // Navigate to the settings page. If the user leaves and returns + // to the app after it has been killed while running in the + // background, the navigation stack is restored. + Navigator.push( + context, + MaterialPageRoute( + builder: (context) => + SettingsView(controller: widget.settingsController)), + ); + }, + ), + ]), + body: FilledButton.icon( + onPressed: () async { + await deleteLocalUserData(); + Restart.restartApp( + notificationTitle: 'Successfully logged out', + notificationBody: 'Click here to open the app again', + ); + }, + label: Text("Logout"), + icon: Icon(Icons.no_accounts)), + ); + } +} diff --git a/lib/src/views/register_view.dart b/lib/src/views/register_view.dart new file mode 100644 index 0000000..699384d --- /dev/null +++ b/lib/src/views/register_view.dart @@ -0,0 +1,152 @@ +import '../utils.dart'; +import 'package:flutter/material.dart'; +import 'package:flutter/services.dart'; + +class RegisterView extends StatefulWidget { + const RegisterView({super.key, required this.callbackOnSuccess}); + + final Function callbackOnSuccess; + @override + State createState() => _RegisterViewState(); +} + +class MyButton extends StatelessWidget { + final void Function()? onTap; + final String text; + const MyButton({super.key, required this.onTap, required this.text}); + + @override + Widget build(BuildContext context) { + return GestureDetector( + onTap: onTap, + child: Container( + padding: const EdgeInsets.all(10), + decoration: BoxDecoration( + color: Theme.of(context).colorScheme.primary, + borderRadius: BorderRadius.circular(9), + ), + child: Center( + child: Text( + text, + textAlign: TextAlign.center, + ), + ), + ), + ); + } +} + +class _RegisterViewState extends State { + final TextEditingController usernameController = TextEditingController(); + final TextEditingController inviteCodeController = TextEditingController(); + + @override + Widget build(BuildContext context) { + InputDecoration getInputDecoration(hintText) { + return InputDecoration(hintText: hintText, fillColor: Colors.grey[400]); + } + + return Scaffold( + appBar: AppBar( + title: Text("Welcome to Connect!"), + ), + body: Padding( + padding: EdgeInsets.all(10), + child: ListView( + children: [ + const SizedBox(height: 20), + Center( + child: Text( + "You made the right decision using Connect which is like SnXpchat but encrypted using the Signal protocol.", + textAlign: TextAlign.center, + style: TextStyle(fontSize: 15), + ), + ), + const SizedBox(height: 40), + Center( + child: Text( + "Choice wisely, this username can't be changed. Only lowercase and numbers are allowed!", + textAlign: TextAlign.center, + ), + ), + const SizedBox(height: 10), + TextField( + controller: usernameController, + inputFormatters: [ + LengthLimitingTextInputFormatter( + 12), // Limit to 12 characters + FilteringTextInputFormatter.allow(RegExp( + r'[a-z0-9]')), // Allow only lowercase letters and numbers + ], + decoration: getInputDecoration("Username")), + const SizedBox(height: 15), + Center( + child: Text( + "To protect this small experimental project you need an invitation code! To get one just ask the right person!", + textAlign: TextAlign.center, + ), + ), + const SizedBox(height: 10), + TextField( + controller: inviteCodeController, + decoration: getInputDecoration("Invitation code")), + const SizedBox(height: 25), + Center( + child: Text( + "Where is the password? There is none! So make a backup of your Connect identity in the settings or you will lose your access if you lose your device!", + textAlign: TextAlign.center, + ), + ), + const SizedBox(height: 30), + FilledButton.icon( + icon: Icon(Icons.group), + onPressed: () async { + final success = await createNewUser( + usernameController.text, inviteCodeController.text); + if (success == null) { + widget.callbackOnSuccess(); + return; + } + showAlertDialog(context, "Oh no!", success); + }, + label: Text("Komm in die Gruppe!"), + ), + OutlinedButton.icon( + onPressed: () { + showAlertDialog(context, "Coming soon", + "This feature is not yet implemented! Just create a new account :/"); + }, + label: Text("Restore identity")), + // MyButton(onTap: () {}, text: "Komm in die Gruppe!") + ], + )), + ); + } +} + +showAlertDialog(BuildContext context, String title, String content) { + // set up the button + Widget okButton = TextButton( + child: Text("OK"), + onPressed: () { + Navigator.pop(context); + }, + ); + + // set up the AlertDialog + AlertDialog alert = AlertDialog( + title: Text(title), + content: Text(content), + actions: [ + okButton, + ], + ); + + // show the dialog + showDialog( + context: context, + builder: (BuildContext context) { + return alert; + }, + ); +} diff --git a/linux/.gitignore b/linux/.gitignore new file mode 100644 index 0000000..d3896c9 --- /dev/null +++ b/linux/.gitignore @@ -0,0 +1 @@ +flutter/ephemeral diff --git a/linux/CMakeLists.txt b/linux/CMakeLists.txt new file mode 100644 index 0000000..50fa8d0 --- /dev/null +++ b/linux/CMakeLists.txt @@ -0,0 +1,145 @@ +# Project-level configuration. +cmake_minimum_required(VERSION 3.10) +project(runner LANGUAGES CXX) + +# The name of the executable created for the application. Change this to change +# the on-disk name of your application. +set(BINARY_NAME "connect") +# The unique GTK application identifier for this application. See: +# https://wiki.gnome.org/HowDoI/ChooseApplicationID +set(APPLICATION_ID "com.example.connect") + +# Explicitly opt in to modern CMake behaviors to avoid warnings with recent +# versions of CMake. +cmake_policy(SET CMP0063 NEW) + +# Load bundled libraries from the lib/ directory relative to the binary. +set(CMAKE_INSTALL_RPATH "$ORIGIN/lib") + +# Root filesystem for cross-building. +if(FLUTTER_TARGET_PLATFORM_SYSROOT) + set(CMAKE_SYSROOT ${FLUTTER_TARGET_PLATFORM_SYSROOT}) + set(CMAKE_FIND_ROOT_PATH ${CMAKE_SYSROOT}) + set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) + set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY) + set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) + set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) +endif() + +# Define build configuration options. +if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES) + set(CMAKE_BUILD_TYPE "Debug" CACHE + STRING "Flutter build mode" FORCE) + set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS + "Debug" "Profile" "Release") +endif() + +# Compilation settings that should be applied to most targets. +# +# Be cautious about adding new options here, as plugins use this function by +# default. In most cases, you should add new options to specific targets instead +# of modifying this function. +function(APPLY_STANDARD_SETTINGS TARGET) + target_compile_features(${TARGET} PUBLIC cxx_std_14) + target_compile_options(${TARGET} PRIVATE -Wall -Werror) + target_compile_options(${TARGET} PRIVATE "$<$>:-O3>") + target_compile_definitions(${TARGET} PRIVATE "$<$>:NDEBUG>") +endfunction() + +# Flutter library and tool build rules. +set(FLUTTER_MANAGED_DIR "${CMAKE_CURRENT_SOURCE_DIR}/flutter") +add_subdirectory(${FLUTTER_MANAGED_DIR}) + +# System-level dependencies. +find_package(PkgConfig REQUIRED) +pkg_check_modules(GTK REQUIRED IMPORTED_TARGET gtk+-3.0) + +add_definitions(-DAPPLICATION_ID="${APPLICATION_ID}") + +# Define the application target. To change its name, change BINARY_NAME above, +# not the value here, or `flutter run` will no longer work. +# +# Any new source files that you add to the application should be added here. +add_executable(${BINARY_NAME} + "main.cc" + "my_application.cc" + "${FLUTTER_MANAGED_DIR}/generated_plugin_registrant.cc" +) + +# Apply the standard set of build settings. This can be removed for applications +# that need different build settings. +apply_standard_settings(${BINARY_NAME}) + +# Add dependency libraries. Add any application-specific dependencies here. +target_link_libraries(${BINARY_NAME} PRIVATE flutter) +target_link_libraries(${BINARY_NAME} PRIVATE PkgConfig::GTK) + +# Run the Flutter tool portions of the build. This must not be removed. +add_dependencies(${BINARY_NAME} flutter_assemble) + +# Only the install-generated bundle's copy of the executable will launch +# correctly, since the resources must in the right relative locations. To avoid +# people trying to run the unbundled copy, put it in a subdirectory instead of +# the default top-level location. +set_target_properties(${BINARY_NAME} + PROPERTIES + RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/intermediates_do_not_run" +) + + +# Generated plugin build rules, which manage building the plugins and adding +# them to the application. +include(flutter/generated_plugins.cmake) + + +# === Installation === +# By default, "installing" just makes a relocatable bundle in the build +# directory. +set(BUILD_BUNDLE_DIR "${PROJECT_BINARY_DIR}/bundle") +if(CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT) + set(CMAKE_INSTALL_PREFIX "${BUILD_BUNDLE_DIR}" CACHE PATH "..." FORCE) +endif() + +# Start with a clean build bundle directory every time. +install(CODE " + file(REMOVE_RECURSE \"${BUILD_BUNDLE_DIR}/\") + " COMPONENT Runtime) + +set(INSTALL_BUNDLE_DATA_DIR "${CMAKE_INSTALL_PREFIX}/data") +set(INSTALL_BUNDLE_LIB_DIR "${CMAKE_INSTALL_PREFIX}/lib") + +install(TARGETS ${BINARY_NAME} RUNTIME DESTINATION "${CMAKE_INSTALL_PREFIX}" + COMPONENT Runtime) + +install(FILES "${FLUTTER_ICU_DATA_FILE}" DESTINATION "${INSTALL_BUNDLE_DATA_DIR}" + COMPONENT Runtime) + +install(FILES "${FLUTTER_LIBRARY}" DESTINATION "${INSTALL_BUNDLE_LIB_DIR}" + COMPONENT Runtime) + +foreach(bundled_library ${PLUGIN_BUNDLED_LIBRARIES}) + install(FILES "${bundled_library}" + DESTINATION "${INSTALL_BUNDLE_LIB_DIR}" + COMPONENT Runtime) +endforeach(bundled_library) + +# Copy the native assets provided by the build.dart from all packages. +set(NATIVE_ASSETS_DIR "${PROJECT_BUILD_DIR}native_assets/linux/") +install(DIRECTORY "${NATIVE_ASSETS_DIR}" + DESTINATION "${INSTALL_BUNDLE_LIB_DIR}" + COMPONENT Runtime) + +# Fully re-copy the assets directory on each build to avoid having stale files +# from a previous install. +set(FLUTTER_ASSET_DIR_NAME "flutter_assets") +install(CODE " + file(REMOVE_RECURSE \"${INSTALL_BUNDLE_DATA_DIR}/${FLUTTER_ASSET_DIR_NAME}\") + " COMPONENT Runtime) +install(DIRECTORY "${PROJECT_BUILD_DIR}/${FLUTTER_ASSET_DIR_NAME}" + DESTINATION "${INSTALL_BUNDLE_DATA_DIR}" COMPONENT Runtime) + +# Install the AOT library on non-Debug builds only. +if(NOT CMAKE_BUILD_TYPE MATCHES "Debug") + install(FILES "${AOT_LIBRARY}" DESTINATION "${INSTALL_BUNDLE_LIB_DIR}" + COMPONENT Runtime) +endif() diff --git a/linux/flutter/CMakeLists.txt b/linux/flutter/CMakeLists.txt new file mode 100644 index 0000000..d5bd016 --- /dev/null +++ b/linux/flutter/CMakeLists.txt @@ -0,0 +1,88 @@ +# This file controls Flutter-level build steps. It should not be edited. +cmake_minimum_required(VERSION 3.10) + +set(EPHEMERAL_DIR "${CMAKE_CURRENT_SOURCE_DIR}/ephemeral") + +# Configuration provided via flutter tool. +include(${EPHEMERAL_DIR}/generated_config.cmake) + +# TODO: Move the rest of this into files in ephemeral. See +# https://github.com/flutter/flutter/issues/57146. + +# Serves the same purpose as list(TRANSFORM ... PREPEND ...), +# which isn't available in 3.10. +function(list_prepend LIST_NAME PREFIX) + set(NEW_LIST "") + foreach(element ${${LIST_NAME}}) + list(APPEND NEW_LIST "${PREFIX}${element}") + endforeach(element) + set(${LIST_NAME} "${NEW_LIST}" PARENT_SCOPE) +endfunction() + +# === Flutter Library === +# System-level dependencies. +find_package(PkgConfig REQUIRED) +pkg_check_modules(GTK REQUIRED IMPORTED_TARGET gtk+-3.0) +pkg_check_modules(GLIB REQUIRED IMPORTED_TARGET glib-2.0) +pkg_check_modules(GIO REQUIRED IMPORTED_TARGET gio-2.0) + +set(FLUTTER_LIBRARY "${EPHEMERAL_DIR}/libflutter_linux_gtk.so") + +# Published to parent scope for install step. +set(FLUTTER_LIBRARY ${FLUTTER_LIBRARY} PARENT_SCOPE) +set(FLUTTER_ICU_DATA_FILE "${EPHEMERAL_DIR}/icudtl.dat" PARENT_SCOPE) +set(PROJECT_BUILD_DIR "${PROJECT_DIR}/build/" PARENT_SCOPE) +set(AOT_LIBRARY "${PROJECT_DIR}/build/lib/libapp.so" PARENT_SCOPE) + +list(APPEND FLUTTER_LIBRARY_HEADERS + "fl_basic_message_channel.h" + "fl_binary_codec.h" + "fl_binary_messenger.h" + "fl_dart_project.h" + "fl_engine.h" + "fl_json_message_codec.h" + "fl_json_method_codec.h" + "fl_message_codec.h" + "fl_method_call.h" + "fl_method_channel.h" + "fl_method_codec.h" + "fl_method_response.h" + "fl_plugin_registrar.h" + "fl_plugin_registry.h" + "fl_standard_message_codec.h" + "fl_standard_method_codec.h" + "fl_string_codec.h" + "fl_value.h" + "fl_view.h" + "flutter_linux.h" +) +list_prepend(FLUTTER_LIBRARY_HEADERS "${EPHEMERAL_DIR}/flutter_linux/") +add_library(flutter INTERFACE) +target_include_directories(flutter INTERFACE + "${EPHEMERAL_DIR}" +) +target_link_libraries(flutter INTERFACE "${FLUTTER_LIBRARY}") +target_link_libraries(flutter INTERFACE + PkgConfig::GTK + PkgConfig::GLIB + PkgConfig::GIO +) +add_dependencies(flutter flutter_assemble) + +# === Flutter tool backend === +# _phony_ is a non-existent file to force this command to run every time, +# since currently there's no way to get a full input/output list from the +# flutter tool. +add_custom_command( + OUTPUT ${FLUTTER_LIBRARY} ${FLUTTER_LIBRARY_HEADERS} + ${CMAKE_CURRENT_BINARY_DIR}/_phony_ + COMMAND ${CMAKE_COMMAND} -E env + ${FLUTTER_TOOL_ENVIRONMENT} + "${FLUTTER_ROOT}/packages/flutter_tools/bin/tool_backend.sh" + ${FLUTTER_TARGET_PLATFORM} ${CMAKE_BUILD_TYPE} + VERBATIM +) +add_custom_target(flutter_assemble DEPENDS + "${FLUTTER_LIBRARY}" + ${FLUTTER_LIBRARY_HEADERS} +) diff --git a/linux/flutter/generated_plugin_registrant.cc b/linux/flutter/generated_plugin_registrant.cc new file mode 100644 index 0000000..dd8425c --- /dev/null +++ b/linux/flutter/generated_plugin_registrant.cc @@ -0,0 +1,19 @@ +// +// Generated file. Do not edit. +// + +// clang-format off + +#include "generated_plugin_registrant.h" + +#include +#include + +void fl_register_plugins(FlPluginRegistry* registry) { + g_autoptr(FlPluginRegistrar) emoji_picker_flutter_registrar = + fl_plugin_registry_get_registrar_for_plugin(registry, "EmojiPickerFlutterPlugin"); + emoji_picker_flutter_plugin_register_with_registrar(emoji_picker_flutter_registrar); + g_autoptr(FlPluginRegistrar) flutter_secure_storage_linux_registrar = + fl_plugin_registry_get_registrar_for_plugin(registry, "FlutterSecureStorageLinuxPlugin"); + flutter_secure_storage_linux_plugin_register_with_registrar(flutter_secure_storage_linux_registrar); +} diff --git a/linux/flutter/generated_plugin_registrant.h b/linux/flutter/generated_plugin_registrant.h new file mode 100644 index 0000000..e0f0a47 --- /dev/null +++ b/linux/flutter/generated_plugin_registrant.h @@ -0,0 +1,15 @@ +// +// Generated file. Do not edit. +// + +// clang-format off + +#ifndef GENERATED_PLUGIN_REGISTRANT_ +#define GENERATED_PLUGIN_REGISTRANT_ + +#include + +// Registers Flutter plugins. +void fl_register_plugins(FlPluginRegistry* registry); + +#endif // GENERATED_PLUGIN_REGISTRANT_ diff --git a/linux/flutter/generated_plugins.cmake b/linux/flutter/generated_plugins.cmake new file mode 100644 index 0000000..a39777e --- /dev/null +++ b/linux/flutter/generated_plugins.cmake @@ -0,0 +1,25 @@ +# +# Generated file, do not edit. +# + +list(APPEND FLUTTER_PLUGIN_LIST + emoji_picker_flutter + flutter_secure_storage_linux +) + +list(APPEND FLUTTER_FFI_PLUGIN_LIST +) + +set(PLUGIN_BUNDLED_LIBRARIES) + +foreach(plugin ${FLUTTER_PLUGIN_LIST}) + add_subdirectory(flutter/ephemeral/.plugin_symlinks/${plugin}/linux plugins/${plugin}) + target_link_libraries(${BINARY_NAME} PRIVATE ${plugin}_plugin) + list(APPEND PLUGIN_BUNDLED_LIBRARIES $) + list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${plugin}_bundled_libraries}) +endforeach(plugin) + +foreach(ffi_plugin ${FLUTTER_FFI_PLUGIN_LIST}) + add_subdirectory(flutter/ephemeral/.plugin_symlinks/${ffi_plugin}/linux plugins/${ffi_plugin}) + list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${ffi_plugin}_bundled_libraries}) +endforeach(ffi_plugin) diff --git a/linux/main.cc b/linux/main.cc new file mode 100644 index 0000000..e7c5c54 --- /dev/null +++ b/linux/main.cc @@ -0,0 +1,6 @@ +#include "my_application.h" + +int main(int argc, char** argv) { + g_autoptr(MyApplication) app = my_application_new(); + return g_application_run(G_APPLICATION(app), argc, argv); +} diff --git a/linux/my_application.cc b/linux/my_application.cc new file mode 100644 index 0000000..93fd937 --- /dev/null +++ b/linux/my_application.cc @@ -0,0 +1,124 @@ +#include "my_application.h" + +#include +#ifdef GDK_WINDOWING_X11 +#include +#endif + +#include "flutter/generated_plugin_registrant.h" + +struct _MyApplication { + GtkApplication parent_instance; + char** dart_entrypoint_arguments; +}; + +G_DEFINE_TYPE(MyApplication, my_application, GTK_TYPE_APPLICATION) + +// Implements GApplication::activate. +static void my_application_activate(GApplication* application) { + MyApplication* self = MY_APPLICATION(application); + GtkWindow* window = + GTK_WINDOW(gtk_application_window_new(GTK_APPLICATION(application))); + + // Use a header bar when running in GNOME as this is the common style used + // by applications and is the setup most users will be using (e.g. Ubuntu + // desktop). + // If running on X and not using GNOME then just use a traditional title bar + // in case the window manager does more exotic layout, e.g. tiling. + // If running on Wayland assume the header bar will work (may need changing + // if future cases occur). + gboolean use_header_bar = TRUE; +#ifdef GDK_WINDOWING_X11 + GdkScreen* screen = gtk_window_get_screen(window); + if (GDK_IS_X11_SCREEN(screen)) { + const gchar* wm_name = gdk_x11_screen_get_window_manager_name(screen); + if (g_strcmp0(wm_name, "GNOME Shell") != 0) { + use_header_bar = FALSE; + } + } +#endif + if (use_header_bar) { + GtkHeaderBar* header_bar = GTK_HEADER_BAR(gtk_header_bar_new()); + gtk_widget_show(GTK_WIDGET(header_bar)); + gtk_header_bar_set_title(header_bar, "connect"); + gtk_header_bar_set_show_close_button(header_bar, TRUE); + gtk_window_set_titlebar(window, GTK_WIDGET(header_bar)); + } else { + gtk_window_set_title(window, "connect"); + } + + gtk_window_set_default_size(window, 1280, 720); + gtk_widget_show(GTK_WIDGET(window)); + + g_autoptr(FlDartProject) project = fl_dart_project_new(); + fl_dart_project_set_dart_entrypoint_arguments(project, self->dart_entrypoint_arguments); + + FlView* view = fl_view_new(project); + gtk_widget_show(GTK_WIDGET(view)); + gtk_container_add(GTK_CONTAINER(window), GTK_WIDGET(view)); + + fl_register_plugins(FL_PLUGIN_REGISTRY(view)); + + gtk_widget_grab_focus(GTK_WIDGET(view)); +} + +// Implements GApplication::local_command_line. +static gboolean my_application_local_command_line(GApplication* application, gchar*** arguments, int* exit_status) { + MyApplication* self = MY_APPLICATION(application); + // Strip out the first argument as it is the binary name. + self->dart_entrypoint_arguments = g_strdupv(*arguments + 1); + + g_autoptr(GError) error = nullptr; + if (!g_application_register(application, nullptr, &error)) { + g_warning("Failed to register: %s", error->message); + *exit_status = 1; + return TRUE; + } + + g_application_activate(application); + *exit_status = 0; + + return TRUE; +} + +// Implements GApplication::startup. +static void my_application_startup(GApplication* application) { + //MyApplication* self = MY_APPLICATION(object); + + // Perform any actions required at application startup. + + G_APPLICATION_CLASS(my_application_parent_class)->startup(application); +} + +// Implements GApplication::shutdown. +static void my_application_shutdown(GApplication* application) { + //MyApplication* self = MY_APPLICATION(object); + + // Perform any actions required at application shutdown. + + G_APPLICATION_CLASS(my_application_parent_class)->shutdown(application); +} + +// Implements GObject::dispose. +static void my_application_dispose(GObject* object) { + MyApplication* self = MY_APPLICATION(object); + g_clear_pointer(&self->dart_entrypoint_arguments, g_strfreev); + G_OBJECT_CLASS(my_application_parent_class)->dispose(object); +} + +static void my_application_class_init(MyApplicationClass* klass) { + G_APPLICATION_CLASS(klass)->activate = my_application_activate; + G_APPLICATION_CLASS(klass)->local_command_line = my_application_local_command_line; + G_APPLICATION_CLASS(klass)->startup = my_application_startup; + G_APPLICATION_CLASS(klass)->shutdown = my_application_shutdown; + G_OBJECT_CLASS(klass)->dispose = my_application_dispose; +} + +static void my_application_init(MyApplication* self) {} + +MyApplication* my_application_new() { + return MY_APPLICATION(g_object_new(my_application_get_type(), + "application-id", APPLICATION_ID, + "flags", G_APPLICATION_NON_UNIQUE, + nullptr)); +} diff --git a/linux/my_application.h b/linux/my_application.h new file mode 100644 index 0000000..72271d5 --- /dev/null +++ b/linux/my_application.h @@ -0,0 +1,18 @@ +#ifndef FLUTTER_MY_APPLICATION_H_ +#define FLUTTER_MY_APPLICATION_H_ + +#include + +G_DECLARE_FINAL_TYPE(MyApplication, my_application, MY, APPLICATION, + GtkApplication) + +/** + * my_application_new: + * + * Creates a new Flutter-based application. + * + * Returns: a new #MyApplication. + */ +MyApplication* my_application_new(); + +#endif // FLUTTER_MY_APPLICATION_H_ diff --git a/macos/.gitignore b/macos/.gitignore new file mode 100644 index 0000000..746adbb --- /dev/null +++ b/macos/.gitignore @@ -0,0 +1,7 @@ +# Flutter-related +**/Flutter/ephemeral/ +**/Pods/ + +# Xcode-related +**/dgph +**/xcuserdata/ diff --git a/macos/Flutter/Flutter-Debug.xcconfig b/macos/Flutter/Flutter-Debug.xcconfig new file mode 100644 index 0000000..4b81f9b --- /dev/null +++ b/macos/Flutter/Flutter-Debug.xcconfig @@ -0,0 +1,2 @@ +#include? "Pods/Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig" +#include "ephemeral/Flutter-Generated.xcconfig" diff --git a/macos/Flutter/Flutter-Release.xcconfig b/macos/Flutter/Flutter-Release.xcconfig new file mode 100644 index 0000000..5caa9d1 --- /dev/null +++ b/macos/Flutter/Flutter-Release.xcconfig @@ -0,0 +1,2 @@ +#include? "Pods/Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig" +#include "ephemeral/Flutter-Generated.xcconfig" diff --git a/macos/Flutter/GeneratedPluginRegistrant.swift b/macos/Flutter/GeneratedPluginRegistrant.swift new file mode 100644 index 0000000..b14dab6 --- /dev/null +++ b/macos/Flutter/GeneratedPluginRegistrant.swift @@ -0,0 +1,24 @@ +// +// Generated file. Do not edit. +// + +import FlutterMacOS +import Foundation + +import device_info_plus +import emoji_picker_flutter +import flutter_secure_storage_macos +import mobile_scanner +import path_provider_foundation +import shared_preferences_foundation +import sqflite_sqlcipher + +func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) { + DeviceInfoPlusMacosPlugin.register(with: registry.registrar(forPlugin: "DeviceInfoPlusMacosPlugin")) + EmojiPickerFlutterPlugin.register(with: registry.registrar(forPlugin: "EmojiPickerFlutterPlugin")) + FlutterSecureStoragePlugin.register(with: registry.registrar(forPlugin: "FlutterSecureStoragePlugin")) + MobileScannerPlugin.register(with: registry.registrar(forPlugin: "MobileScannerPlugin")) + PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin")) + SharedPreferencesPlugin.register(with: registry.registrar(forPlugin: "SharedPreferencesPlugin")) + SqfliteSqlCipherPlugin.register(with: registry.registrar(forPlugin: "SqfliteSqlCipherPlugin")) +} diff --git a/macos/Podfile b/macos/Podfile new file mode 100644 index 0000000..c795730 --- /dev/null +++ b/macos/Podfile @@ -0,0 +1,43 @@ +platform :osx, '10.14' + +# CocoaPods analytics sends network stats synchronously affecting flutter build latency. +ENV['COCOAPODS_DISABLE_STATS'] = 'true' + +project 'Runner', { + 'Debug' => :debug, + 'Profile' => :release, + 'Release' => :release, +} + +def flutter_root + generated_xcode_build_settings_path = File.expand_path(File.join('..', 'Flutter', 'ephemeral', 'Flutter-Generated.xcconfig'), __FILE__) + unless File.exist?(generated_xcode_build_settings_path) + raise "#{generated_xcode_build_settings_path} must exist. If you're running pod install manually, make sure \"flutter pub get\" is executed first" + end + + File.foreach(generated_xcode_build_settings_path) do |line| + matches = line.match(/FLUTTER_ROOT\=(.*)/) + return matches[1].strip if matches + end + raise "FLUTTER_ROOT not found in #{generated_xcode_build_settings_path}. Try deleting Flutter-Generated.xcconfig, then run \"flutter pub get\"" +end + +require File.expand_path(File.join('packages', 'flutter_tools', 'bin', 'podhelper'), flutter_root) + +flutter_macos_podfile_setup + +target 'Runner' do + use_frameworks! + use_modular_headers! + + flutter_install_all_macos_pods File.dirname(File.realpath(__FILE__)) + target 'RunnerTests' do + inherit! :search_paths + end +end + +post_install do |installer| + installer.pods_project.targets.each do |target| + flutter_additional_macos_build_settings(target) + end +end diff --git a/macos/Podfile.lock b/macos/Podfile.lock new file mode 100644 index 0000000..900f253 --- /dev/null +++ b/macos/Podfile.lock @@ -0,0 +1,54 @@ +PODS: + - device_info_plus (0.0.1): + - FlutterMacOS + - emoji_picker_flutter (0.0.1): + - FlutterMacOS + - flutter_secure_storage_macos (6.1.1): + - FlutterMacOS + - FlutterMacOS (1.0.0) + - mobile_scanner (6.0.2): + - FlutterMacOS + - path_provider_foundation (0.0.1): + - Flutter + - FlutterMacOS + - shared_preferences_foundation (0.0.1): + - Flutter + - FlutterMacOS + +DEPENDENCIES: + - device_info_plus (from `Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos`) + - emoji_picker_flutter (from `Flutter/ephemeral/.symlinks/plugins/emoji_picker_flutter/macos`) + - flutter_secure_storage_macos (from `Flutter/ephemeral/.symlinks/plugins/flutter_secure_storage_macos/macos`) + - FlutterMacOS (from `Flutter/ephemeral`) + - mobile_scanner (from `Flutter/ephemeral/.symlinks/plugins/mobile_scanner/macos`) + - path_provider_foundation (from `Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin`) + - shared_preferences_foundation (from `Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin`) + +EXTERNAL SOURCES: + device_info_plus: + :path: Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos + emoji_picker_flutter: + :path: Flutter/ephemeral/.symlinks/plugins/emoji_picker_flutter/macos + flutter_secure_storage_macos: + :path: Flutter/ephemeral/.symlinks/plugins/flutter_secure_storage_macos/macos + FlutterMacOS: + :path: Flutter/ephemeral + mobile_scanner: + :path: Flutter/ephemeral/.symlinks/plugins/mobile_scanner/macos + path_provider_foundation: + :path: Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin + shared_preferences_foundation: + :path: Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin + +SPEC CHECKSUMS: + device_info_plus: 1b14eed9bf95428983aed283a8d51cce3d8c4215 + emoji_picker_flutter: 533634326b1c5de9a181ba14b9758e6dfe967a20 + flutter_secure_storage_macos: 59459653abe1adb92abbc8ea747d79f8d19866c9 + FlutterMacOS: 8f6f14fa908a6fb3fba0cd85dbd81ec4b251fb24 + mobile_scanner: 07710d6b9b2c220ae899de2d7ecf5d77ffa56333 + path_provider_foundation: 2b6b4c569c0fb62ec74538f866245ac84301af46 + shared_preferences_foundation: fcdcbc04712aee1108ac7fda236f363274528f78 + +PODFILE CHECKSUM: 236401fc2c932af29a9fcf0e97baeeb2d750d367 + +COCOAPODS: 1.16.2 diff --git a/macos/Runner.xcodeproj/project.pbxproj b/macos/Runner.xcodeproj/project.pbxproj new file mode 100644 index 0000000..a155d51 --- /dev/null +++ b/macos/Runner.xcodeproj/project.pbxproj @@ -0,0 +1,801 @@ +// !$*UTF8*$! +{ + archiveVersion = 1; + classes = { + }; + objectVersion = 54; + objects = { + +/* Begin PBXAggregateTarget section */ + 33CC111A2044C6BA0003C045 /* Flutter Assemble */ = { + isa = PBXAggregateTarget; + buildConfigurationList = 33CC111B2044C6BA0003C045 /* Build configuration list for PBXAggregateTarget "Flutter Assemble" */; + buildPhases = ( + 33CC111E2044C6BF0003C045 /* ShellScript */, + ); + dependencies = ( + ); + name = "Flutter Assemble"; + productName = FLX; + }; +/* End PBXAggregateTarget section */ + +/* Begin PBXBuildFile section */ + 331C80D8294CF71000263BE5 /* RunnerTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 331C80D7294CF71000263BE5 /* RunnerTests.swift */; }; + 335BBD1B22A9A15E00E9071D /* GeneratedPluginRegistrant.swift in Sources */ = {isa = PBXBuildFile; fileRef = 335BBD1A22A9A15E00E9071D /* GeneratedPluginRegistrant.swift */; }; + 33CC10F12044A3C60003C045 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 33CC10F02044A3C60003C045 /* AppDelegate.swift */; }; + 33CC10F32044A3C60003C045 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 33CC10F22044A3C60003C045 /* Assets.xcassets */; }; + 33CC10F62044A3C60003C045 /* MainMenu.xib in Resources */ = {isa = PBXBuildFile; fileRef = 33CC10F42044A3C60003C045 /* MainMenu.xib */; }; + 33CC11132044BFA00003C045 /* MainFlutterWindow.swift in Sources */ = {isa = PBXBuildFile; fileRef = 33CC11122044BFA00003C045 /* MainFlutterWindow.swift */; }; + 93026427A9DF7AAA6CC7B97C /* Pods_Runner.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 4265710EECAA2F97B8113D01 /* Pods_Runner.framework */; }; + AB296B701251E3CE239B5DC3 /* Pods_RunnerTests.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 48B1995FEE403CAECAA47C00 /* Pods_RunnerTests.framework */; }; +/* End PBXBuildFile section */ + +/* Begin PBXContainerItemProxy section */ + 331C80D9294CF71000263BE5 /* PBXContainerItemProxy */ = { + isa = PBXContainerItemProxy; + containerPortal = 33CC10E52044A3C60003C045 /* Project object */; + proxyType = 1; + remoteGlobalIDString = 33CC10EC2044A3C60003C045; + remoteInfo = Runner; + }; + 33CC111F2044C79F0003C045 /* PBXContainerItemProxy */ = { + isa = PBXContainerItemProxy; + containerPortal = 33CC10E52044A3C60003C045 /* Project object */; + proxyType = 1; + remoteGlobalIDString = 33CC111A2044C6BA0003C045; + remoteInfo = FLX; + }; +/* End PBXContainerItemProxy section */ + +/* Begin PBXCopyFilesBuildPhase section */ + 33CC110E2044A8840003C045 /* Bundle Framework */ = { + isa = PBXCopyFilesBuildPhase; + buildActionMask = 2147483647; + dstPath = ""; + dstSubfolderSpec = 10; + files = ( + ); + name = "Bundle Framework"; + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXCopyFilesBuildPhase section */ + +/* Begin PBXFileReference section */ + 1789A69B9BC449AC934B2739 /* Pods-RunnerTests.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-RunnerTests.debug.xcconfig"; path = "Target Support Files/Pods-RunnerTests/Pods-RunnerTests.debug.xcconfig"; sourceTree = ""; }; + 17E8104198C1A0DDA47869A1 /* Pods-RunnerTests.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-RunnerTests.profile.xcconfig"; path = "Target Support Files/Pods-RunnerTests/Pods-RunnerTests.profile.xcconfig"; sourceTree = ""; }; + 29C6541DF6E6A63F5A5D3C23 /* Pods-RunnerTests.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-RunnerTests.release.xcconfig"; path = "Target Support Files/Pods-RunnerTests/Pods-RunnerTests.release.xcconfig"; sourceTree = ""; }; + 331C80D5294CF71000263BE5 /* RunnerTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = RunnerTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; + 331C80D7294CF71000263BE5 /* RunnerTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RunnerTests.swift; sourceTree = ""; }; + 333000ED22D3DE5D00554162 /* Warnings.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = Warnings.xcconfig; sourceTree = ""; }; + 335BBD1A22A9A15E00E9071D /* GeneratedPluginRegistrant.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = GeneratedPluginRegistrant.swift; sourceTree = ""; }; + 33CC10ED2044A3C60003C045 /* connect.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = connect.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 33CC10F02044A3C60003C045 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; + 33CC10F22044A3C60003C045 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; name = Assets.xcassets; path = Runner/Assets.xcassets; sourceTree = ""; }; + 33CC10F52044A3C60003C045 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/MainMenu.xib; sourceTree = ""; }; + 33CC10F72044A3C60003C045 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = Info.plist; path = Runner/Info.plist; sourceTree = ""; }; + 33CC11122044BFA00003C045 /* MainFlutterWindow.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MainFlutterWindow.swift; sourceTree = ""; }; + 33CEB47222A05771004F2AC0 /* Flutter-Debug.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = "Flutter-Debug.xcconfig"; sourceTree = ""; }; + 33CEB47422A05771004F2AC0 /* Flutter-Release.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = "Flutter-Release.xcconfig"; sourceTree = ""; }; + 33CEB47722A0578A004F2AC0 /* Flutter-Generated.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; name = "Flutter-Generated.xcconfig"; path = "ephemeral/Flutter-Generated.xcconfig"; sourceTree = ""; }; + 33E51913231747F40026EE4D /* DebugProfile.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = DebugProfile.entitlements; sourceTree = ""; }; + 33E51914231749380026EE4D /* Release.entitlements */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.entitlements; path = Release.entitlements; sourceTree = ""; }; + 33E5194F232828860026EE4D /* AppInfo.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = AppInfo.xcconfig; sourceTree = ""; }; + 4265710EECAA2F97B8113D01 /* Pods_Runner.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_Runner.framework; sourceTree = BUILT_PRODUCTS_DIR; }; + 48B1995FEE403CAECAA47C00 /* Pods_RunnerTests.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_RunnerTests.framework; sourceTree = BUILT_PRODUCTS_DIR; }; + 71E524D25EA1025FA1CAFBF3 /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = ""; }; + 7A86767FBB6E91E4EB0A83B5 /* Pods-Runner.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.profile.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.profile.xcconfig"; sourceTree = ""; }; + 7AFA3C8E1D35360C0083082E /* Release.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = Release.xcconfig; sourceTree = ""; }; + 8999E7436DEE4145BFBCCA69 /* Pods-Runner.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.release.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig"; sourceTree = ""; }; + 9740EEB21CF90195004384FC /* Debug.xcconfig */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xcconfig; path = Debug.xcconfig; sourceTree = ""; }; +/* End PBXFileReference section */ + +/* Begin PBXFrameworksBuildPhase section */ + 331C80D2294CF70F00263BE5 /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + AB296B701251E3CE239B5DC3 /* Pods_RunnerTests.framework in Frameworks */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + 33CC10EA2044A3C60003C045 /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + 93026427A9DF7AAA6CC7B97C /* Pods_Runner.framework in Frameworks */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXFrameworksBuildPhase section */ + +/* Begin PBXGroup section */ + 331C80D6294CF71000263BE5 /* RunnerTests */ = { + isa = PBXGroup; + children = ( + 331C80D7294CF71000263BE5 /* RunnerTests.swift */, + ); + path = RunnerTests; + sourceTree = ""; + }; + 33BA886A226E78AF003329D5 /* Configs */ = { + isa = PBXGroup; + children = ( + 33E5194F232828860026EE4D /* AppInfo.xcconfig */, + 9740EEB21CF90195004384FC /* Debug.xcconfig */, + 7AFA3C8E1D35360C0083082E /* Release.xcconfig */, + 333000ED22D3DE5D00554162 /* Warnings.xcconfig */, + ); + path = Configs; + sourceTree = ""; + }; + 33CC10E42044A3C60003C045 = { + isa = PBXGroup; + children = ( + 33FAB671232836740065AC1E /* Runner */, + 33CEB47122A05771004F2AC0 /* Flutter */, + 331C80D6294CF71000263BE5 /* RunnerTests */, + 33CC10EE2044A3C60003C045 /* Products */, + D73912EC22F37F3D000D13A0 /* Frameworks */, + A3E483E6288DAA9A6CD24475 /* Pods */, + ); + sourceTree = ""; + }; + 33CC10EE2044A3C60003C045 /* Products */ = { + isa = PBXGroup; + children = ( + 33CC10ED2044A3C60003C045 /* connect.app */, + 331C80D5294CF71000263BE5 /* RunnerTests.xctest */, + ); + name = Products; + sourceTree = ""; + }; + 33CC11242044D66E0003C045 /* Resources */ = { + isa = PBXGroup; + children = ( + 33CC10F22044A3C60003C045 /* Assets.xcassets */, + 33CC10F42044A3C60003C045 /* MainMenu.xib */, + 33CC10F72044A3C60003C045 /* Info.plist */, + ); + name = Resources; + path = ..; + sourceTree = ""; + }; + 33CEB47122A05771004F2AC0 /* Flutter */ = { + isa = PBXGroup; + children = ( + 335BBD1A22A9A15E00E9071D /* GeneratedPluginRegistrant.swift */, + 33CEB47222A05771004F2AC0 /* Flutter-Debug.xcconfig */, + 33CEB47422A05771004F2AC0 /* Flutter-Release.xcconfig */, + 33CEB47722A0578A004F2AC0 /* Flutter-Generated.xcconfig */, + ); + path = Flutter; + sourceTree = ""; + }; + 33FAB671232836740065AC1E /* Runner */ = { + isa = PBXGroup; + children = ( + 33CC10F02044A3C60003C045 /* AppDelegate.swift */, + 33CC11122044BFA00003C045 /* MainFlutterWindow.swift */, + 33E51913231747F40026EE4D /* DebugProfile.entitlements */, + 33E51914231749380026EE4D /* Release.entitlements */, + 33CC11242044D66E0003C045 /* Resources */, + 33BA886A226E78AF003329D5 /* Configs */, + ); + path = Runner; + sourceTree = ""; + }; + A3E483E6288DAA9A6CD24475 /* Pods */ = { + isa = PBXGroup; + children = ( + 71E524D25EA1025FA1CAFBF3 /* Pods-Runner.debug.xcconfig */, + 8999E7436DEE4145BFBCCA69 /* Pods-Runner.release.xcconfig */, + 7A86767FBB6E91E4EB0A83B5 /* Pods-Runner.profile.xcconfig */, + 1789A69B9BC449AC934B2739 /* Pods-RunnerTests.debug.xcconfig */, + 29C6541DF6E6A63F5A5D3C23 /* Pods-RunnerTests.release.xcconfig */, + 17E8104198C1A0DDA47869A1 /* Pods-RunnerTests.profile.xcconfig */, + ); + name = Pods; + path = Pods; + sourceTree = ""; + }; + D73912EC22F37F3D000D13A0 /* Frameworks */ = { + isa = PBXGroup; + children = ( + 4265710EECAA2F97B8113D01 /* Pods_Runner.framework */, + 48B1995FEE403CAECAA47C00 /* Pods_RunnerTests.framework */, + ); + name = Frameworks; + sourceTree = ""; + }; +/* End PBXGroup section */ + +/* Begin PBXNativeTarget section */ + 331C80D4294CF70F00263BE5 /* RunnerTests */ = { + isa = PBXNativeTarget; + buildConfigurationList = 331C80DE294CF71000263BE5 /* Build configuration list for PBXNativeTarget "RunnerTests" */; + buildPhases = ( + BF4817297D117DAC2F609608 /* [CP] Check Pods Manifest.lock */, + 331C80D1294CF70F00263BE5 /* Sources */, + 331C80D2294CF70F00263BE5 /* Frameworks */, + 331C80D3294CF70F00263BE5 /* Resources */, + ); + buildRules = ( + ); + dependencies = ( + 331C80DA294CF71000263BE5 /* PBXTargetDependency */, + ); + name = RunnerTests; + productName = RunnerTests; + productReference = 331C80D5294CF71000263BE5 /* RunnerTests.xctest */; + productType = "com.apple.product-type.bundle.unit-test"; + }; + 33CC10EC2044A3C60003C045 /* Runner */ = { + isa = PBXNativeTarget; + buildConfigurationList = 33CC10FB2044A3C60003C045 /* Build configuration list for PBXNativeTarget "Runner" */; + buildPhases = ( + 370419EFA4226E12C806FAA3 /* [CP] Check Pods Manifest.lock */, + 33CC10E92044A3C60003C045 /* Sources */, + 33CC10EA2044A3C60003C045 /* Frameworks */, + 33CC10EB2044A3C60003C045 /* Resources */, + 33CC110E2044A8840003C045 /* Bundle Framework */, + 3399D490228B24CF009A79C7 /* ShellScript */, + 9F6EC26B34D9BD2E254C77E4 /* [CP] Embed Pods Frameworks */, + ); + buildRules = ( + ); + dependencies = ( + 33CC11202044C79F0003C045 /* PBXTargetDependency */, + ); + name = Runner; + productName = Runner; + productReference = 33CC10ED2044A3C60003C045 /* connect.app */; + productType = "com.apple.product-type.application"; + }; +/* End PBXNativeTarget section */ + +/* Begin PBXProject section */ + 33CC10E52044A3C60003C045 /* Project object */ = { + isa = PBXProject; + attributes = { + BuildIndependentTargetsInParallel = YES; + LastSwiftUpdateCheck = 0920; + LastUpgradeCheck = 1510; + ORGANIZATIONNAME = ""; + TargetAttributes = { + 331C80D4294CF70F00263BE5 = { + CreatedOnToolsVersion = 14.0; + TestTargetID = 33CC10EC2044A3C60003C045; + }; + 33CC10EC2044A3C60003C045 = { + CreatedOnToolsVersion = 9.2; + LastSwiftMigration = 1100; + ProvisioningStyle = Automatic; + SystemCapabilities = { + com.apple.Sandbox = { + enabled = 1; + }; + }; + }; + 33CC111A2044C6BA0003C045 = { + CreatedOnToolsVersion = 9.2; + ProvisioningStyle = Manual; + }; + }; + }; + buildConfigurationList = 33CC10E82044A3C60003C045 /* Build configuration list for PBXProject "Runner" */; + compatibilityVersion = "Xcode 9.3"; + developmentRegion = en; + hasScannedForEncodings = 0; + knownRegions = ( + en, + Base, + ); + mainGroup = 33CC10E42044A3C60003C045; + productRefGroup = 33CC10EE2044A3C60003C045 /* Products */; + projectDirPath = ""; + projectRoot = ""; + targets = ( + 33CC10EC2044A3C60003C045 /* Runner */, + 331C80D4294CF70F00263BE5 /* RunnerTests */, + 33CC111A2044C6BA0003C045 /* Flutter Assemble */, + ); + }; +/* End PBXProject section */ + +/* Begin PBXResourcesBuildPhase section */ + 331C80D3294CF70F00263BE5 /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; + 33CC10EB2044A3C60003C045 /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 33CC10F32044A3C60003C045 /* Assets.xcassets in Resources */, + 33CC10F62044A3C60003C045 /* MainMenu.xib in Resources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXResourcesBuildPhase section */ + +/* Begin PBXShellScriptBuildPhase section */ + 3399D490228B24CF009A79C7 /* ShellScript */ = { + isa = PBXShellScriptBuildPhase; + alwaysOutOfDate = 1; + buildActionMask = 2147483647; + files = ( + ); + inputFileListPaths = ( + ); + inputPaths = ( + ); + outputFileListPaths = ( + ); + outputPaths = ( + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "echo \"$PRODUCT_NAME.app\" > \"$PROJECT_DIR\"/Flutter/ephemeral/.app_filename && \"$FLUTTER_ROOT\"/packages/flutter_tools/bin/macos_assemble.sh embed\n"; + }; + 33CC111E2044C6BF0003C045 /* ShellScript */ = { + isa = PBXShellScriptBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + inputFileListPaths = ( + Flutter/ephemeral/FlutterInputs.xcfilelist, + ); + inputPaths = ( + Flutter/ephemeral/tripwire, + ); + outputFileListPaths = ( + Flutter/ephemeral/FlutterOutputs.xcfilelist, + ); + outputPaths = ( + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "\"$FLUTTER_ROOT\"/packages/flutter_tools/bin/macos_assemble.sh && touch Flutter/ephemeral/tripwire"; + }; + 370419EFA4226E12C806FAA3 /* [CP] Check Pods Manifest.lock */ = { + isa = PBXShellScriptBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + inputFileListPaths = ( + ); + inputPaths = ( + "${PODS_PODFILE_DIR_PATH}/Podfile.lock", + "${PODS_ROOT}/Manifest.lock", + ); + name = "[CP] Check Pods Manifest.lock"; + outputFileListPaths = ( + ); + outputPaths = ( + "$(DERIVED_FILE_DIR)/Pods-Runner-checkManifestLockResult.txt", + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n"; + showEnvVarsInLog = 0; + }; + 9F6EC26B34D9BD2E254C77E4 /* [CP] Embed Pods Frameworks */ = { + isa = PBXShellScriptBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + inputFileListPaths = ( + "${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks-${CONFIGURATION}-input-files.xcfilelist", + ); + name = "[CP] Embed Pods Frameworks"; + outputFileListPaths = ( + "${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks-${CONFIGURATION}-output-files.xcfilelist", + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks.sh\"\n"; + showEnvVarsInLog = 0; + }; + BF4817297D117DAC2F609608 /* [CP] Check Pods Manifest.lock */ = { + isa = PBXShellScriptBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + inputFileListPaths = ( + ); + inputPaths = ( + "${PODS_PODFILE_DIR_PATH}/Podfile.lock", + "${PODS_ROOT}/Manifest.lock", + ); + name = "[CP] Check Pods Manifest.lock"; + outputFileListPaths = ( + ); + outputPaths = ( + "$(DERIVED_FILE_DIR)/Pods-RunnerTests-checkManifestLockResult.txt", + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n"; + showEnvVarsInLog = 0; + }; +/* End PBXShellScriptBuildPhase section */ + +/* Begin PBXSourcesBuildPhase section */ + 331C80D1294CF70F00263BE5 /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 331C80D8294CF71000263BE5 /* RunnerTests.swift in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + 33CC10E92044A3C60003C045 /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 33CC11132044BFA00003C045 /* MainFlutterWindow.swift in Sources */, + 33CC10F12044A3C60003C045 /* AppDelegate.swift in Sources */, + 335BBD1B22A9A15E00E9071D /* GeneratedPluginRegistrant.swift in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXSourcesBuildPhase section */ + +/* Begin PBXTargetDependency section */ + 331C80DA294CF71000263BE5 /* PBXTargetDependency */ = { + isa = PBXTargetDependency; + target = 33CC10EC2044A3C60003C045 /* Runner */; + targetProxy = 331C80D9294CF71000263BE5 /* PBXContainerItemProxy */; + }; + 33CC11202044C79F0003C045 /* PBXTargetDependency */ = { + isa = PBXTargetDependency; + target = 33CC111A2044C6BA0003C045 /* Flutter Assemble */; + targetProxy = 33CC111F2044C79F0003C045 /* PBXContainerItemProxy */; + }; +/* End PBXTargetDependency section */ + +/* Begin PBXVariantGroup section */ + 33CC10F42044A3C60003C045 /* MainMenu.xib */ = { + isa = PBXVariantGroup; + children = ( + 33CC10F52044A3C60003C045 /* Base */, + ); + name = MainMenu.xib; + path = Runner; + sourceTree = ""; + }; +/* End PBXVariantGroup section */ + +/* Begin XCBuildConfiguration section */ + 331C80DB294CF71000263BE5 /* Debug */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 1789A69B9BC449AC934B2739 /* Pods-RunnerTests.debug.xcconfig */; + buildSettings = { + BUNDLE_LOADER = "$(TEST_HOST)"; + CURRENT_PROJECT_VERSION = 1; + GENERATE_INFOPLIST_FILE = YES; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect.RunnerTests; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_VERSION = 5.0; + TEST_HOST = "$(BUILT_PRODUCTS_DIR)/connect.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/connect"; + }; + name = Debug; + }; + 331C80DC294CF71000263BE5 /* Release */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 29C6541DF6E6A63F5A5D3C23 /* Pods-RunnerTests.release.xcconfig */; + buildSettings = { + BUNDLE_LOADER = "$(TEST_HOST)"; + CURRENT_PROJECT_VERSION = 1; + GENERATE_INFOPLIST_FILE = YES; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect.RunnerTests; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_VERSION = 5.0; + TEST_HOST = "$(BUILT_PRODUCTS_DIR)/connect.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/connect"; + }; + name = Release; + }; + 331C80DD294CF71000263BE5 /* Profile */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 17E8104198C1A0DDA47869A1 /* Pods-RunnerTests.profile.xcconfig */; + buildSettings = { + BUNDLE_LOADER = "$(TEST_HOST)"; + CURRENT_PROJECT_VERSION = 1; + GENERATE_INFOPLIST_FILE = YES; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = com.example.connect.RunnerTests; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_VERSION = 5.0; + TEST_HOST = "$(BUILT_PRODUCTS_DIR)/connect.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/connect"; + }; + name = Profile; + }; + 338D0CE9231458BD00FA5F75 /* Profile */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 7AFA3C8E1D35360C0083082E /* Release.xcconfig */; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES; + CLANG_ANALYZER_NONNULL = YES; + CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CODE_SIGN_IDENTITY = "-"; + COPY_PHASE_STRIP = NO; + DEAD_CODE_STRIPPING = YES; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + ENABLE_NS_ASSERTIONS = NO; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_USER_SCRIPT_SANDBOXING = NO; + GCC_C_LANGUAGE_STANDARD = gnu11; + GCC_NO_COMMON_BLOCKS = YES; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + MACOSX_DEPLOYMENT_TARGET = 10.14; + MTL_ENABLE_DEBUG_INFO = NO; + SDKROOT = macosx; + SWIFT_COMPILATION_MODE = wholemodule; + SWIFT_OPTIMIZATION_LEVEL = "-O"; + }; + name = Profile; + }; + 338D0CEA231458BD00FA5F75 /* Profile */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 33E5194F232828860026EE4D /* AppInfo.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ENABLE_MODULES = YES; + CODE_SIGN_ENTITLEMENTS = Runner/DebugProfile.entitlements; + CODE_SIGN_STYLE = Automatic; + COMBINE_HIDPI_IMAGES = YES; + INFOPLIST_FILE = Runner/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/../Frameworks", + ); + PROVISIONING_PROFILE_SPECIFIER = ""; + SWIFT_VERSION = 5.0; + }; + name = Profile; + }; + 338D0CEB231458BD00FA5F75 /* Profile */ = { + isa = XCBuildConfiguration; + buildSettings = { + CODE_SIGN_STYLE = Manual; + PRODUCT_NAME = "$(TARGET_NAME)"; + }; + name = Profile; + }; + 33CC10F92044A3C60003C045 /* Debug */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 9740EEB21CF90195004384FC /* Debug.xcconfig */; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES; + CLANG_ANALYZER_NONNULL = YES; + CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CODE_SIGN_IDENTITY = "-"; + COPY_PHASE_STRIP = NO; + DEAD_CODE_STRIPPING = YES; + DEBUG_INFORMATION_FORMAT = dwarf; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_TESTABILITY = YES; + ENABLE_USER_SCRIPT_SANDBOXING = NO; + GCC_C_LANGUAGE_STANDARD = gnu11; + GCC_DYNAMIC_NO_PIC = NO; + GCC_NO_COMMON_BLOCKS = YES; + GCC_OPTIMIZATION_LEVEL = 0; + GCC_PREPROCESSOR_DEFINITIONS = ( + "DEBUG=1", + "$(inherited)", + ); + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + MACOSX_DEPLOYMENT_TARGET = 10.14; + MTL_ENABLE_DEBUG_INFO = YES; + ONLY_ACTIVE_ARCH = YES; + SDKROOT = macosx; + SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; + SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + }; + name = Debug; + }; + 33CC10FA2044A3C60003C045 /* Release */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 7AFA3C8E1D35360C0083082E /* Release.xcconfig */; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES; + CLANG_ANALYZER_NONNULL = YES; + CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CODE_SIGN_IDENTITY = "-"; + COPY_PHASE_STRIP = NO; + DEAD_CODE_STRIPPING = YES; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + ENABLE_NS_ASSERTIONS = NO; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_USER_SCRIPT_SANDBOXING = NO; + GCC_C_LANGUAGE_STANDARD = gnu11; + GCC_NO_COMMON_BLOCKS = YES; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + MACOSX_DEPLOYMENT_TARGET = 10.14; + MTL_ENABLE_DEBUG_INFO = NO; + SDKROOT = macosx; + SWIFT_COMPILATION_MODE = wholemodule; + SWIFT_OPTIMIZATION_LEVEL = "-O"; + }; + name = Release; + }; + 33CC10FC2044A3C60003C045 /* Debug */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 33E5194F232828860026EE4D /* AppInfo.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ENABLE_MODULES = YES; + CODE_SIGN_ENTITLEMENTS = Runner/DebugProfile.entitlements; + CODE_SIGN_STYLE = Automatic; + COMBINE_HIDPI_IMAGES = YES; + INFOPLIST_FILE = Runner/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/../Frameworks", + ); + PROVISIONING_PROFILE_SPECIFIER = ""; + SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + SWIFT_VERSION = 5.0; + }; + name = Debug; + }; + 33CC10FD2044A3C60003C045 /* Release */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 33E5194F232828860026EE4D /* AppInfo.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ENABLE_MODULES = YES; + CODE_SIGN_ENTITLEMENTS = Runner/Release.entitlements; + CODE_SIGN_STYLE = Automatic; + COMBINE_HIDPI_IMAGES = YES; + INFOPLIST_FILE = Runner/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/../Frameworks", + ); + PROVISIONING_PROFILE_SPECIFIER = ""; + SWIFT_VERSION = 5.0; + }; + name = Release; + }; + 33CC111C2044C6BA0003C045 /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + CODE_SIGN_STYLE = Manual; + PRODUCT_NAME = "$(TARGET_NAME)"; + }; + name = Debug; + }; + 33CC111D2044C6BA0003C045 /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + CODE_SIGN_STYLE = Automatic; + PRODUCT_NAME = "$(TARGET_NAME)"; + }; + name = Release; + }; +/* End XCBuildConfiguration section */ + +/* Begin XCConfigurationList section */ + 331C80DE294CF71000263BE5 /* Build configuration list for PBXNativeTarget "RunnerTests" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 331C80DB294CF71000263BE5 /* Debug */, + 331C80DC294CF71000263BE5 /* Release */, + 331C80DD294CF71000263BE5 /* Profile */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + 33CC10E82044A3C60003C045 /* Build configuration list for PBXProject "Runner" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 33CC10F92044A3C60003C045 /* Debug */, + 33CC10FA2044A3C60003C045 /* Release */, + 338D0CE9231458BD00FA5F75 /* Profile */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + 33CC10FB2044A3C60003C045 /* Build configuration list for PBXNativeTarget "Runner" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 33CC10FC2044A3C60003C045 /* Debug */, + 33CC10FD2044A3C60003C045 /* Release */, + 338D0CEA231458BD00FA5F75 /* Profile */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + 33CC111B2044C6BA0003C045 /* Build configuration list for PBXAggregateTarget "Flutter Assemble" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 33CC111C2044C6BA0003C045 /* Debug */, + 33CC111D2044C6BA0003C045 /* Release */, + 338D0CEB231458BD00FA5F75 /* Profile */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; +/* End XCConfigurationList section */ + }; + rootObject = 33CC10E52044A3C60003C045 /* Project object */; +} diff --git a/macos/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist b/macos/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist new file mode 100644 index 0000000..18d9810 --- /dev/null +++ b/macos/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist @@ -0,0 +1,8 @@ + + + + + IDEDidComputeMac32BitWarning + + + diff --git a/macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme b/macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme new file mode 100644 index 0000000..731b1fb --- /dev/null +++ b/macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme @@ -0,0 +1,98 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/macos/Runner.xcworkspace/contents.xcworkspacedata b/macos/Runner.xcworkspace/contents.xcworkspacedata new file mode 100644 index 0000000..21a3cc1 --- /dev/null +++ b/macos/Runner.xcworkspace/contents.xcworkspacedata @@ -0,0 +1,10 @@ + + + + + + + diff --git a/macos/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist b/macos/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist new file mode 100644 index 0000000..18d9810 --- /dev/null +++ b/macos/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist @@ -0,0 +1,8 @@ + + + + + IDEDidComputeMac32BitWarning + + + diff --git a/macos/Runner/AppDelegate.swift b/macos/Runner/AppDelegate.swift new file mode 100644 index 0000000..8e02df2 --- /dev/null +++ b/macos/Runner/AppDelegate.swift @@ -0,0 +1,9 @@ +import Cocoa +import FlutterMacOS + +@main +class AppDelegate: FlutterAppDelegate { + override func applicationShouldTerminateAfterLastWindowClosed(_ sender: NSApplication) -> Bool { + return true + } +} diff --git a/macos/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json b/macos/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json new file mode 100644 index 0000000..a2ec33f --- /dev/null +++ b/macos/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json @@ -0,0 +1,68 @@ +{ + "images" : [ + { + "size" : "16x16", + "idiom" : "mac", + "filename" : "app_icon_16.png", + "scale" : "1x" + }, + { + "size" : "16x16", + "idiom" : "mac", + "filename" : "app_icon_32.png", + "scale" : "2x" + }, + { + "size" : "32x32", + "idiom" : "mac", + "filename" : "app_icon_32.png", + "scale" : "1x" + }, + { + "size" : "32x32", + "idiom" : "mac", + "filename" : "app_icon_64.png", + "scale" : "2x" + }, + { + "size" : "128x128", + "idiom" : "mac", + "filename" : "app_icon_128.png", + "scale" : "1x" + }, + { + "size" : "128x128", + "idiom" : "mac", + "filename" : "app_icon_256.png", + "scale" : "2x" + }, + { + "size" : "256x256", + "idiom" : "mac", + "filename" : "app_icon_256.png", + "scale" : "1x" + }, + { + "size" : "256x256", + "idiom" : "mac", + "filename" : "app_icon_512.png", + "scale" : "2x" + }, + { + "size" : "512x512", + "idiom" : "mac", + "filename" : "app_icon_512.png", + "scale" : "1x" + }, + { + "size" : "512x512", + "idiom" : "mac", + "filename" : "app_icon_1024.png", + "scale" : "2x" + } + ], + "info" : { + "version" : 1, + "author" : "xcode" + } +} diff --git a/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_1024.png b/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_1024.png new file mode 100644 index 0000000000000000000000000000000000000000..82b6f9d9a33e198f5747104729e1fcef999772a5 GIT binary patch literal 102994 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ⅅ8MglG&ER{i5lN315cO?EdHNLrg? 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 z zKpxF`G*X(YOz2^@7i#D+s-~A1E;3&x%%qL5hkiy^JhYjJ74{hvVmAx*6BH`M`!qGC zO9pjEsR)A-n1`6KLACSL%FS_Kcm+?4*z-V?WAZPs?RkzoijIr~I+oh1^~T`q^dCFvG$Gbd8AnTYBjLKYUmayaQz#S1le7Q^Hyr#;X&h*1wDpm+gZC!rSKom zq|+o&UGpeXtlQ1;?@JukKG!8PGS1Io0z6O}ZeL&DsON^I0K+>Mxv#ohK+;ByAZ`Eb z2orY{j0Pa3edA(#-pJA0AaJ6h& z81Gl(pd#j~mrizktoid14K5ig7u8FvZmLLP%l@dl05IprCyqDB?mA2fc*6UB+49lb zZ8`V9epdo=OeZoiY%zw-w`8DNwTORV_>>3T{r)1-YsGSo0E2s>tix9OBqKFBjg#}G z`pgkCblKMYs!Z)r^(qT_c+}gLhR|gnq!1~Qr|~kt&2@_yswx{i$KEn`8J1W8BGljl zr@GEG#W(s#AKKyuqLp+cl1C}7%`m#-!$15XF{M(M*-fD%+i#mFbP35jlgN3{8#A-dmj&OQtG)!031jTwGMal=&YtPfq2AUWekP9J-JT(p099!L`+yen$ zVH1?kRrhV7(mGKkm_jPP_U@Xd;x=ppk}4WY0Rbr> z0MJM_;$GGxL*P68y%KBqHntF{>X&<{aeI4m6+{TQ%~Zp}v%Pujr)zg5mV;cFKqeA- zQm5`#Sd{B6Rc*4PS-rO(vf>YEdXmOK?>K@`L5}|9q}#t_IE%g+U<-1qw3mr5&v;2A zCQ}BEn9_u;;>n5N#dP0RhCF-_UplC+U(i~Zjh>U5+b8%@p3HK(R*IMQwE!uritb}< zF)AK2?+0@-aE3LYkg`B*&N&m~JWB9>(Z>`aqRwgioU)0w{U1K4?>-#i|ZfhNa9hV)2)(%ch zJMH1twoeZWwkE@I!dz$ma+;9GeACv>Ncupl@+gBSeU_uzfj!$+h&@EACkZG_vwLGA z(?^;rcJu1$5H~xI@6lHIYC-$+b&hF1p`AoAOKqw{t0Fu#X`OGt$)7Q!nmJ=&)xjq@ zHoxT4pcYKSPT5(4yzIuQ^S*N2NJpR4v0?rB-^JuaXNLis?E(l>Jo8mUw(gsFLLOy? zEszHWGaCn|lw$LSwoj{G7Uq(zK0W^VVWu#ms8BMRlF2z%-g`fOXmndgC(na8fc)s` zz$GAoxP+l|+T_S4$r1sLwkV77ew1Gug*`|HiE*?FGLm1q; z^p0A0eqqbmk3?|!CB9DBN1Zof6d7+ zJSn!`VD~tVaqy<*Mw^8dM5v3Bvj2VdVFb=)U3L2eDM3@>n(P z?Rr_=I17+r4fE{>1LBQG0&o97nef67n-aNnVP<{dd6*B!Q344 zZbsAof&jw+;CLeK2d87t9s~YZ5?6Qwf&{NPEBN+)LbjOcZRXNcR&h)x`TtdpI+b!>$E~h0o1L*2OddpR9!Gw~-E^Cj(7i69S<66ak$)AYMv|xG+;uR(`;h zGIV3}?+Qxdjz)s;s}jHY{JPmeo@-tN$H@hxaV@)}K?y~ts~E6H(F|SlsN5oH8g7*h zGiC!8c1doE3U|D}Vul1yPmXuCk*hmyU4MG2ml#V0+(G5I+`L_=3cD$%$I=@*8m-LU-!fn&-sZO1%ls63+w}AiAK`Jv z>`q~ztr&&(gCkFpci+*1Ekdv*MhBCzGfPBj9dM|YEjZk(tWBuz4?MGeq+*)t>Q=z6UXF_w z{QDUT4^JQ8J%hW;d2xGB>Fl4Y-bRT!ttP2GE5jYoI1e(eVK0&V5W+>zludt=nf|UN zi1IV;MK$Fy%$yw<oGeW?JIGjmfGLH$Y;l|T0p1V!N*Jvu zHSAG0WpwPip0vm7%VRq8$2O2>P5b!WBfTz*6dZ4Wd6O9Y(8A;nOuG((y?F`ac_u2( z#~17CoTK)1G<~~Z4jXlout{e&nZbDHyHf(=a?OtaJ(2Q(!g#)Ugw-QQ?A?mN#yN%T zBtJ`sA6Lpg`k>Pi8a7GssiY$eG0Be8LCoQL{GDqi-;j0pLmT!Z)szldvbN7GVcu*S zzb1rEq|M)1qa7rM*I8!<#w7FnQ?{v^? z0`MlS3+`#ZB5$DT4+`7e-Hlp_2G0`*F@STbRJ|!tk3cC~1T%NR-p4s=sTT+RqsMjF zyrp-Jv?CD4Y3N&Zb1gr=%`MFR8;|r)uxQ6*X{OpEhQ~+tu}^n8Wijiy`pSMw0uKNi zSNX^Z1y;WirM0o_x%zft0U2GcLm_2BS`b{Z>g|9VOVr%QF*R?pTpiJsEbj4jLVAyd zTA;x15=f~b0^(e*Vo;Tn;WTJSxpI9LmL($Lxob<^S!k7mGhnnVNnAC*g!$ms0#Q|q zs=25I0<>fUw_&+KU`}5P9wlmjRWdMYh%Np6n?AAHQ;JzG?s(Z9UR`pNh79Nzk~DF+ zX~jy>>f-2bl?drlM8 z3NfIQnrT@pLmv+QA6efWPv!sqe;mh3_RcOj5>Ya;4hhN13dtx*_TJ-=kX_kZQDkPz zIw}#e_dK%au@1*L&iUP^cfH?zf1iK)tHv=t|>-9mMT!;;Vg|svSzWkN7q#t$c4N$Q;tl3EYwef_4q>GO<#I89VhY;`X*hz$n*GZ%f+;uViG z?uLlxD1OIeid}0r9%Ssoc7@vJjZIsZlU9zvYpjhYiOrzD5sq3OC zpf-X;Nb!DLpxqX^zDIK%=46-Z3%i-bac`RIBS5*wcw5Pu>G|kF>TQP$dGRYh#1hwD z{|cbbTOKL>Gb1-;X6?vWLC+KJ_^Ij?KzJ7eZ?^8XNgoYU9^z&>d zsIjX*uOK`#Wu!`>L@y!=XpQcW+mBaRjm|XrB@etLdr}Ob57e7EkE;7a*t7=M#XFL6 za;KHHk-rBNTjp-gS^;ehKNv>K>+_jPQ45J%4><1HyKJ?;T9#~k_23?xD}B&@Wp{%H z($hU+nWR?g!9dsJkgVz(J_Yrdns+m~9V_gQ7Sb`&F4wZZ!k}##j$>O{4{?avCbCZfyW zO$)m7LE=P?$CXHDU_RUD+sYwT;nKI7 zSs_XTv!BuxpJ!7(b~uYfsgzt~mj5(vf2r~`LHwpePs!o2A3zEr@#sxo8HEe8>V||d zBiz0@e&6}p*}!6jsm}I0bN9Mc2(c#jg@;Nu6!Kv&4&P8-UcQ-00WJIO%4OuUn;^jU z;I3r=T3KQtiMQ7&x32eVtB`mCe)9ws^7u%2P`B%Xc}=Qc&O^{FmS^{~Rho}^s`B+H z=1_T);9LRK?{$Vx22!5m)Er8aoPOA8&{7fyt`t@~Vw%gtx~+g3qs8LFR%(2Uny28A6dFYnNQgcUa>Sq=%alFh&8#@1o_qgwve* zVFimnUtL{4aHP6s?FB%bu2SP=e*VGqXC8iuZ-JOc{5%Lx0g|VvyWkdh&FD^Gkc!0N zhoolXvp6GC8wj?Y+V;r*EN+<1ac`-+!8Mqb@Nz)=OqV?4gxhR^t7*+^+AfxxVt(n{ z+fkk|-xSGqmkZa@Q%`;;r`-Z|? z0fR6b@l%pTwK*@xY+(MwBUwf^z+F*~piC64BWTrz}-HS1-XF-IA%?Zs_#F8 zcmUuEZ6Of>YIJOe$&{V;3vIBw7|jSGPeS6cvTMdj96Y~pI-z7InGW;(DhFqaiTTO9@KWvQi9__j0btLZ9 zAa~-Po%^sDFfme4@Yiq}r`BgnYK2eTwCjg9_zC4V{{&_GTm-!qHGVR6JXDjw;}GzF z6lXA{xo1+tQM{9vwb1&sRXPdGDHbEMbnwh}t+%tvcw5p4J4r#hEpDl=A{;Mjc%0)T zsG}v<$^HhdcE)5IJ^iBWK{7?Zn)vb%c!5eIj4 zbT}CGO*u)Od@^LuIC@_2{=AP2-O99NglFudj{!T}0e8wtTQcB@F9QW6$J!0Ye`T+U zXDx84b$!hD#4YzSyZLy~!IIZuFa3%eU zG4eg5?}sZ6Yj29P^-PcXG*8%VzLL$0!oL?c(!oQ+G!kORsa+lsf5YER>PX83R4LgF zgPNQJ#Bo#)MXU%J9k?RWD;c>|as5b5p>xAwau=X5XbERX`_ZHB8_XSNDe`s?n(e>) zGF$G%n6o+W{6A-@4hsIK0*J%jpB#Y*G^B48eQD(CDZR5oBl-P=)r7fH^PLf?!aK6V zwkIM35?l*I6p@;^H}JIDNs-fF*IFN?k?kj(M)QKM%%?dSkf1d$Nly2z(>)oq8z}0H zH?Qa{x&36#W@y04!9zx@x7un@ob$&)V8#f~0n1|jF0kFs4aZ{ND1~QjWHToIY5)LY zrgKDCj@dFCx&-w$QMi=CqD*=`$NqC~2k366pPXl#>Y7A=iQD}f`)+B-pS@LIW_M?9 zlBS_)(vGz!L$#P`?<3Hvonw@B1uJ244y)M?0)z0-hq++sJ0GZ+{oiiH;lFi&wy(C! z0Bv9z^M;`4@)USP)7dhg@K5K&U&|7&-@I0Sk>I+ZH75_xEn>qh9qmc%aA@NEKBsVBgUuK zC=b{w-0oU|)~tAVI zyJ3BAB}%rsjz7qZ?x_XCWe6!_u-{e_3u68Asso0IvwKdxq1lN#%4w>J zi>}P;$JZ>58(ZAjsmSJl6BWUTe`0eGEf3f_yS#H6vx;UJWO7CCK!{)4C}`C$j5gNj|k znb$4QRurEE3tPEe!JzG-a0DmvXePO zSD#Q-qOAjTMm|=aBSnvwHoEbgyVIz@J$hT*legak-hhb}e#%cm2$nR2 zV9A{kc)WT$np=5coPQIskbGMO@Fn2NxPv$@SJZdG6}jV;+%(cH+*RFQ(+DjsJlman zy`D(yN?8MCtjWD3w}Q|jQccb$}BDW%M$zZZnri2+5ls)@@(wQD`jt_GpTKL_^CO&SSCcHbfMX#JXYFI^*947 zPh&S-G=l*C@`E5CU1$m7ao(Q&oSmY7)ZZ#5_fEyYzLsFJwJ%GfErFeRN@7lUbUrL| z$6;gQSNsI91LJvT+$Zb0>g<4g8T{B!U05lfKmoSRH^pB^^8sJ3{8PzVq0NeypMF5k zU3qOqksdq{>AUjm3O~dZx^vS6C$ldgCWszl?xd8-sJ;-kPnISB*-f=L*8XggOx$?u zg%B-QovSjBbj}%sShZv~r?`*6PiiQW;nee<-=+y4}S#}q_BgXIJoSOf$YbE7vXt4;Np zrKzZf6Ny0aES8(-cqmnIGMg&ieYWryBZ0VTB=4<*@auP4NdIk&q(Mt(OLPm|Yl za!0OpC9sA#tk>OsaCSx0;!$5r6naw ztzLBo>#LKaxxsO=yWe%yGilL`A|6E#TK! z+1VRQlo*D?(k0-mlRM+`OMT8kVB*-%ZGv}Aj1u^j!wu*~>L<-T+u?6sX!3C}lQte- zk(6_=iwXsQ0JbRvJDwMnk!c99w~s~uD_4vMB=m~-ft-*|z~$*g4g;pgG~Ap1m@@Fx zWS)8IKSN6`^vVQ8hv^Oc+O(Rt7!U%wVsGP+Y6fyS%GG+v+dIdVfCXPzAV~~li+3m5 ztFQmbE)(#2#Oi@k$1#zUS6ijD_yYsa{+BHZAw+^zAEI3bc(h0qm?|pNf?oS}Km#OG zrOfCKn_-CVO;}DXu|5YE#d8I2o>}vUxYlv&>=+I28WY>a1;uI)HUM_IvpF;Ln4ROT zf!=1rpKihNFUo=R@sD-pT!EOm%%ncl43f;aem^;|A#s3`b6vjeAzO!M-gwc`-Kj~{ zBX)tq64*kJl#TrgW4o%hTY3x$P01nD6a6s2#MmwM$vyX5PU|YngU*wXGK*?f?#Eg$~^OWW3I@of-=XVuu-b%A1Z|nqY_2 z;~jD&=QnB#WGU>;RwFq(I< z34K1fCMwf9F}G%k(&?~2EY&)W*-_z0ReS$;7+I1)zz`)M zpAF{5ZHLPMJhYU z;GE*@hM1NM{G{L94dL$!Y-h6A9K9W=I6AYb`Y=v{(tpyLQz^^Aibea(q()R*TU|-m zozpyr!|-BZ_Dn+$*2|vq2Y@ghHo!-`WjVtU-bab(SJp2*2i-}$UP9^qnF_OIFS~-< zYj^VS!)Wu}vn6!LDIt!HJ1SU-@ce>z8f4cT4R9V@O^Xg9)4`VpjsXm*~@%l^Ux;Rf#Zck`BNXu0Y(!C zj%Z}UAmD00nsOS%Uull)dU(fZgJ$bo>3Oa`8h~Wt)EM?v(ndlTS1p0|E9Pg>=&>58 zghD~%R;YpqZAw;F;M(lx5b_wkVbnd+ER+6A-SYj^1XUgNGn0I~ES|f|5emjyPIW)S z0z8i6)BZt&h(qQxih4HbFYa6~jyeKbc_`QEdLD@9SBGButjw|b^l*oQjDk<7Nig08IK zb`ATVGzK%LP+>9aFM0hr8t+m`uNr?h&8o3Rp$T&ql||K}7GgobFhCViaDH~+F#yC- zt>7T3&_PZ*feTKTyd6vlF~JmEA1f+*>CCE4ex}5N^$4o)YuxX&3T$P0(IS!+kan^J z_p>v#1J8bWELml|S02YAQe-&yVew+kipZr~H-I@yc$=8#rZ-8L<_nDx&Qv3dJDwUX z!)@=h1`~R2M{$J8bM^1O&Gy2oxe1T;K?NA{iv_eYuhpLyc3%xu%z`dVc}Z}%cHGHQ<7P!Q|e?dwnSpL!AUf!B^!?#^Q#W!Ry+7ofwPZ1mZq z(Id0{htmX1W?2cAYWZo_lOtT#+Us-nlP$=CGK|Ri4x0Xh>(|iN9y1 z=9y26A4Y}ViRi9Fxzm{>J`YM>GX1D|$4BY9xJrY{oY2~Z&};B{Zq9Pp!pox`8e#0C z-h~@fohA74(#ws!{7kIe4v6XUX<)9bd)g66Bz%^Y4p0~OF+rY;l$v&7T<3~4y!bv> zR$r#LblZcVgy2lq!ff+>yuR4qCcljQa03x|dTcG7`CHcxh#POtGKt6ymNd_0qF7Wf zBj_KC8{jl!zZ>0neDp19n3sD?HC=|WM3!}cK4zCnu6Uoj*hbV1<#F2BD)@A~y%@VXx+u}Hcn=_s-({PxzmMZ^xJ1SV zoZMY*FarYvO_@z8Lr2ep)%HgIL7rhYa~#X&&V8oYSw zA4m{3{hw1Vb~~26K^xro&e7i9eg^SqK0i}kG3z(!_~E?sjJlSWIWXJqKiHAWTG*SpPcCMD`kEc1gx`R^YkYWz zEN4vEIkj@&e4tC!(_~x`-K$w6CU%X7U2Y z)Y}T5stEyoSsB{H{+xfST3tov~6@lO}2gx#N(rHXiOAHT!dp6FiV8V)B4{L_P_% zmX0rPa^-{1xG6|#uEGo+!v)QAOjRe|jg2ICcXU!|Cr+LMbLHlhJ)ErR*P9*z$NLlt zmYjAUbljq004ZyOco?HJovV7M*Wb2nF8vT2D;3kGi%F)6Kr#TVW>}zTHnUQxoGmD0CY9J`|d%8@}n;_co2q zWr98`R_c@PQbMi}x3bWo4XZj{it6qYj+o*XvNoS4>rF;7WNn;vA*|A!3H}Wh-uk@n z*hV0S+XnX;K;BOoz?&*9_{NnM25s4^^QUt|>R!()^Z6#G3OmL{CU^-IG_M7_a~B+& zCrV;ouC1ljbK(K=ygqAE_-}ewnH2&&t0enS7}I4i0wJgNvCf|P$`|DHku`K`HfDa2=n@DCg8MRi_)vpMR2Mxy4PE2Qe! zD||kNXy=0WeU(43v%md9Hg9Zu#CP%d%C67gk_#pfXs8lf>M=betm(}0fdDKq0{26# z_c?J!Cgo-~*=wswLXkR|W8d+rDdV00`22Ouv=_Hod9bmB!=D$I4r@7DZX7e+0tO!9 zR{0d}A6^K#yRx@ykotO4(WUJsmFvN)d-o-wZ(wcDSUS`8jO-JSAMa4y@MK4fDP`(P zzxQ2})ofiauWKj9{Rm$Yw^?g=?`oO(Vf|T^I+-A+o1#F`>tn59d=FtgVJAV=y;G&` z0GMvtEeil5;e$Ln8-41(UeMl2kYLk%vPl?0+Egg_;g)494o5FsvdeZKP;&&fjw7o{ z|B+e%Z|)8Ts?=>@p|hr!nYXgV=ZjI4Cp#$E>+g^6r7Nd3<>-t=G%B5IyZUI{e{49G zqnIXEB=M@5Ndf1J#l5YWcLG=A4ufF8S{z5Kz-uM?Ni{{%mr);=l0=473h#cIc{K3> zZ-VUw_Ng5^HgWQhs5tQU@qv-YBej9`R$a^|lknX<*+sSVXue8M0#EPBJ6_Liwl*8l z_zoD#!l%WIXJZ$jm?|zUu0LdeP&8IW*(|39&QzKGnem$6--u{ZGtHt#Hro*h)?lu zXGKo-4Hv1WP*VLj;uA6UwGSV*6ro%PRbwR{@tXoCOb=OFTB4ru-|Id!rP5Y6LF*-D zy|t0qDSVPo$ffyoj#CIZV?l3VsPRYye$F^xxv~Z78_fwlCWbwW!nYCR2nx0_+@tg3C_UDMVa2Br=X3hfP}^Cp4Yg=#OK}K zKYVY`V9jEKD!UrCbSX6Xym2T-cg}!n;?;o{mM|zWj0P@D|FO-rQ zKt#ApEh#AX%_f%9!G6`I*K=bSnMIhQ%W5&BOMntzVr*eS;WR;FgM)+k`#+Vze*z&V zkU^I-R|!Nwy<~>eeQ~hJqa2|DdpX15kD=6U73Du;T|VarycBP^n#IZeIJ&H3S9#@oec~poZELqX$DAc>XZyuIqd^GK0Jq~0kI=d zA7gMo8%zmkEdnqMh)tkp?V0I;Tm3`>aU3^~dXw zlhdd3=iygnUgYu#GRhxln}4D?Gokczq?T;RjCk0=fUHy18$lt!-q!%sNxee7No^+N$9d?Es*``)0UJ4SC&FNY0pf z_MlbGdUy$|F}YDvJ9GTCkZbsNKj3DL5;=BGBx8xI;n)=A0d0j6MP7Mi6MQdk@Tux2Qy`oI_&*%EQ0bE?|R>P$rDhcFa8O?JIK zPOpFDa?-L*+Q7RrCg#y5z$l0d>n@+OYo3g>-Z*x&`Jj5|=*UOYaJer6;FAbdtt0O? zrFGUE?!XeUG}G8wMgeTs%+r;3uUU;Nq5EuU{h-g&UOBKhdS`;J=m!~xn*ztv_p@dD zR)tR!P=~5kX)FRsx9)uyuu?0dh%Ht7`PTM@e#Cq!z2ts;O;L)tQ1ipDiWqbGz@o_p z^D=UKR#`S7HAt4vQtD(_SeWyj_av~#tJKlb9>-s5Ykuzx_E1ZNl4)~f=zG$*;-y=T z2ozmFva9az<{2&63fQ?(Q8{IPx@t1LuFcxP-LXVctWh3AwazVTt2)w^*Zn-#eB`bD zSHoAusjOBK5(>uQPGj=ijdOH3jqG?(<5#C{*JQ?Lt~@zow=Ii4Al$Vr!#+Cf-gx)A z`_h(>b@7?*6bYM8%628gGW^rwWoG$mK_eCk`}B&llStfwHf12*{5spmTeNH$4{gCY z@Yuwr*k@%m;T<60bw9z6^WpWi@Bu^qe-g;YAzI+VjgsuZaGA=^G*I{KLy@rIjSpWb zFQNsCp2T;S$VaJtZ<(waRu8y7^X;>YhsWp zM)mKgCeE@K;J4vQSV z&-(Gl5AJCp>K*2-`U|4i;u3p8xo6(isu-38>cY zml1Eo&FBBKJpour?}q&nggpFiGM%m+YX`ng8P+uRnJiMyWcv*_AZ8KAB$w;rfmN8C z<-2EB6TqZO>A~P{*<);wYqZgxQS8E*syOXvGkGxF@s(scud0uv?T)fQ z(DGrwM7lvpitUG~6!*}kZUpBn9PuP`5^nMK@($xI^0Q~axP5qU>L~uF{R_<9&m z({}$$WuD1y-QzMVb3jLPk`~bDJNkw(Dv-6cKUb4uzD= z-w?i0NZ2K}AbT}Zi^uOZ32xmSxJw+6(3j%a!~Tdy-@RxVx6YUw2|V6JX+mSJNclfl zF~SD#eo+lnB=ZpHLl{)E+`sI^-V1Vn!6#Ml_W4aH*Pe(++sNI`M=5L3?X1z0;CJeE zJiX5Mp6JH*=R9W0t(1@>>1y=lP^F=yJil6JxU~I}EpTsBx?rJ5LbCbQ zuLBmmX1MO&!E}khx=+#hCesIB53`IWwqyFtR{AUv7vJ{Q^dn1S0@*^UOmRwctFy&> zd={(J@avBzmu$MbyamRMt_$kfHY<*v)%%&nY4hUDH=$k)$8LHlUG0G3Kv#T~-vQjw z)hXbsNIg?~b-jRw)ir5Q(gfwM+Zk+0haf z+4ER%>T8RnKAoJ-(s&tu&-iZ@A?^J|d z6md=9C4am*v2r=aa&a?~37bc($n#wQ<8UGXL+!RtrRXGSj-2INJ#+3J=}e6nOC}G8 zN~lvCS@rxoq7w$CLg-wx!%V%ymw>~xhUw4cADX*$A}D~{21F$!Y61aHwpdL!QcrsN zl~$s5kk%7HWHkZ43%mOcwlk3RcbKGQ*}K(Fxput)rpE0zH0vY(EyY=blQZ`odG#hD z)~{&r6XkSE(^csqsaMm>2c%xsT2&g_Nab1bTY%fIoNHatDY@C@Ei~v@19|F?szU6SWRS)uDXqNY!48RlAb;S*ijqus; zp;bteR835>3BXML2CewOM<^q3M*ubU`}gnI-oS&(vf=GF|JJB-inGOH_dc1xb|iqR zWgrcNy?1*8)vAlAaiBE%K3Q>5Ygy-#Wf$>FqL|Kvgb&6H?iQC*Z|PN)xZJhH#d#=a z@s9O0oea6Lg}submzNZ{iZ*_okZ$6G*h5YO!dE=7c4=YA9g$y%1xjkVl#|1DShEjM zH3(sS?uRfB3mhW5Wrm} zrY>KpBxM&CC;s5Ie_{o}upN{vdb8x<_$5iiQN49`z`+Zz`&E`yLAim;X&}$HAfKmT zkO2Dgdno95mWMH~h2c4);H=MigT8hyzl|4g;dU7F;p^X>w!fa0zf{^rf?>~ z0w{=F_R}ru{g5i@&xwC%R-!-1x|(k6pSb5_)$f`zyErIvSCs{z`iVvU4x_znFKti!!av6BkRX_=+kEc;*`_rla zB`g4ruCJGT3XVTTrlh3Yj>1>PNIy?sV%Yo*=qaBIOY87_?P04yx6TV?_{~K? zOHEo3|2EA2JAMPYZM!H<{|!s-$r>l5{19icxV`Wf-{<0I>{v&H4FZaCy$B6Ludz{v zRH!!HV#JGP?5(L!Zp#}NlOODgWqjO+yo~+LasPYxH+ht2KjdfCFQr(oovP3?vkFK^5FvPJ4^LD=DpYQi4tUXuY1;erJaBQ79 zHcp(>mKvoD+)bq5SX9siR>(%CL??*D>Snn%p}NfGO4(RY^puLI+j$Pw)NZLb5bKo{s|0L~ z-A3R~;QHMg0bHSgESOM&N&@oF4|8gkPF-nVM=sQ;d}wcS{{!iW-)yQ``D6t#xlh(O zRF0Z@O>0uMz9g)u{P))ptV5lH2(gC8I5i(FDRG5Gp1bgBydKgxJy5gBfK(#D7NzZU zatG}S^z#KL*Do5=K*F7hk(`mbdgI1XoM!8*-};#UzNtEG@Nki#`7)GfV;VlfW^)=` zBaAjK5>gx@wf_D!B!2C6xBK^K4%x|+#?P@5N7tlfWo6xWJD~Wz^cnPfFF($Ixt4!j z9%x^1$on56XZB0Irm^kw-*rd1YVO;(*LbB21@7OPJspo%WO676#~oUMws(zP#+shG+$ns0IC3W z_{kYU>N5<_6=j>*0d}r-?8U+--eXfy2M+opoYL|=I932TMp=&k#tzJ^72OtRJ8BVOvTYPh;@EE=LJLeOk`y?d|Dd9%fWlhON^LnB^6x0LyZqz@imyogJ`$C@Lr9Z4o)ZQz>NCavG$$@e2#r3 z4I=}I5KgV>wl)~_Ja7gLQGju0c1{h%cV&6c`doWWv$>q*=ZLc8J{hBiKXNK?zx2Nr zz!pph;BLU2OaZTv>Pzj(VpSp2&OWNCF<~>NgL!nezhxEgj;&2 zl>z@V#>sykFCnFL?|(j)J3SFr|FFa`n@KbhC2pZB7 z#3>qIn&~mG_Vki=p8_x&CFeD4V7MvgJlk^G7H;(apFxr+7Gc0+1KfI6$@aeF+d7DJ~_-A|H=0?Da#&^Cqb=!=fVz>giW5nw=jWQBS%L^t1EZ@ zCm9;qlG{($@0W3T&l17ownc5pWhfM8Mwn-fLtb7H|IYl)8@QikEc_Le+s60x?&B*m z5kObB5{BD}gGr7l84~vP{N)C~3V;xhBWd%=^j0&KBw3T3-HU`;hqWA3OWW~<8nl-M zfYn-BI0_?g`3$_;&Exw<(G{QM|8)Kq28x9NF-F$>r@_BO)t^T*i-U1bX01<)zC_uE zR@8qEQQ#cm$YbXIUPVO?z7KI$pw@r=-V{V@>dC9Hn==1QBVy_b;#*jR+&f*$AwCl?o&G?2Uk4=*Ej zFK^Yvw*HTO9n!XRBWe++o3)4O!OC9PC=_l_<$M(W8(Akk`zv5?nJifb^rH3N?Hhio zo$=nNmSEz_QFHj|XF!vQEcdqPyZz_4|M_GBH)k)KA9XGRlTJD;3*y1c#?ZWkeaQM* z^`Bf04#Z)ARgrE4rMmlk8E5F=NpaW8xKNd3)-orW$m+kh(W12jQbQ7oi z)=#qbmhkplt}u`FC0sV9sdnb5$E!zX_xlA{4wW&j0*DCm`=1;Sh_sB1xiH@C89Z93;8d)EUk=lPNIZ`o3H`Vd+Ig`=CV}#?PAXvzWk{x96fn z0(rYh<>?PJ>Hd8v@c8=*vm+)>P1k@i2>yMaKw2nihLV6Z;wcdc*E2{8=xNh(FkEe3 zq_pc;ISw&}`?lqKx<4vIa67!xu|P}G$c3MDyg?u^InS?uM6Zzys0QM9ChW>g-ypzA zkOUSfvhTTWq{_>TJ{+kpgwX{@>P5ptiJ1NTO5)8 z8BiLUY_!*AJ$V386^TicK@z0qOPWP#Ea5?}!$_&fQ zOcRKuR^tLX*&CM(ahYftiNg!a=uU|He)2nU2(~iX@Yo|foZp906;o=d%aK09YEW7_ z-yX*;XE#z@?zZ&fQ?2fYX!T8@-$(K5Jo+AkyOM+(944x4B%2NR&avFFJY^9_br5UtzSX5@gmYYm@ z@S$jtqFn18bXQr0IYhQ=+2~ZDB_DRW3d=*B+3q`-*1P$i!GVIG(AMp=vBQ#^_mNxp z(;4Iz#_~&9jZ}}7oW?R;_x8&h?b0N326NJq4~>W^TeI^!o4=G5G{|9ff|`NN5+?ns zL@IWva(*@PXPmVGQ#rgIOY*nnoqNDDy$hd2uMT>wBgzg>YT&BV2U{k1ah1(1j_v0` z@o;6~SUGW=!+j!oa9ko_2^G75?VolPmWk=Pb-h{k=phZga( z88Rp7QzbHkpYG!aug9e^DF63Bi|1#CeAW^CpakO9DTT!p$yhuT8Aq10^cl2O@Zl-2RXr`+zCPj#_FqXs}W2{Qvn2Y{BmNsG45? zB{BF_rVgT$u0 zE8o6|@C>uOK1Ba}!V zx!M$9J1B7#_JSs90cKlucib?T&HqQpLE9YV1?v{gh2NWKEt9FX8;3DePnCL5Z=k)Flp=?-i$<5H4zc z`?2ZZ+p~Y8FYr;m3Vn2(u5Z`Av6#S}zkpQpZ|vNP0DY^I-oa$HXzg+ajQC7%wldRN zfOAL!UwFtuphqqR41v|3He4cQF5;UU9M~lti-k<HSTs^#>-Tf|C2&~#m%6WZAy1jz!Q_-IbpZP z8ht8}UG13lz+N-7+01+RlE)6OT^3px7fn@1|_b7^{bhPet}< z_)77(<^>8-qQ2X(n4faVhm@T0@Z{5HFSWs~EDXtV@7IAMbVUP6;v8^%l3PZ#wOZ-* z*Vk4lRj6OYpAZ_$*`t|tYKmLar&&{5{d+5cst)rQTn`n8>Xi+0zXc6YbTPMgzewFg z23F=+`8=FXXF6b*CDVN$v3|6iy;TSFSYh$qrbhKDcT^U9l zj}3g#zty{k*>s8S+>t|cng#3@Rz`z}njy{*?90mV6_Mkvv=iL9pb0ttHf$7;TxkX1 z-klTGb`2~-Mxx6~+{b-KiFd3XG`p?+6-0PMorB#Q@TY_CH5)En#5WrmHqj;@Fvi1A zeGpO@wuYIPOgRY&02e-U+j7!$LZ#5mS72R3MJS^gfheL5`kQV_n{8}KXaj)V%4b~As zFrQ7yZal}~{ELX@8c#V?2LlM@)g(|;VvcBjEuTJ=`WkOem{DL!+7Lr!U;F!mGm_^~ z+V^T?%bz+8noq9{ybcq16Gzd^fS2`skac)@6|;8X8l6Q19epZ@l^3@1ES!x2XLNA4 z_FI8#x5sq7hXVr83D;_5$sU!*Ye}zyx1wMC?Q{DSgrUx#fM?_Fj@{syA2x2yL^J{S zPPLkQ#O+9E9a^H*USdriL6rGHDt$B!vu~t7^)@_e=(<|SVd!MenX48AP(Z$4WoC9_ zeN;I;hEAr{ZvB^gK*1AWfI~5H0a{Y#2UBjn9`7;3JDrI5leeufemoZol*pDlVTSHP z3#8@6kxsJwUFg9(;)>Xm!{nsFC<7}Xwv_?o=eP)$>vvvj>yw z=YS7{pIOg(u@mJ%G0G^TM@L6>l)?_{_e`(yLxmX%h*D zMJS13@e!}HFR{?GNtq;%=4#zUgfFP^$g|Ax1<`vC&qIPbwGNo}3>ZM?=Evk6r|J&S zi$UD-za)A$kcqu)8)1mG z{FI*zS4{wM6S3;RP-!$0&8!6*;>|%T%HJxZt}cmap#~4vD0Pkx22gBbPo~=2iEMFa zSN<~qRz>jf54?e)>3%j;Gc6C1_YO0C|CDQDt7+bE({$0($tizZ)xn2L?@6_ zR3$`yiwH?E%X*^k*^oQ=z!1GA|E&fXHPR=rIEGq4%0=SGvror2Y%k#d`aPmx5@~7a zdkmPa1d-<`6M%& zp9rn|?C(5SRowEcasXoE$)s`=GvJk9wPt|2VX31T2F}6x3#(&IMqZND*a1muBh9?X zX_HSLo?$y$a;qFx^U1W|YAd%)Gaf|AEHqZ*{PW96FF*&nO-@c?c6t5=K_z@2f$8<^ zY}d|9NRviy7sF$61>@bV$B3*VeDg4DX3qScxVTL~5Go^T?}aG+th- z2`EduJx~ZcSssR;yX%oW&ze|$TF?;>HGHp~Eq?$w&SAD?d#s$$|4F@l*T7}X$7>}7 zRvPwxrPaLO5X-qYiQ7{P^4Ui2GDbq&DJ3Yu`)8zfMi1{>HEq`+uR1bJ4x!#n0D6_M8Zs_# z3mc%u30aK|avL-!XI&?{^%v4OXUr4OzaL*|-HV&M5GPx)SUqYMWw@Ex;%DHx^&FOD zncjYHD@AiYbGx1O(rsKW>Eg}cid)6bqA}!r!G{?x#)c?^k+q_uv%Xh3ha^A^{%wnpRPY({1LqK{NQy>!UjUc8f7x2` zgyLiGpsKlFO75ee2#drn3Glyna)PvUP}e(t6P z(8^W6g23+fzT5gZQQ^L-Yg#^P;QK8FTZAe)*|CKS6(I>8a2aoN+XEkYf2jAF!Zi3! zjS($tF@bu(ypeC>`IZtF;jz`F6A-Y7ZUQBuZxp&q4zHb9cc*!1`T3p9xL9`nWhNVr z!2lf=fCA>;1E&E|yfmrHqB#XnUCu28b*4#eZ{lLL(42#`ui?BO&uZj|d_Fh!Bw8g$ zn@2uezsJz@^XM(T{!CEw+EyG*eaF`FuTN%C zOZg)khBpDobCl(3ud$bhr>EdmuQ^l^Cic|y2m>LM+gsZGYKUAeJE5YUX9}j^JDoojv<}Cm&t+agmp?JE0%d#fo}m_cYogpjn5&egilTvDFz-Df}1i zB4)bXfn$dqb!cCa13DdCgMNehaa&${n5Mw&bxeKfNmHq%e{T_H@WB!H3QgFK2gNpB zP<;xkez-y-Lr(0^P^G!YH~WLut`0=mPXbVN64iv6Nd`s=eUQ;?V((+QU0&B4SF3*{Pm$AVrq;v&)c>VLy_UCe45VEsI@ZWM2TaB# zRU6XaLx0^H=0)Z!$rIu`3*s{Z!W7pU@6aHvX*vUuzME+!B5H}k_gFD)3=f;nI zi1|B!@iO%p;L{!JSEI~vyUByf_{HY=;RuAK##-h!06XFwxYi?xl}oWStJ*P{OcVe~ z_v(y8!+BaLQB`(D(XrL0ReKMn$R)8mU2@$q$Pq; zbZq-$IkP4V(`m}e<)cwnZLrjiA-X0@VY~Gi5-PKX20#Eag!JOw1br%7Rr}`(v@d!u zCo@&wE1SwM=zt~$K!eJ**9GAv!}Cogn9(d0X~BwPkU4gaWh?WVRcE3N?C%_R_D)Vw z(YmJTJ_0~fhItqHPqoIFGQYE2!~?aSRa{vjcDWhy5>oT zGOMFTWfL`aLx-!QL(9r?~D6y9Uhq=af8z!rqg#p zXk%gE-;=@G>MUv7p@P#ni@zP*$YQwA0Dlc21`%pV;p!_F@xI(^eA5&SZ{rU?^Wj}! z6Y%C^eMYilc_~MAwqV`h=I0;WA)MqJ^$IvyJ-O0)*RuLYjTL1TWd|(NbhIZ;nOop( z`4bc=fsxaeI@zc!vvYFFetFRKSMjef2_#oIzzPIxZ4oB0sxKOzX4Wltz#G@LD2Qr5 zm9o~xF;EU*_!O`}IigC{sU%1^$$B@>Fa_H0*>*1Amc^7tnKxcPpr8zZTme`6(0@J| zXfBE;0)lcuv%tqq05V8P2B^)Nhq~qdR|1KCfe>(GeuFaNc)T~zvma>o)FZv;sVD@D zynx%jpd8m<{zI zz44BQcmN85TNhy2plu`Nt$b;sKELSBpW)my@*ZnL{lFaD|7-8c-;zw*wh@(1yH+~o zQd6mwOU~P(B4CS|mX=v+F44&NRvMbQpcpDmU!|BhndzGgrsa}~;RGs*v>~aLX|A9$ zxrCyC3y6ZiciVh3@BH@t1LJY%FM8{e94DY4JQ} zYS0fcOC|N!{@iq*a@H$Qe9ONriBWJrhLhC?o5K2)!=~i)0hGh-mMd~RkqdIGCB(fU zy5*IvHssJ&gxudt>g(3w2{)axskJ_#h96qTc~<{c!`n^f zg+SOfdm8=UI!4%}d%RkXd}yWU1H66h)eDTsQr!qkcZE^zbI#F$k(dn7l7z}@YSv1+ zIcEYw{HJjfg()x7R@zQ&o;LdJ2vi6Fkl?OHM-Ga!%w}co(6=I5LZ>n{9pr~6!z|S$ zq_VfE7##n|{H(t$wPI-D`~L#((@V(MZ>p6Eb8k%4{lIGT;hZ9cg%~HhcbDCd%0RbM zs?uZG1wSL{Z0f+NzDiO?w9~XT^dWptKJ@M~0(@5*az*ZgabU465JN9eFY7vD8Wdz_ zlAIonnlivB;uDXov3sIgoKx2>G6a;@?v0qg;r`RnZ{4wMw2%}(e*c8k`R7sNT@>H} zfUU~mHR~8!4rJTHVlT=v3wz2kx&95Nz?@Tj8)s5E}t{|AFA=d_Y zOTqb{ATx>U``k~NJ2hYk3r#Gn1}|1Xj}jq!9%;{k(?9!WZt1z#{OATvapC-}#$LWi zi2R>~v0v6A<|?Eg)Ye#VyRyr7RJ$N4vFEFfmb1jHF(yZN^rc!ULDen>KWu(D9Z5!P ze(qg(G2HmSqyi2B&W`vo@N=3l?+dXbWn-`1LrY1^_mSilpKLLxQp}@s?=Tqw6Do5Pui*IhPZtaT|GAE&MF$;(4s9Bt5f+vbITElRv3( ze&@3GgY%ltiz;PZXq||TeA+sP9bc(#*G<2ck&zF3W?0$Bxit`EwvZb7jke;810>h3 zb}}!oS_xUbJ^$_PWrSlJ-;v4qq!@|L9uM#ALcMu|+|fni+AqPpu+CtjBrs#Y1jKVU zEc6L$d!2l-MgMi5&7?{Dfxj)qn;mIZudn7I6V$88%05A!PtCQTGSxXKMGh;qXa|fE zJBUmhM!}@e#A?s%bajm+=Ka1WxHZWaj;k#XT{T#;bH9c5zA8txVHEz(EeE*PP9eD9 z<2|evdxmVLj_n@`lp>6@ zy_ZTczm54_lGjPwPaq$dF1HdIks&Mp;%bge$QZnnp${}#&Z3)z95ei@b9;c=kJpY- z$G#RZbgyTi3&d4=3%+gXOSp|g^~^%K1id>re4gTka;7m@WA}bFo`GUbT8-n19VVdO}IkuW(H_iil_S}@$xy(Q*fCcNaD60 zxqsWK5lESLWnKgy^ci@da#k9^aW5)oLzbFxlUVBA&UM~79PF7=rW@Ot`>9(Gju3N{A4%EK0dPuz{=J_LUv|Pe^*x3eq_ExMNjB3?{$+xH^_Y z;e5pH)*~Lo@y=;b=P$Iqp9KR|j(>D-kaI4WeI&&HPFRtbZBMiQ^PwE`pF$Z7#(@UF zP2~&InXDTNx3`4)H2mD8yHl{Jk(|C(VA2vwY}3IRqo*qy9HvN7a!$$hlZqjmb6tZy zp1fLd^be5LmcI`_d3@@A`jLDS!b0qXVvP%y>+DfL86Ie=*TZ)PL??Lk^F};4=dwv; zPRBV>*)f&NE0vtjYHw@vs9l(Dk*g-}ARSciwv!f)E361d_9y<;9b7)PBw$3dh`AZi zAY4)BVh3t>;gR=s)nZW3PT_3bOLDK)eTZT^*m%P!HdC!FvK=Z=_iA>Bg!`SsC|P3u zz+oMr^PUcTebccFK>bqp475+?5RUC{Y7klp^p=Q;ZM+c8Zq6wBtH*5c=QHlp7wZS%6AszeebN>>_2^H7uuK@g%1{vF}DT>U{h`}c+u5ubXcFMH)fZ6-l z!y=qVN>jqgj)3T!mALcM;1!8}PDcMCU6<9?l#euNff${zE=b0d%;TcPFfw`y>zjLg#_WgnwatH|t}Y&WrR32m5W_AWNa`OqIc{ zW{_mX(Ck1psRCgMhJ*hXhcAG1ocb_kuY)%9rlYzq8h$K;X}=5m+8CYpJ4Yw6zLi%S zpu}dkAc_hVv>NfWy9eLsQ-6OzoBl{WAkRi|U;anmJ5dFwz(C9~-A(!Vfw z(E!S5ua;@}(q5GrIc6|PAOSPg{il$s$UBI}tk5xuP-VedGyZd}xqXvWvU_`{;Cf0> z5fN79T(#iq-q$RLb(of0ZA0lfepj^!a2-6 zv{v^7r2J*xmj&XVgZ>Wd=RqwGGe1`-Svll~bz(-y7*N1ooU5J*aY@&5ea5ss6n(a? z`N9l?w~=^1g2wLDVRD5ovqLc^Z#YRDFR+QYV4emH*fzOpzer3>Pudh??f``be>dD3 z)xB}1O6bZpnt=j(m92Fxq0dz89n>B05xx10QDL-YDz&e>h_u@9+RG)Pv4{2IYNiMy z8auH}j+fW*;q%Ymtbq+KI_r4gxGUeYJ>hq~vbe!N3%NntH+Dyh7I70!cu(qE_`Vp; z07NvH4Q2s#9;mKj;>umoviK|H+#CbgGq`D+QxI*$r6&D`yf%-M^{H;6gi4*j3?c9c z8$}NK?0I4%b?c`p2;SvL3*xY`0fe_KIZqPm`M%{DCrPUt{bS|zlhbHBNlUe7zcK}E z$L2zIl+z#Z!thJW!}{G&JAC@Pg`H(}GLM_m;uV}C9Yt(vF+F0Dy7{`k zY&v=ZZf?8^qSD>~2iP#{qQK632aMplZye6Q3X>dctS@JHSz2)zJaqXvFEZlr>9$oY z^&9^4pN`1EJcEw_wi@P{zJqQX470?WZTB*5Y7F!3#xJO^z|Gw@)bFoY5#daTP5OgI zcbKI$Ok(|9g_%#If*$3ga=U0_n%|#}eWwyeW~(19Te+!xF*(rd=LU(nM15;<7Z&oA zrqIw#r7}&_qgCdvS7+!|3?8w7JNRtHQ$~8Yyw(xC+n=- z7SQBo3+)tbg2NJn^=lukNOCkiEsgt~4tCrZ{aSnrHRMk@_?1^whFrEn3mT1NSC9B&c-(JrWu@FUhSNf+(>-_%kX#@LYnzq`^M#XX}(*!_LZCY za24(5Y$WH^=;GY^#0c{Y4{_!GPvm_bd#&6ypUpfwu%|+=UEe^Q+oe$7cXnyF@O67L3%SKO#rdayD^4^vH2hG{w%vp|_*jKf4 z=jb?40UP4S+Mi~(Uz(^cvgVB+r+Rt|;wnFRYcz(i=&Q14Ok=V-tTPw4%v&;ZrxI#w z6&rvLjj#yzBr5~N*7o09CkIE=>EWwo`ceL*@Y=504RB*xY#SY{)p3Gvn9zBL_FCN0 zl^axu8p~su8HpiDNi{%5ojAv1{0?t7*mflF9&Y_x4#)X(jyLl~c+s6*I1G7{zBI;tH*_ z94)o##4$cU4ohj~e#C^E><)3E`d;ftdwTQZpDmp)9)n5^+h%BE?)8LI2A`L!zjTBL zPYE&+#0&jDFc&4Tg}VC}E@4ZGyWbiK2dvn6Mpu!cQT_^6!RG!7)fE>V>?PNFm?vc5 z>A8gcW=5Xm2#LEW_;XgMQ$=Y-#lc|zs2}}2ny_4Kb%D@Vrtu6rOmUe!ph7;;L`XHi zXcDHc;OYbIk44?|A9-=Ml{Xap)^{jb5$Kl?v`CIT`bDXV*x{h+UARtzOd}#US>a%X zOdU`5^_P@lkQxB*B<&RQB?FgJOH2-~rMnXf_{5%~s&OlUM^i30FeOM{`XOXs)3_BU zEAyNr%bz8RJ=Cvw8y=)3p z`K|i!j$l~LqQ)kabHK}7WeyB$x*({t#cQWf98qh&X{R*Y--9)~g)?XCL>&z;v9#hY zTFY?DV&1fPE&*z}6Ki`Y5#(-eVYB;OzZjPSDnN%ArA8D>wODpQT4Jt}ah556JE+G_! z_P0uQ!qDhR94VdpAqajIOl4~>oTaQ8H5yXaTZUOb%cRAkWYV?KSNlTqgSM=Wgf)JP zz=?Q5f5zPEVO!NbOCbqEwP^Ff_O_`gdm67#U{Mp^_bKcq2IoO%zcJb(M5z`cjv1Ck z+!awNRhwjj6CQqu+xC#{UWo^3+h?6ymzq3r?3JV}<|u_9x=MWAm`1AqAnOsJ*@)^4 zr|`FkZlg{Cd!#Chmhn=_ZQe;~-DTUOv>)Tbmh0{z_42vWa|vNUO% z_5KA1xNHBgw0zjUH|s5xg$b4k z@Koa#-AFizrr6h2#$k*41tm7_jp$yL4X*DZcklq!u+>9E0WnhcOFPn7Vh^ao@~tno z@RwY)*+8&|Hpdq)`a=L*Teuw;_B@u;o!a!YaOO@bs-?*gqpm?nRkXl~mKFfF z+OVzE%RlC`M5-+KM_GXZ@9b;=2C(sq+R&Ko_RzZ%5P~kDieK3yzV4BN*{$E%KY;4k z)s?*vacHYN~u+?SoI`e@S2!9Co!cdvz;@N@{yj`0-9^8osR(V7PR-O&gM)x3owqs5oJpIwc zgY`#VzjI$V>YYDrIr8D;0JK<10@ycefw z;;oV(!gUR*xBg%xTl-#d>u(5}#jFrLKo}q0b{IuuZhuO7n++ zo@9)d#`(AT$mbW5g;c;&z>1_2Nk%;L?TIhfeK%PYp>5N<5wdihxw4-qvVsN6t@bol zDFgi~t`B&ZU3ek!#fXVE5Ao$7AwI+@amT_m2SclwQE{cLcv3kwhokq+!S%>Fe_*(Z z75)vhq@YqZqa~Hf$0S?T@nr_%mV%*aT${~4)6|(P@Bq_Q!VC4tZa`7?ra`4?oV+wSr2`TVSUmKS_>V@3%0*S#!+L=3f@oF=4k9U9xv0p1;Fx&}V;X2J~h zcz^}G3|;s8JyEFR*LB*fPUm+?f+ofnBQ5uK%NrwA+RV_~h<6-mw_wU?NGRI!zNTh% z&>ty6x8&gW75gdW)?p->&%?{*brS|k@b|(>&<^nyO55Pi_q*eK)=J*Uunw2cw--p%E!VXuDa? ztZ$HPKJ6$Sh7!UrpxVBLFSnpZOw$(ftvg!Nk1LVfL+FL(u zh1Abu(oCSmgqQ2IrE;Zz2f2DAD%T4XO6tU&)2IB}vV3{^xpz1MYFEPy_09RP2QvmA zIqw<(UaCnCs!mFX$+3sjnV*(O5)y`jW!*wzF-l^K`Bxgap+0Ej z@c^nf{Ic`6I5#9bcE7fwiiP8JZ9dr3FsD~SBiW_`8{UgFt*{$@qj#E)90JYra>Zs3 z$sCTuzOye2GdTO;4@;wgJK@!ij-|c--insluCR}{#q=D6Xz#nL6;`rkc*UzLTR%Y{ zN2YK;Zcz4YY=+|(0_?E=#~3U@I1fIyRiBF zIeWj=id+b|L;kSMs>NMfeB^(={IdrC;NYJy_$L+olL`OdOqgH0OpSa?FTRhwb<|%A Pe7HEdAEg|=c=LY&YVNkY literal 0 HcmV?d00001 diff --git a/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_128.png b/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_128.png new file mode 100644 index 0000000000000000000000000000000000000000..13b35eba55c6dabc3aac36f33d859266c18fa0d0 GIT binary patch literal 5680 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 literal 0 HcmV?d00001 diff --git a/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_16.png b/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_16.png new file mode 100644 index 0000000000000000000000000000000000000000..0a3f5fa40fb3d1e0710331a48de5d256da3f275d GIT binary patch literal 520 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 literal 0 HcmV?d00001 diff --git a/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_64.png b/macos/Runner/Assets.xcassets/AppIcon.appiconset/app_icon_64.png new file mode 100644 index 0000000000000000000000000000000000000000..2f1632cfddf3d9dade342351e627a0a75609fb46 GIT binary patch literal 2218 zcmV;b2vzrqP)Px#L}ge>W=%~1DgXcg2mk?xX#fNO00031000^Q000001E2u_0{{R30RRC20H6W@ z1ONa40RR91K%fHv1ONa40RR91KmY&$07g+lumAuE6iGxuRCodHTWf3-RTMruyW6Fu zQYeUM04eX6D5c0FCjKKPrco1(K`<0SL=crI{PC3-^hZU0kQie$gh-5!7z6SH6Q0J% zqot*`H1q{R5fHFYS}dje@;kG=v$L0(yY0?wY2%*c?A&{2?!D*x?m71{of2gv!$5|C z3>qG_BW}7K_yUcT3A5C6QD<+{aq?x;MAUyAiJn#Jv8_zZtQ{P zTRzbL3U9!qVuZzS$xKU10KiW~Bgdcv1-!uAhQxf3a7q+dU6lj?yoO4Lq4TUN4}h{N z*fIM=SS8|C2$(T>w$`t@3Tka!(r!7W`x z-isCVgQD^mG-MJ;XtJuK3V{Vy72GQ83KRWsHU?e*wrhKk=ApIYeDqLi;JI1e zuvv}5^Dc=k7F7?nm3nIw$NVmU-+R>> zyqOR$-2SDpJ}Pt;^RkJytDVXNTsu|mI1`~G7yw`EJR?VkGfNdqK9^^8P`JdtTV&tX4CNcV4 z&N06nZa??Fw1AgQOUSE2AmPE@WO(Fvo`%m`cDgiv(fAeRA%3AGXUbsGw{7Q`cY;1BI#ac3iN$$Hw z0LT0;xc%=q)me?Y*$xI@GRAw?+}>=9D+KTk??-HJ4=A>`V&vKFS75@MKdSF1JTq{S zc1!^8?YA|t+uKigaq!sT;Z!&0F2=k7F0PIU;F$leJLaw2UI6FL^w}OG&!;+b%ya1c z1n+6-inU<0VM-Y_s5iTElq)ThyF?StVcebpGI znw#+zLx2@ah{$_2jn+@}(zJZ{+}_N9BM;z)0yr|gF-4=Iyu@hI*Lk=-A8f#bAzc9f z`Kd6K--x@t04swJVC3JK1cHY-Hq+=|PN-VO;?^_C#;coU6TDP7Bt`;{JTG;!+jj(` zw5cLQ-(Cz-Tlb`A^w7|R56Ce;Wmr0)$KWOUZ6ai0PhzPeHwdl0H(etP zUV`va_i0s-4#DkNM8lUlqI7>YQLf)(lz9Q3Uw`)nc(z3{m5ZE77Ul$V%m)E}3&8L0 z-XaU|eB~Is08eORPk;=<>!1w)Kf}FOVS2l&9~A+@R#koFJ$Czd%Y(ENTV&A~U(IPI z;UY+gf+&6ioZ=roly<0Yst8ck>(M=S?B-ys3mLdM&)ex!hbt+ol|T6CTS+Sc0jv(& z7ijdvFwBq;0a{%3GGwkDKTeG`b+lyj0jjS1OMkYnepCdoosNY`*zmBIo*981BU%%U z@~$z0V`OVtIbEx5pa|Tct|Lg#ZQf5OYMUMRD>Wdxm5SAqV2}3!ceE-M2 z@O~lQ0OiKQp}o9I;?uxCgYVV?FH|?Riri*U$Zi_`V2eiA>l zdSm6;SEm6#T+SpcE8Ro_f2AwxzI z44hfe^WE3!h@W3RDyA_H440cpmYkv*)6m1XazTqw%=E5Xv7^@^^T7Q2wxr+Z2kVYr + + + + + + + + + + + + + + + + + + + + + +

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/macos/Runner/Configs/AppInfo.xcconfig b/macos/Runner/Configs/AppInfo.xcconfig new file mode 100644 index 0000000..15307b7 --- /dev/null +++ b/macos/Runner/Configs/AppInfo.xcconfig @@ -0,0 +1,14 @@ +// Application-level settings for the Runner target. +// +// This may be replaced with something auto-generated from metadata (e.g., pubspec.yaml) in the +// future. If not, the values below would default to using the project name when this becomes a +// 'flutter create' template. + +// The application's name. By default this is also the title of the Flutter window. +PRODUCT_NAME = connect + +// The application's bundle identifier +PRODUCT_BUNDLE_IDENTIFIER = com.example.connect + +// The copyright displayed in application information +PRODUCT_COPYRIGHT = Copyright © 2024 com.example. All rights reserved. diff --git a/macos/Runner/Configs/Debug.xcconfig b/macos/Runner/Configs/Debug.xcconfig new file mode 100644 index 0000000..36b0fd9 --- /dev/null +++ b/macos/Runner/Configs/Debug.xcconfig @@ -0,0 +1,2 @@ +#include "../../Flutter/Flutter-Debug.xcconfig" +#include "Warnings.xcconfig" diff --git a/macos/Runner/Configs/Release.xcconfig b/macos/Runner/Configs/Release.xcconfig new file mode 100644 index 0000000..dff4f49 --- /dev/null +++ b/macos/Runner/Configs/Release.xcconfig @@ -0,0 +1,2 @@ +#include "../../Flutter/Flutter-Release.xcconfig" +#include "Warnings.xcconfig" diff --git a/macos/Runner/Configs/Warnings.xcconfig b/macos/Runner/Configs/Warnings.xcconfig new file mode 100644 index 0000000..42bcbf4 --- /dev/null +++ b/macos/Runner/Configs/Warnings.xcconfig @@ -0,0 +1,13 @@ +WARNING_CFLAGS = -Wall -Wconditional-uninitialized -Wnullable-to-nonnull-conversion -Wmissing-method-return-type -Woverlength-strings +GCC_WARN_UNDECLARED_SELECTOR = YES +CLANG_UNDEFINED_BEHAVIOR_SANITIZER_NULLABILITY = YES +CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE +CLANG_WARN__DUPLICATE_METHOD_MATCH = YES +CLANG_WARN_PRAGMA_PACK = YES +CLANG_WARN_STRICT_PROTOTYPES = YES +CLANG_WARN_COMMA = YES +GCC_WARN_STRICT_SELECTOR_MATCH = YES +CLANG_WARN_OBJC_REPEATED_USE_OF_WEAK = YES +CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES +GCC_WARN_SHADOW = YES +CLANG_WARN_UNREACHABLE_CODE = YES diff --git a/macos/Runner/DebugProfile.entitlements b/macos/Runner/DebugProfile.entitlements new file mode 100644 index 0000000..dddb8a3 --- /dev/null +++ b/macos/Runner/DebugProfile.entitlements @@ -0,0 +1,12 @@ + + + + + com.apple.security.app-sandbox + + com.apple.security.cs.allow-jit + + com.apple.security.network.server + + + diff --git a/macos/Runner/Info.plist b/macos/Runner/Info.plist new file mode 100644 index 0000000..4789daa --- /dev/null +++ b/macos/Runner/Info.plist @@ -0,0 +1,32 @@ + + + + + CFBundleDevelopmentRegion + $(DEVELOPMENT_LANGUAGE) + CFBundleExecutable + $(EXECUTABLE_NAME) + CFBundleIconFile + + CFBundleIdentifier + $(PRODUCT_BUNDLE_IDENTIFIER) + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + $(PRODUCT_NAME) + CFBundlePackageType + APPL + CFBundleShortVersionString + $(FLUTTER_BUILD_NAME) + CFBundleVersion + $(FLUTTER_BUILD_NUMBER) + LSMinimumSystemVersion + $(MACOSX_DEPLOYMENT_TARGET) + NSHumanReadableCopyright + $(PRODUCT_COPYRIGHT) + NSMainNibFile + MainMenu + NSPrincipalClass + NSApplication + + diff --git a/macos/Runner/MainFlutterWindow.swift b/macos/Runner/MainFlutterWindow.swift new file mode 100644 index 0000000..3cc05eb --- /dev/null +++ b/macos/Runner/MainFlutterWindow.swift @@ -0,0 +1,15 @@ +import Cocoa +import FlutterMacOS + +class MainFlutterWindow: NSWindow { + override func awakeFromNib() { + let flutterViewController = FlutterViewController() + let windowFrame = self.frame + self.contentViewController = flutterViewController + self.setFrame(windowFrame, display: true) + + RegisterGeneratedPlugins(registry: flutterViewController) + + super.awakeFromNib() + } +} diff --git a/macos/Runner/Release.entitlements b/macos/Runner/Release.entitlements new file mode 100644 index 0000000..852fa1a --- /dev/null +++ b/macos/Runner/Release.entitlements @@ -0,0 +1,8 @@ + + + + + com.apple.security.app-sandbox + + + diff --git a/macos/RunnerTests/RunnerTests.swift b/macos/RunnerTests/RunnerTests.swift new file mode 100644 index 0000000..61f3bd1 --- /dev/null +++ b/macos/RunnerTests/RunnerTests.swift @@ -0,0 +1,12 @@ +import Cocoa +import FlutterMacOS +import XCTest + +class RunnerTests: XCTestCase { + + func testExample() { + // If you add code to the Runner application, consider adding tests here. + // See https://developer.apple.com/documentation/xctest for more information about using XCTest. + } + +} diff --git a/pubspec.lock b/pubspec.lock new file mode 100644 index 0000000..94e4d81 --- /dev/null +++ b/pubspec.lock @@ -0,0 +1,1124 @@ +# Generated by pub +# See https://dart.dev/tools/pub/glossary#lockfile +packages: + _fe_analyzer_shared: + dependency: transitive + description: + name: _fe_analyzer_shared + sha256: f256b0c0ba6c7577c15e2e4e114755640a875e885099367bf6e012b19314c834 + url: "https://pub.dev" + source: hosted + version: "72.0.0" + _macros: + dependency: transitive + description: dart + source: sdk + version: "0.3.2" + adaptive_number: + dependency: transitive + description: + name: adaptive_number + sha256: "3a567544e9b5c9c803006f51140ad544aedc79604fd4f3f2c1380003f97c1d77" + url: "https://pub.dev" + source: hosted + version: "1.0.0" + analyzer: + dependency: transitive + description: + name: analyzer + sha256: b652861553cd3990d8ed361f7979dc6d7053a9ac8843fa73820ab68ce5410139 + url: "https://pub.dev" + source: hosted + version: "6.7.0" + archive: + dependency: transitive + description: + name: archive + sha256: cb6a278ef2dbb298455e1a713bda08524a175630ec643a242c399c932a0a1f7d + url: "https://pub.dev" + source: hosted + version: "3.6.1" + args: + dependency: transitive + description: + name: args + sha256: bf9f5caeea8d8fe6721a9c358dd8a5c1947b27f1cfaa18b39c301273594919e6 + url: "https://pub.dev" + source: hosted + version: "2.6.0" + async: + dependency: transitive + description: + name: async + sha256: "947bfcf187f74dbc5e146c9eb9c0f10c9f8b30743e341481c1e2ed3ecc18c20c" + url: "https://pub.dev" + source: hosted + version: "2.11.0" + boolean_selector: + dependency: transitive + description: + name: boolean_selector + sha256: "6cfb5af12253eaf2b368f07bacc5a80d1301a071c73360d746b7f2e32d762c66" + url: "https://pub.dev" + source: hosted + version: "2.1.1" + build: + dependency: transitive + description: + name: build + sha256: "80184af8b6cb3e5c1c4ec6d8544d27711700bc3e6d2efad04238c7b5290889f0" + url: "https://pub.dev" + source: hosted + version: "2.4.1" + build_config: + dependency: transitive + description: + name: build_config + sha256: bf80fcfb46a29945b423bd9aad884590fb1dc69b330a4d4700cac476af1708d1 + url: "https://pub.dev" + source: hosted + version: "1.1.1" + build_daemon: + dependency: transitive + description: + name: build_daemon + sha256: "79b2aef6ac2ed00046867ed354c88778c9c0f029df8a20fe10b5436826721ef9" + url: "https://pub.dev" + source: hosted + version: "4.0.2" + build_resolvers: + dependency: transitive + description: + name: build_resolvers + sha256: "339086358431fa15d7eca8b6a36e5d783728cf025e559b834f4609a1fcfb7b0a" + url: "https://pub.dev" + source: hosted + version: "2.4.2" + build_runner: + dependency: "direct dev" + description: + name: build_runner + sha256: "028819cfb90051c6b5440c7e574d1896f8037e3c96cf17aaeb054c9311cfbf4d" + url: "https://pub.dev" + source: hosted + version: "2.4.13" + build_runner_core: + dependency: transitive + description: + name: build_runner_core + sha256: f8126682b87a7282a339b871298cc12009cb67109cfa1614d6436fb0289193e0 + url: "https://pub.dev" + source: hosted + version: "7.3.2" + built_collection: + dependency: transitive + description: + name: built_collection + sha256: "376e3dd27b51ea877c28d525560790aee2e6fbb5f20e2f85d5081027d94e2100" + url: "https://pub.dev" + source: hosted + version: "5.1.1" + built_value: + dependency: transitive + description: + name: built_value + sha256: c7913a9737ee4007efedaffc968c049fd0f3d0e49109e778edc10de9426005cb + url: "https://pub.dev" + source: hosted + version: "8.9.2" + camera: + dependency: "direct main" + description: + name: camera + sha256: "26ff41045772153f222ffffecba711a206f670f5834d40ebf5eed3811692f167" + url: "https://pub.dev" + source: hosted + version: "0.11.0+2" + camera_android_camerax: + dependency: transitive + description: + name: camera_android_camerax + sha256: e3627fdc2132d89212b8a8676679f5b07008c7e3d8ae00cea775c3397f9e742b + url: "https://pub.dev" + source: hosted + version: "0.6.10" + camera_avfoundation: + dependency: transitive + description: + name: camera_avfoundation + sha256: "2e4c568f70e406ccb87376bc06b53d2f5bebaab71e2fbcc1a950e31449381bcf" + url: "https://pub.dev" + source: hosted + version: "0.9.17+5" + camera_platform_interface: + dependency: transitive + description: + name: camera_platform_interface + sha256: b3ede1f171532e0d83111fe0980b46d17f1aa9788a07a2fbed07366bbdbb9061 + url: "https://pub.dev" + source: hosted + version: "2.8.0" + camera_web: + dependency: transitive + description: + name: camera_web + sha256: "595f28c89d1fb62d77c73c633193755b781c6d2e0ebcd8dc25b763b514e6ba8f" + url: "https://pub.dev" + source: hosted + version: "0.3.5" + characters: + dependency: transitive + description: + name: characters + sha256: "04a925763edad70e8443c99234dc3328f442e811f1d8fd1a72f1c8ad0f69a605" + url: "https://pub.dev" + source: hosted + version: "1.3.0" + checked_yaml: + dependency: transitive + description: + name: checked_yaml + sha256: feb6bed21949061731a7a75fc5d2aa727cf160b91af9a3e464c5e3a32e28b5ff + url: "https://pub.dev" + source: hosted + version: "2.0.3" + cli_util: + dependency: transitive + description: + name: cli_util + sha256: ff6785f7e9e3c38ac98b2fb035701789de90154024a75b6cb926445e83197d1c + url: "https://pub.dev" + source: hosted + version: "0.4.2" + clock: + dependency: transitive + description: + name: clock + sha256: cb6d7f03e1de671e34607e909a7213e31d7752be4fb66a86d29fe1eb14bfb5cf + url: "https://pub.dev" + source: hosted + version: "1.1.1" + code_builder: + dependency: transitive + description: + name: code_builder + sha256: "0ec10bf4a89e4c613960bf1e8b42c64127021740fb21640c29c909826a5eea3e" + url: "https://pub.dev" + source: hosted + version: "4.10.1" + collection: + dependency: "direct main" + description: + name: collection + sha256: ee67cb0715911d28db6bf4af1026078bd6f0128b07a5f66fb2ed94ec6783c09a + url: "https://pub.dev" + source: hosted + version: "1.18.0" + convert: + dependency: transitive + description: + name: convert + sha256: b30acd5944035672bc15c6b7a8b47d773e41e2f17de064350988c5d02adb1c68 + url: "https://pub.dev" + source: hosted + version: "3.1.2" + cross_file: + dependency: transitive + description: + name: cross_file + sha256: "7caf6a750a0c04effbb52a676dce9a4a592e10ad35c34d6d2d0e4811160d5670" + url: "https://pub.dev" + source: hosted + version: "0.3.4+2" + crypto: + dependency: transitive + description: + name: crypto + sha256: "1e445881f28f22d6140f181e07737b22f1e099a5e1ff94b0af2f9e4a463f4855" + url: "https://pub.dev" + source: hosted + version: "3.0.6" + cv: + dependency: "direct main" + description: + name: cv + sha256: b7ad2d39ebd8d0a610c69becbd9b0131c1b1544d42186fa025710f8ebff038a0 + url: "https://pub.dev" + source: hosted + version: "1.1.3" + dart_style: + dependency: transitive + description: + name: dart_style + sha256: "7856d364b589d1f08986e140938578ed36ed948581fbc3bc9aef1805039ac5ab" + url: "https://pub.dev" + source: hosted + version: "2.3.7" + device_info_plus: + dependency: transitive + description: + name: device_info_plus + sha256: f545ffbadee826f26f2e1a0f0cbd667ae9a6011cc0f77c0f8f00a969655e6e95 + url: "https://pub.dev" + source: hosted + version: "11.1.1" + device_info_plus_platform_interface: + dependency: transitive + description: + name: device_info_plus_platform_interface + sha256: "282d3cf731045a2feb66abfe61bbc40870ae50a3ed10a4d3d217556c35c8c2ba" + url: "https://pub.dev" + source: hosted + version: "7.0.1" + ed25519_edwards: + dependency: transitive + description: + name: ed25519_edwards + sha256: "6ce0112d131327ec6d42beede1e5dfd526069b18ad45dcf654f15074ad9276cd" + url: "https://pub.dev" + source: hosted + version: "0.3.1" + emoji_picker_flutter: + dependency: transitive + description: + name: emoji_picker_flutter + sha256: "08567e6f914d36c32091a96cf2f51d2558c47aa2bd47a590dc4f50e42e0965f6" + url: "https://pub.dev" + source: hosted + version: "3.1.0" + fake_async: + dependency: transitive + description: + name: fake_async + sha256: "511392330127add0b769b75a987850d136345d9227c6b94c96a04cf4a391bf78" + url: "https://pub.dev" + source: hosted + version: "1.3.1" + ffi: + dependency: transitive + description: + name: ffi + sha256: "16ed7b077ef01ad6170a3d0c57caa4a112a38d7a2ed5602e0aca9ca6f3d98da6" + url: "https://pub.dev" + source: hosted + version: "2.1.3" + file: + dependency: transitive + description: + name: file + sha256: a3b4f84adafef897088c160faf7dfffb7696046cb13ae90b508c2cbc95d3b8d4 + url: "https://pub.dev" + source: hosted + version: "7.0.1" + fixnum: + dependency: transitive + description: + name: fixnum + sha256: b6dc7065e46c974bc7c5f143080a6764ec7a4be6da1285ececdc37be96de53be + url: "https://pub.dev" + source: hosted + version: "1.1.1" + flutter: + dependency: "direct main" + description: flutter + source: sdk + version: "0.0.0" + flutter_launcher_icons: + dependency: "direct dev" + description: + name: flutter_launcher_icons + sha256: "619817c4b65b322b5104b6bb6dfe6cda62d9729bd7ad4303ecc8b4e690a67a77" + url: "https://pub.dev" + source: hosted + version: "0.14.1" + flutter_lints: + dependency: "direct dev" + description: + name: flutter_lints + sha256: "5398f14efa795ffb7a33e9b6a08798b26a180edac4ad7db3f231e40f82ce11e1" + url: "https://pub.dev" + source: hosted + version: "5.0.0" + flutter_localizations: + dependency: "direct main" + description: flutter + source: sdk + version: "0.0.0" + flutter_plugin_android_lifecycle: + dependency: transitive + description: + name: flutter_plugin_android_lifecycle + sha256: "9b78450b89f059e96c9ebb355fa6b3df1d6b330436e0b885fb49594c41721398" + url: "https://pub.dev" + source: hosted + version: "2.0.23" + flutter_secure_storage: + dependency: "direct main" + description: + name: flutter_secure_storage + sha256: "165164745e6afb5c0e3e3fcc72a012fb9e58496fb26ffb92cf22e16a821e85d0" + url: "https://pub.dev" + source: hosted + version: "9.2.2" + flutter_secure_storage_linux: + dependency: transitive + description: + name: flutter_secure_storage_linux + sha256: "4d91bfc23047422cbcd73ac684bc169859ee766482517c22172c86596bf1464b" + url: "https://pub.dev" + source: hosted + version: "1.2.1" + flutter_secure_storage_macos: + dependency: transitive + description: + name: flutter_secure_storage_macos + sha256: "1693ab11121a5f925bbea0be725abfcfbbcf36c1e29e571f84a0c0f436147a81" + url: "https://pub.dev" + source: hosted + version: "3.1.2" + flutter_secure_storage_platform_interface: + dependency: transitive + description: + name: flutter_secure_storage_platform_interface + sha256: cf91ad32ce5adef6fba4d736a542baca9daf3beac4db2d04be350b87f69ac4a8 + url: "https://pub.dev" + source: hosted + version: "1.1.2" + flutter_secure_storage_web: + dependency: transitive + description: + name: flutter_secure_storage_web + sha256: f4ebff989b4f07b2656fb16b47852c0aab9fed9b4ec1c70103368337bc1886a9 + url: "https://pub.dev" + source: hosted + version: "1.2.1" + flutter_secure_storage_windows: + dependency: transitive + description: + name: flutter_secure_storage_windows + sha256: b20b07cb5ed4ed74fc567b78a72936203f587eba460af1df11281c9326cd3709 + url: "https://pub.dev" + source: hosted + version: "3.1.2" + flutter_test: + dependency: "direct dev" + description: flutter + source: sdk + version: "0.0.0" + flutter_web_plugins: + dependency: transitive + description: flutter + source: sdk + version: "0.0.0" + frontend_server_client: + dependency: transitive + description: + name: frontend_server_client + sha256: f64a0333a82f30b0cca061bc3d143813a486dc086b574bfb233b7c1372427694 + url: "https://pub.dev" + source: hosted + version: "4.0.0" + glob: + dependency: transitive + description: + name: glob + sha256: "0e7014b3b7d4dac1ca4d6114f82bf1782ee86745b9b42a92c9289c23d8a0ab63" + url: "https://pub.dev" + source: hosted + version: "2.1.2" + google_fonts: + dependency: "direct main" + description: + name: google_fonts + sha256: b1ac0fe2832c9cc95e5e88b57d627c5e68c223b9657f4b96e1487aa9098c7b82 + url: "https://pub.dev" + source: hosted + version: "6.2.1" + graphs: + dependency: transitive + description: + name: graphs + sha256: "741bbf84165310a68ff28fe9e727332eef1407342fca52759cb21ad8177bb8d0" + url: "https://pub.dev" + source: hosted + version: "2.3.2" + http: + dependency: transitive + description: + name: http + sha256: b9c29a161230ee03d3ccf545097fccd9b87a5264228c5d348202e0f0c28f9010 + url: "https://pub.dev" + source: hosted + version: "1.2.2" + http_multi_server: + dependency: transitive + description: + name: http_multi_server + sha256: "97486f20f9c2f7be8f514851703d0119c3596d14ea63227af6f7a481ef2b2f8b" + url: "https://pub.dev" + source: hosted + version: "3.2.1" + http_parser: + dependency: transitive + description: + name: http_parser + sha256: "2aa08ce0341cc9b354a498388e30986515406668dbcc4f7c950c3e715496693b" + url: "https://pub.dev" + source: hosted + version: "4.0.2" + image: + dependency: "direct main" + description: + name: image + sha256: f31d52537dc417fdcde36088fdf11d191026fd5e4fae742491ebd40e5a8bea7d + url: "https://pub.dev" + source: hosted + version: "4.3.0" + intl: + dependency: transitive + description: + name: intl + sha256: d6f56758b7d3014a48af9701c085700aac781a92a87a62b1333b46d8879661cf + url: "https://pub.dev" + source: hosted + version: "0.19.0" + io: + dependency: transitive + description: + name: io + sha256: "2ec25704aba361659e10e3e5f5d672068d332fc8ac516421d483a11e5cbd061e" + url: "https://pub.dev" + source: hosted + version: "1.0.4" + js: + dependency: transitive + description: + name: js + sha256: f2c445dce49627136094980615a031419f7f3eb393237e4ecd97ac15dea343f3 + url: "https://pub.dev" + source: hosted + version: "0.6.7" + json_annotation: + dependency: "direct main" + description: + name: json_annotation + sha256: "1ce844379ca14835a50d2f019a3099f419082cfdd231cd86a142af94dd5c6bb1" + url: "https://pub.dev" + source: hosted + version: "4.9.0" + json_serializable: + dependency: "direct dev" + description: + name: json_serializable + sha256: ea1432d167339ea9b5bb153f0571d0039607a873d6e04e0117af043f14a1fd4b + url: "https://pub.dev" + source: hosted + version: "6.8.0" + leak_tracker: + dependency: transitive + description: + name: leak_tracker + sha256: "3f87a60e8c63aecc975dda1ceedbc8f24de75f09e4856ea27daf8958f2f0ce05" + url: "https://pub.dev" + source: hosted + version: "10.0.5" + leak_tracker_flutter_testing: + dependency: transitive + description: + name: leak_tracker_flutter_testing + sha256: "932549fb305594d82d7183ecd9fa93463e9914e1b67cacc34bc40906594a1806" + url: "https://pub.dev" + source: hosted + version: "3.0.5" + leak_tracker_testing: + dependency: transitive + description: + name: leak_tracker_testing + sha256: "6ba465d5d76e67ddf503e1161d1f4a6bc42306f9d66ca1e8f079a47290fb06d3" + url: "https://pub.dev" + source: hosted + version: "3.0.1" + libsignal_protocol_dart: + dependency: "direct main" + description: + name: libsignal_protocol_dart + sha256: "2a8d54cddb89eab0301d333c4346d7edc920da0a0c0daa5e324878de2841dce6" + url: "https://pub.dev" + source: hosted + version: "0.7.1" + lints: + dependency: transitive + description: + name: lints + sha256: "3315600f3fb3b135be672bf4a178c55f274bebe368325ae18462c89ac1e3b413" + url: "https://pub.dev" + source: hosted + version: "5.0.0" + logging: + dependency: "direct main" + description: + name: logging + sha256: c8245ada5f1717ed44271ed1c26b8ce85ca3228fd2ffdb75468ab01979309d61 + url: "https://pub.dev" + source: hosted + version: "1.3.0" + macros: + dependency: transitive + description: + name: macros + sha256: "0acaed5d6b7eab89f63350bccd82119e6c602df0f391260d0e32b5e23db79536" + url: "https://pub.dev" + source: hosted + version: "0.1.2-main.4" + matcher: + dependency: transitive + description: + name: matcher + sha256: d2323aa2060500f906aa31a895b4030b6da3ebdcc5619d14ce1aada65cd161cb + url: "https://pub.dev" + source: hosted + version: "0.12.16+1" + material_color_utilities: + dependency: transitive + description: + name: material_color_utilities + sha256: f7142bb1154231d7ea5f96bc7bde4bda2a0945d2806bb11670e30b850d56bdec + url: "https://pub.dev" + source: hosted + version: "0.11.1" + meta: + dependency: transitive + description: + name: meta + sha256: bdb68674043280c3428e9ec998512fb681678676b3c54e773629ffe74419f8c7 + url: "https://pub.dev" + source: hosted + version: "1.15.0" + mime: + dependency: transitive + description: + name: mime + sha256: "41a20518f0cb1256669420fdba0cd90d21561e560ac240f26ef8322e45bb7ed6" + url: "https://pub.dev" + source: hosted + version: "2.0.0" + mobile_scanner: + dependency: "direct main" + description: + name: mobile_scanner + sha256: "728828a798d1a2ee506beb652ca23d974c542c96ed03dcbd5eaf97bef96cdaad" + url: "https://pub.dev" + source: hosted + version: "6.0.2" + optional: + dependency: transitive + description: + name: optional + sha256: f80327d7a3335a0be68418072668043c7ab291df575c21aa42e0c5633641da39 + url: "https://pub.dev" + source: hosted + version: "6.1.0+1" + package_config: + dependency: transitive + description: + name: package_config + sha256: "1c5b77ccc91e4823a5af61ee74e6b972db1ef98c2ff5a18d3161c982a55448bd" + url: "https://pub.dev" + source: hosted + version: "2.1.0" + path: + dependency: "direct main" + description: + name: path + sha256: "087ce49c3f0dc39180befefc60fdb4acd8f8620e5682fe2476afd0b3688bb4af" + url: "https://pub.dev" + source: hosted + version: "1.9.0" + path_provider: + dependency: "direct main" + description: + name: path_provider + sha256: "50c5dd5b6e1aaf6fb3a78b33f6aa3afca52bf903a8a5298f53101fdaee55bbcd" + url: "https://pub.dev" + source: hosted + version: "2.1.5" + path_provider_android: + dependency: transitive + description: + name: path_provider_android + sha256: c464428172cb986b758c6d1724c603097febb8fb855aa265aeecc9280c294d4a + url: "https://pub.dev" + source: hosted + version: "2.2.12" + path_provider_foundation: + dependency: transitive + description: + name: path_provider_foundation + sha256: f234384a3fdd67f989b4d54a5d73ca2a6c422fa55ae694381ae0f4375cd1ea16 + url: "https://pub.dev" + source: hosted + version: "2.4.0" + path_provider_linux: + dependency: transitive + description: + name: path_provider_linux + sha256: f7a1fe3a634fe7734c8d3f2766ad746ae2a2884abe22e241a8b301bf5cac3279 + url: "https://pub.dev" + source: hosted + version: "2.2.1" + path_provider_platform_interface: + dependency: transitive + description: + name: path_provider_platform_interface + sha256: "88f5779f72ba699763fa3a3b06aa4bf6de76c8e5de842cf6f29e2e06476c2334" + url: "https://pub.dev" + source: hosted + version: "2.1.2" + path_provider_windows: + dependency: transitive + description: + name: path_provider_windows + sha256: bd6f00dbd873bfb70d0761682da2b3a2c2fccc2b9e84c495821639601d81afe7 + url: "https://pub.dev" + source: hosted + version: "2.3.0" + permission_handler: + dependency: "direct main" + description: + name: permission_handler + sha256: "18bf33f7fefbd812f37e72091a15575e72d5318854877e0e4035a24ac1113ecb" + url: "https://pub.dev" + source: hosted + version: "11.3.1" + permission_handler_android: + dependency: transitive + description: + name: permission_handler_android + sha256: "71bbecfee799e65aff7c744761a57e817e73b738fedf62ab7afd5593da21f9f1" + url: "https://pub.dev" + source: hosted + version: "12.0.13" + permission_handler_apple: + dependency: transitive + description: + name: permission_handler_apple + sha256: e6f6d73b12438ef13e648c4ae56bd106ec60d17e90a59c4545db6781229082a0 + url: "https://pub.dev" + source: hosted + version: "9.4.5" + permission_handler_html: + dependency: transitive + description: + name: permission_handler_html + sha256: "6b9cb54b7135073841a35513fba39e598b421702d5f4d92319992fd6eb5532a9" + url: "https://pub.dev" + source: hosted + version: "0.1.3+4" + permission_handler_platform_interface: + dependency: transitive + description: + name: permission_handler_platform_interface + sha256: e9c8eadee926c4532d0305dff94b85bf961f16759c3af791486613152af4b4f9 + url: "https://pub.dev" + source: hosted + version: "4.2.3" + permission_handler_windows: + dependency: transitive + description: + name: permission_handler_windows + sha256: "1a790728016f79a41216d88672dbc5df30e686e811ad4e698bfc51f76ad91f1e" + url: "https://pub.dev" + source: hosted + version: "0.2.1" + petitparser: + dependency: transitive + description: + name: petitparser + sha256: c15605cd28af66339f8eb6fbe0e541bfe2d1b72d5825efc6598f3e0a31b9ad27 + url: "https://pub.dev" + source: hosted + version: "6.0.2" + platform: + dependency: transitive + description: + name: platform + sha256: "5d6b1b0036a5f331ebc77c850ebc8506cbc1e9416c27e59b439f917a902a4984" + url: "https://pub.dev" + source: hosted + version: "3.1.6" + plugin_platform_interface: + dependency: transitive + description: + name: plugin_platform_interface + sha256: "4820fbfdb9478b1ebae27888254d445073732dae3d6ea81f0b7e06d5dedc3f02" + url: "https://pub.dev" + source: hosted + version: "2.1.8" + pointycastle: + dependency: transitive + description: + name: pointycastle + sha256: "4be0097fcf3fd3e8449e53730c631200ebc7b88016acecab2b0da2f0149222fe" + url: "https://pub.dev" + source: hosted + version: "3.9.1" + pool: + dependency: transitive + description: + name: pool + sha256: "20fe868b6314b322ea036ba325e6fc0711a22948856475e2c2b6306e8ab39c2a" + url: "https://pub.dev" + source: hosted + version: "1.5.1" + pro_image_editor: + dependency: "direct main" + description: + name: pro_image_editor + sha256: "419691ffe116b0282c8c4467aa1098d76e1dc2671002f8269d54715e349ebe24" + url: "https://pub.dev" + source: hosted + version: "6.1.3" + protobuf: + dependency: transitive + description: + name: protobuf + sha256: "01dd9bd0fa02548bf2ceee13545d4a0ec6046459d847b6b061d8a27237108a08" + url: "https://pub.dev" + source: hosted + version: "2.1.0" + pub_semver: + dependency: transitive + description: + name: pub_semver + sha256: "40d3ab1bbd474c4c2328c91e3a7df8c6dd629b79ece4c4bd04bee496a224fb0c" + url: "https://pub.dev" + source: hosted + version: "2.1.4" + pubspec_parse: + dependency: transitive + description: + name: pubspec_parse + sha256: c799b721d79eb6ee6fa56f00c04b472dcd44a30d258fac2174a6ec57302678f8 + url: "https://pub.dev" + source: hosted + version: "1.3.0" + restart_app: + dependency: "direct main" + description: + name: restart_app + sha256: "00d5ec3e9de871cedbe552fc41e615b042b5ec654385e090e0983f6d02f655ed" + url: "https://pub.dev" + source: hosted + version: "1.3.2" + shared_preferences: + dependency: transitive + description: + name: shared_preferences + sha256: "95f9997ca1fb9799d494d0cb2a780fd7be075818d59f00c43832ed112b158a82" + url: "https://pub.dev" + source: hosted + version: "2.3.3" + shared_preferences_android: + dependency: transitive + description: + name: shared_preferences_android + sha256: "3b9febd815c9ca29c9e3520d50ec32f49157711e143b7a4ca039eb87e8ade5ab" + url: "https://pub.dev" + source: hosted + version: "2.3.3" + shared_preferences_foundation: + dependency: transitive + description: + name: shared_preferences_foundation + sha256: "07e050c7cd39bad516f8d64c455f04508d09df104be326d8c02551590a0d513d" + url: "https://pub.dev" + source: hosted + version: "2.5.3" + shared_preferences_linux: + dependency: transitive + description: + name: shared_preferences_linux + sha256: "580abfd40f415611503cae30adf626e6656dfb2f0cee8f465ece7b6defb40f2f" + url: "https://pub.dev" + source: hosted + version: "2.4.1" + shared_preferences_platform_interface: + dependency: transitive + description: + name: shared_preferences_platform_interface + sha256: "57cbf196c486bc2cf1f02b85784932c6094376284b3ad5779d1b1c6c6a816b80" + url: "https://pub.dev" + source: hosted + version: "2.4.1" + shared_preferences_web: + dependency: transitive + description: + name: shared_preferences_web + sha256: d2ca4132d3946fec2184261726b355836a82c33d7d5b67af32692aff18a4684e + url: "https://pub.dev" + source: hosted + version: "2.4.2" + shared_preferences_windows: + dependency: transitive + description: + name: shared_preferences_windows + sha256: "94ef0f72b2d71bc3e700e025db3710911bd51a71cefb65cc609dd0d9a982e3c1" + url: "https://pub.dev" + source: hosted + version: "2.4.1" + shelf: + dependency: transitive + description: + name: shelf + sha256: ad29c505aee705f41a4d8963641f91ac4cee3c8fad5947e033390a7bd8180fa4 + url: "https://pub.dev" + source: hosted + version: "1.4.1" + shelf_web_socket: + dependency: transitive + description: + name: shelf_web_socket + sha256: "073c147238594ecd0d193f3456a5fe91c4b0abbcc68bf5cd95b36c4e194ac611" + url: "https://pub.dev" + source: hosted + version: "2.0.0" + sky_engine: + dependency: transitive + description: flutter + source: sdk + version: "0.0.99" + source_gen: + dependency: transitive + description: + name: source_gen + sha256: "14658ba5f669685cd3d63701d01b31ea748310f7ab854e471962670abcf57832" + url: "https://pub.dev" + source: hosted + version: "1.5.0" + source_helper: + dependency: transitive + description: + name: source_helper + sha256: "6adebc0006c37dd63fe05bca0a929b99f06402fc95aa35bf36d67f5c06de01fd" + url: "https://pub.dev" + source: hosted + version: "1.3.4" + source_span: + dependency: transitive + description: + name: source_span + sha256: "53e943d4206a5e30df338fd4c6e7a077e02254531b138a15aec3bd143c1a8b3c" + url: "https://pub.dev" + source: hosted + version: "1.10.0" + sqflite_common: + dependency: transitive + description: + name: sqflite_common + sha256: "761b9740ecbd4d3e66b8916d784e581861fd3c3553eda85e167bc49fdb68f709" + url: "https://pub.dev" + source: hosted + version: "2.5.4+6" + sqflite_sqlcipher: + dependency: "direct main" + description: + name: sqflite_sqlcipher + sha256: "16033fde6c7d7bd657b71a2bc42332ab02bc8001c3212f502d2e02714e735ec9" + url: "https://pub.dev" + source: hosted + version: "3.1.0+1" + stack_trace: + dependency: transitive + description: + name: stack_trace + sha256: "73713990125a6d93122541237550ee3352a2d84baad52d375a4cad2eb9b7ce0b" + url: "https://pub.dev" + source: hosted + version: "1.11.1" + stream_channel: + dependency: transitive + description: + name: stream_channel + sha256: ba2aa5d8cc609d96bbb2899c28934f9e1af5cddbd60a827822ea467161eb54e7 + url: "https://pub.dev" + source: hosted + version: "2.1.2" + stream_transform: + dependency: transitive + description: + name: stream_transform + sha256: "14a00e794c7c11aa145a170587321aedce29769c08d7f58b1d141da75e3b1c6f" + url: "https://pub.dev" + source: hosted + version: "2.1.0" + string_scanner: + dependency: transitive + description: + name: string_scanner + sha256: "556692adab6cfa87322a115640c11f13cb77b3f076ddcc5d6ae3c20242bedcde" + url: "https://pub.dev" + source: hosted + version: "1.2.0" + synchronized: + dependency: transitive + description: + name: synchronized + sha256: "69fe30f3a8b04a0be0c15ae6490fc859a78ef4c43ae2dd5e8a623d45bfcf9225" + url: "https://pub.dev" + source: hosted + version: "3.3.0+3" + term_glyph: + dependency: transitive + description: + name: term_glyph + sha256: a29248a84fbb7c79282b40b8c72a1209db169a2e0542bce341da992fe1bc7e84 + url: "https://pub.dev" + source: hosted + version: "1.2.1" + test_api: + dependency: transitive + description: + name: test_api + sha256: "5b8a98dafc4d5c4c9c72d8b31ab2b23fc13422348d2997120294d3bac86b4ddb" + url: "https://pub.dev" + source: hosted + version: "0.7.2" + timing: + dependency: transitive + description: + name: timing + sha256: "70a3b636575d4163c477e6de42f247a23b315ae20e86442bebe32d3cabf61c32" + url: "https://pub.dev" + source: hosted + version: "1.0.1" + typed_data: + dependency: transitive + description: + name: typed_data + sha256: f9049c039ebfeb4cf7a7104a675823cd72dba8297f264b6637062516699fa006 + url: "https://pub.dev" + source: hosted + version: "1.4.0" + vector_math: + dependency: transitive + description: + name: vector_math + sha256: "80b3257d1492ce4d091729e3a67a60407d227c27241d6927be0130c98e741803" + url: "https://pub.dev" + source: hosted + version: "2.1.4" + very_good_analysis: + dependency: transitive + description: + name: very_good_analysis + sha256: "9ae7f3a3bd5764fb021b335ca28a34f040cd0ab6eec00a1b213b445dae58a4b8" + url: "https://pub.dev" + source: hosted + version: "5.1.0" + vibration: + dependency: transitive + description: + name: vibration + sha256: f0af02af2d63132135ae0332a3e54d5de718e214ee94c4f082176ef6ce624a4b + url: "https://pub.dev" + source: hosted + version: "2.0.1" + vibration_platform_interface: + dependency: transitive + description: + name: vibration_platform_interface + sha256: f66b39aab2447038978c16f3d6f77228e49ef5717556e3da02313e044e4a7600 + url: "https://pub.dev" + source: hosted + version: "0.0.2" + vm_service: + dependency: transitive + description: + name: vm_service + sha256: "5c5f338a667b4c644744b661f309fb8080bb94b18a7e91ef1dbd343bed00ed6d" + url: "https://pub.dev" + source: hosted + version: "14.2.5" + watcher: + dependency: transitive + description: + name: watcher + sha256: "3d2ad6751b3c16cf07c7fca317a1413b3f26530319181b37e3b9039b84fc01d8" + url: "https://pub.dev" + source: hosted + version: "1.1.0" + web: + dependency: transitive + description: + name: web + sha256: cd3543bd5798f6ad290ea73d210f423502e71900302dde696f8bff84bf89a1cb + url: "https://pub.dev" + source: hosted + version: "1.1.0" + web_socket: + dependency: transitive + description: + name: web_socket + sha256: "3c12d96c0c9a4eec095246debcea7b86c0324f22df69893d538fcc6f1b8cce83" + url: "https://pub.dev" + source: hosted + version: "0.1.6" + web_socket_channel: + dependency: "direct main" + description: + name: web_socket_channel + sha256: "9f187088ed104edd8662ca07af4b124465893caf063ba29758f97af57e61da8f" + url: "https://pub.dev" + source: hosted + version: "3.0.1" + win32: + dependency: transitive + description: + name: win32 + sha256: "84ba388638ed7a8cb3445a320c8273136ab2631cd5f2c57888335504ddab1bc2" + url: "https://pub.dev" + source: hosted + version: "5.8.0" + win32_registry: + dependency: transitive + description: + name: win32_registry + sha256: "21ec76dfc731550fd3e2ce7a33a9ea90b828fdf19a5c3bcf556fa992cfa99852" + url: "https://pub.dev" + source: hosted + version: "1.1.5" + x25519: + dependency: transitive + description: + name: x25519 + sha256: cec3c125f0d934dccba6c4cab48f3fbf866dc78895dcc5a1584d35b0a845005b + url: "https://pub.dev" + source: hosted + version: "0.1.1" + xdg_directories: + dependency: transitive + description: + name: xdg_directories + sha256: "7a3f37b05d989967cdddcbb571f1ea834867ae2faa29725fd085180e0883aa15" + url: "https://pub.dev" + source: hosted + version: "1.1.0" + xml: + dependency: transitive + description: + name: xml + sha256: b015a8ad1c488f66851d762d3090a21c600e479dc75e68328c52774040cf9226 + url: "https://pub.dev" + source: hosted + version: "6.5.0" + yaml: + dependency: transitive + description: + name: yaml + sha256: "75769501ea3489fca56601ff33454fe45507ea3bfb014161abc3b43ae25989d5" + url: "https://pub.dev" + source: hosted + version: "3.1.2" +sdks: + dart: ">=3.5.4 <4.0.0" + flutter: ">=3.24.0" diff --git a/pubspec.yaml b/pubspec.yaml new file mode 100644 index 0000000..0ecf289 --- /dev/null +++ b/pubspec.yaml @@ -0,0 +1,57 @@ +name: connect +description: "Connect securely with your friends." + +# Prevent accidental publishing to pub.dev. +publish_to: 'none' + +version: 1.0.0+1 + +environment: + sdk: ^3.5.4 + +dependencies: + camera: ^0.11.0+2 + collection: ^1.18.0 + cv: ^1.1.3 + flutter: + sdk: flutter + flutter_localizations: + sdk: flutter + flutter_secure_storage: ^9.2.2 + google_fonts: ^6.2.1 + image: ^4.3.0 + json_annotation: ^4.9.0 + libsignal_protocol_dart: ^0.7.1 + logging: ^1.3.0 + mobile_scanner: ^6.0.2 + path: ^1.9.0 + path_provider: ^2.1.5 + permission_handler: ^11.3.1 + pro_image_editor: ^6.1.3 + restart_app: ^1.3.2 + sqflite_sqlcipher: ^3.1.0+1 + web_socket_channel: ^3.0.1 + +dev_dependencies: + flutter_test: + sdk: flutter + build_runner: ^2.3.3 + json_serializable: ^6.8.0 + flutter_lints: ^5.0.0 + flutter_launcher_icons: ^0.14.1 + +flutter_launcher_icons: + android: "launcher_icon" + ios: true + image_path: "assets/images/logo.png" + min_sdk_android: 21 # android min sdk min:16, default 21 + +flutter: + uses-material-design: true + + # Enable generation of localized Strings from arb files. + generate: true + + assets: + # Add assets from the images directory to the application. + - assets/images/ diff --git a/test/unit_test.dart b/test/unit_test.dart new file mode 100644 index 0000000..026f329 --- /dev/null +++ b/test/unit_test.dart @@ -0,0 +1,15 @@ +// This is an example unit test. +// +// A unit test tests a single function, method, or class. To learn more about +// writing unit tests, visit +// https://flutter.dev/to/unit-testing + +import 'package:flutter_test/flutter_test.dart'; + +void main() { + group('Plus Operator', () { + test('should add two numbers together', () { + expect(1 + 1, 2); + }); + }); +} diff --git a/test/widget_test.dart b/test/widget_test.dart new file mode 100644 index 0000000..1d8332f --- /dev/null +++ b/test/widget_test.dart @@ -0,0 +1,31 @@ +// This is an example Flutter widget test. +// +// To perform an interaction with a widget in your test, use the WidgetTester +// utility in the flutter_test package. For example, you can send tap and scroll +// gestures. You can also use WidgetTester to find child widgets in the widget +// tree, read text, and verify that the values of widget properties are correct. +// +// Visit https://flutter.dev/to/widget-testing for +// more information about Widget testing. + +import 'package:flutter/material.dart'; +import 'package:flutter_test/flutter_test.dart'; + +void main() { + group('MyWidget', () { + testWidgets('should display a string of text', (WidgetTester tester) async { + // Define a Widget + const myWidget = MaterialApp( + home: Scaffold( + body: Text('Hello'), + ), + ); + + // Build myWidget and trigger a frame. + await tester.pumpWidget(myWidget); + + // Verify myWidget shows some text + expect(find.byType(Text), findsOneWidget); + }); + }); +} diff --git a/web/favicon.png b/web/favicon.png new file mode 100644 index 0000000000000000000000000000000000000000..8aaa46ac1ae21512746f852a42ba87e4165dfdd1 GIT binary patch literal 917 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`jKx9jP7LeL$-D$|I14-?iy0X7 zltGxWVyS%@P(fs7NJL45ua8x7ey(0(N`6wRUPW#JP&EUCO@$SZnVVXYs8ErclUHn2 zVXFjIVFhG^g!Ppaz)DK8ZIvQ?0~DO|i&7O#^-S~(l1AfjnEK zjFOT9D}DX)@^Za$W4-*MbbUihOG|wNBYh(yU7!lx;>x^|#0uTKVr7USFmqf|i<65o z3raHc^AtelCMM;Vme?vOfh>Xph&xL%(-1c06+^uR^q@XSM&D4+Kp$>4P^%3{)XKjo zGZknv$b36P8?Z_gF{nK@`XI}Z90TzwSQO}0J1!f2c(B=V`5aP@1P1a|PZ!4!3&Gl8 zTYqUsf!gYFyJnXpu0!n&N*SYAX-%d(5gVjrHJWqXQshj@!Zm{!01WsQrH~9=kTxW#6SvuapgMqt>$=j#%eyGrQzr zP{L-3gsMA^$I1&gsBAEL+vxi1*Igl=8#8`5?A-T5=z-sk46WA1IUT)AIZHx1rdUrf zVJrJn<74DDw`j)Ki#gt}mIT-Q`XRa2-jQXQoI%w`nb|XblvzK${ZzlV)m-XcwC(od z71_OEC5Bt9GEXosOXaPTYOia#R4ID2TiU~`zVMl08TV_C%DnU4^+HE>9(CE4D6?Fz oujB08i7adh9xk7*FX66dWH6F5TM;?E2b5PlUHx3vIVCg!0Dx9vYXATM literal 0 HcmV?d00001 diff --git a/web/icons/Icon-192.png b/web/icons/Icon-192.png new file mode 100644 index 0000000000000000000000000000000000000000..b749bfef07473333cf1dd31e9eed89862a5d52aa GIT binary patch literal 5292 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 literal 0 HcmV?d00001 diff --git a/web/icons/Icon-512.png b/web/icons/Icon-512.png new file mode 100644 index 0000000000000000000000000000000000000000..88cfd48dff1169879ba46840804b412fe02fefd6 GIT binary patch literal 8252 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 literal 0 HcmV?d00001 diff --git a/web/icons/Icon-maskable-192.png b/web/icons/Icon-maskable-192.png new file mode 100644 index 0000000000000000000000000000000000000000..eb9b4d76e525556d5d89141648c724331630325d GIT binary patch literal 5594 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 X>c!)3PgKfL&lX^$Z>Cpu&6)6jvi^Z! literal 0 HcmV?d00001 diff --git a/web/icons/Icon-maskable-512.png b/web/icons/Icon-maskable-512.png new file mode 100644 index 0000000000000000000000000000000000000000..d69c56691fbdb0b7efa65097c7cc1edac12a6d3e GIT binary patch literal 20998 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 MPgg&ebxsLQ025IeI{*Lx literal 0 HcmV?d00001 diff --git a/web/index.html b/web/index.html new file mode 100644 index 0000000..85c6dab --- /dev/null +++ b/web/index.html @@ -0,0 +1,38 @@ + + + + + + + + + + + + + + + + + + + + connect + + + + + + diff --git a/web/manifest.json b/web/manifest.json new file mode 100644 index 0000000..57574b7 --- /dev/null +++ b/web/manifest.json @@ -0,0 +1,35 @@ +{ + "name": "connect", + "short_name": "connect", + "start_url": ".", + "display": "standalone", + "background_color": "#0175C2", + "theme_color": "#0175C2", + "description": "A new Flutter project.", + "orientation": "portrait-primary", + "prefer_related_applications": false, + "icons": [ + { + "src": "icons/Icon-192.png", + "sizes": "192x192", + "type": "image/png" + }, + { + "src": "icons/Icon-512.png", + "sizes": "512x512", + "type": "image/png" + }, + { + "src": "icons/Icon-maskable-192.png", + "sizes": "192x192", + "type": "image/png", + "purpose": "maskable" + }, + { + "src": "icons/Icon-maskable-512.png", + "sizes": "512x512", + "type": "image/png", + "purpose": "maskable" + } + ] +} diff --git a/windows/.gitignore b/windows/.gitignore new file mode 100644 index 0000000..d492d0d --- /dev/null +++ b/windows/.gitignore @@ -0,0 +1,17 @@ +flutter/ephemeral/ + +# Visual Studio user-specific files. +*.suo +*.user +*.userosscache +*.sln.docstates + +# Visual Studio build-related files. +x64/ +x86/ + +# Visual Studio cache files +# files ending in .cache can be ignored +*.[Cc]ache +# but keep track of directories ending in .cache +!*.[Cc]ache/ diff --git a/windows/CMakeLists.txt b/windows/CMakeLists.txt new file mode 100644 index 0000000..4bdc26d --- /dev/null +++ b/windows/CMakeLists.txt @@ -0,0 +1,108 @@ +# Project-level configuration. +cmake_minimum_required(VERSION 3.14) +project(connect LANGUAGES CXX) + +# The name of the executable created for the application. Change this to change +# the on-disk name of your application. +set(BINARY_NAME "connect") + +# Explicitly opt in to modern CMake behaviors to avoid warnings with recent +# versions of CMake. +cmake_policy(VERSION 3.14...3.25) + +# Define build configuration option. +get_property(IS_MULTICONFIG GLOBAL PROPERTY GENERATOR_IS_MULTI_CONFIG) +if(IS_MULTICONFIG) + set(CMAKE_CONFIGURATION_TYPES "Debug;Profile;Release" + CACHE STRING "" FORCE) +else() + if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES) + set(CMAKE_BUILD_TYPE "Debug" CACHE + STRING "Flutter build mode" FORCE) + set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS + "Debug" "Profile" "Release") + endif() +endif() +# Define settings for the Profile build mode. +set(CMAKE_EXE_LINKER_FLAGS_PROFILE "${CMAKE_EXE_LINKER_FLAGS_RELEASE}") +set(CMAKE_SHARED_LINKER_FLAGS_PROFILE "${CMAKE_SHARED_LINKER_FLAGS_RELEASE}") +set(CMAKE_C_FLAGS_PROFILE "${CMAKE_C_FLAGS_RELEASE}") +set(CMAKE_CXX_FLAGS_PROFILE "${CMAKE_CXX_FLAGS_RELEASE}") + +# Use Unicode for all projects. +add_definitions(-DUNICODE -D_UNICODE) + +# Compilation settings that should be applied to most targets. +# +# Be cautious about adding new options here, as plugins use this function by +# default. In most cases, you should add new options to specific targets instead +# of modifying this function. +function(APPLY_STANDARD_SETTINGS TARGET) + target_compile_features(${TARGET} PUBLIC cxx_std_17) + target_compile_options(${TARGET} PRIVATE /W4 /WX /wd"4100") + target_compile_options(${TARGET} PRIVATE /EHsc) + target_compile_definitions(${TARGET} PRIVATE "_HAS_EXCEPTIONS=0") + target_compile_definitions(${TARGET} PRIVATE "$<$:_DEBUG>") +endfunction() + +# Flutter library and tool build rules. +set(FLUTTER_MANAGED_DIR "${CMAKE_CURRENT_SOURCE_DIR}/flutter") +add_subdirectory(${FLUTTER_MANAGED_DIR}) + +# Application build; see runner/CMakeLists.txt. +add_subdirectory("runner") + + +# Generated plugin build rules, which manage building the plugins and adding +# them to the application. +include(flutter/generated_plugins.cmake) + + +# === Installation === +# Support files are copied into place next to the executable, so that it can +# run in place. This is done instead of making a separate bundle (as on Linux) +# so that building and running from within Visual Studio will work. +set(BUILD_BUNDLE_DIR "$") +# Make the "install" step default, as it's required to run. +set(CMAKE_VS_INCLUDE_INSTALL_TO_DEFAULT_BUILD 1) +if(CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT) + set(CMAKE_INSTALL_PREFIX "${BUILD_BUNDLE_DIR}" CACHE PATH "..." FORCE) +endif() + +set(INSTALL_BUNDLE_DATA_DIR "${CMAKE_INSTALL_PREFIX}/data") +set(INSTALL_BUNDLE_LIB_DIR "${CMAKE_INSTALL_PREFIX}") + +install(TARGETS ${BINARY_NAME} RUNTIME DESTINATION "${CMAKE_INSTALL_PREFIX}" + COMPONENT Runtime) + +install(FILES "${FLUTTER_ICU_DATA_FILE}" DESTINATION "${INSTALL_BUNDLE_DATA_DIR}" + COMPONENT Runtime) + +install(FILES "${FLUTTER_LIBRARY}" DESTINATION "${INSTALL_BUNDLE_LIB_DIR}" + COMPONENT Runtime) + +if(PLUGIN_BUNDLED_LIBRARIES) + install(FILES "${PLUGIN_BUNDLED_LIBRARIES}" + DESTINATION "${INSTALL_BUNDLE_LIB_DIR}" + COMPONENT Runtime) +endif() + +# Copy the native assets provided by the build.dart from all packages. +set(NATIVE_ASSETS_DIR "${PROJECT_BUILD_DIR}native_assets/windows/") +install(DIRECTORY "${NATIVE_ASSETS_DIR}" + DESTINATION "${INSTALL_BUNDLE_LIB_DIR}" + COMPONENT Runtime) + +# Fully re-copy the assets directory on each build to avoid having stale files +# from a previous install. +set(FLUTTER_ASSET_DIR_NAME "flutter_assets") +install(CODE " + file(REMOVE_RECURSE \"${INSTALL_BUNDLE_DATA_DIR}/${FLUTTER_ASSET_DIR_NAME}\") + " COMPONENT Runtime) +install(DIRECTORY "${PROJECT_BUILD_DIR}/${FLUTTER_ASSET_DIR_NAME}" + DESTINATION "${INSTALL_BUNDLE_DATA_DIR}" COMPONENT Runtime) + +# Install the AOT library on non-Debug builds only. +install(FILES "${AOT_LIBRARY}" DESTINATION "${INSTALL_BUNDLE_DATA_DIR}" + CONFIGURATIONS Profile;Release + COMPONENT Runtime) diff --git a/windows/flutter/CMakeLists.txt b/windows/flutter/CMakeLists.txt new file mode 100644 index 0000000..903f489 --- /dev/null +++ b/windows/flutter/CMakeLists.txt @@ -0,0 +1,109 @@ +# This file controls Flutter-level build steps. It should not be edited. +cmake_minimum_required(VERSION 3.14) + +set(EPHEMERAL_DIR "${CMAKE_CURRENT_SOURCE_DIR}/ephemeral") + +# Configuration provided via flutter tool. +include(${EPHEMERAL_DIR}/generated_config.cmake) + +# TODO: Move the rest of this into files in ephemeral. See +# https://github.com/flutter/flutter/issues/57146. +set(WRAPPER_ROOT "${EPHEMERAL_DIR}/cpp_client_wrapper") + +# Set fallback configurations for older versions of the flutter tool. +if (NOT DEFINED FLUTTER_TARGET_PLATFORM) + set(FLUTTER_TARGET_PLATFORM "windows-x64") +endif() + +# === Flutter Library === +set(FLUTTER_LIBRARY "${EPHEMERAL_DIR}/flutter_windows.dll") + +# Published to parent scope for install step. +set(FLUTTER_LIBRARY ${FLUTTER_LIBRARY} PARENT_SCOPE) +set(FLUTTER_ICU_DATA_FILE "${EPHEMERAL_DIR}/icudtl.dat" PARENT_SCOPE) +set(PROJECT_BUILD_DIR "${PROJECT_DIR}/build/" PARENT_SCOPE) +set(AOT_LIBRARY "${PROJECT_DIR}/build/windows/app.so" PARENT_SCOPE) + +list(APPEND FLUTTER_LIBRARY_HEADERS + "flutter_export.h" + "flutter_windows.h" + "flutter_messenger.h" + "flutter_plugin_registrar.h" + "flutter_texture_registrar.h" +) +list(TRANSFORM FLUTTER_LIBRARY_HEADERS PREPEND "${EPHEMERAL_DIR}/") +add_library(flutter INTERFACE) +target_include_directories(flutter INTERFACE + "${EPHEMERAL_DIR}" +) +target_link_libraries(flutter INTERFACE "${FLUTTER_LIBRARY}.lib") +add_dependencies(flutter flutter_assemble) + +# === Wrapper === +list(APPEND CPP_WRAPPER_SOURCES_CORE + "core_implementations.cc" + "standard_codec.cc" +) +list(TRANSFORM CPP_WRAPPER_SOURCES_CORE PREPEND "${WRAPPER_ROOT}/") +list(APPEND CPP_WRAPPER_SOURCES_PLUGIN + "plugin_registrar.cc" +) +list(TRANSFORM CPP_WRAPPER_SOURCES_PLUGIN PREPEND "${WRAPPER_ROOT}/") +list(APPEND CPP_WRAPPER_SOURCES_APP + "flutter_engine.cc" + "flutter_view_controller.cc" +) +list(TRANSFORM CPP_WRAPPER_SOURCES_APP PREPEND "${WRAPPER_ROOT}/") + +# Wrapper sources needed for a plugin. +add_library(flutter_wrapper_plugin STATIC + ${CPP_WRAPPER_SOURCES_CORE} + ${CPP_WRAPPER_SOURCES_PLUGIN} +) +apply_standard_settings(flutter_wrapper_plugin) +set_target_properties(flutter_wrapper_plugin PROPERTIES + POSITION_INDEPENDENT_CODE ON) +set_target_properties(flutter_wrapper_plugin PROPERTIES + CXX_VISIBILITY_PRESET hidden) +target_link_libraries(flutter_wrapper_plugin PUBLIC flutter) +target_include_directories(flutter_wrapper_plugin PUBLIC + "${WRAPPER_ROOT}/include" +) +add_dependencies(flutter_wrapper_plugin flutter_assemble) + +# Wrapper sources needed for the runner. +add_library(flutter_wrapper_app STATIC + ${CPP_WRAPPER_SOURCES_CORE} + ${CPP_WRAPPER_SOURCES_APP} +) +apply_standard_settings(flutter_wrapper_app) +target_link_libraries(flutter_wrapper_app PUBLIC flutter) +target_include_directories(flutter_wrapper_app PUBLIC + "${WRAPPER_ROOT}/include" +) +add_dependencies(flutter_wrapper_app flutter_assemble) + +# === Flutter tool backend === +# _phony_ is a non-existent file to force this command to run every time, +# since currently there's no way to get a full input/output list from the +# flutter tool. +set(PHONY_OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/_phony_") +set_source_files_properties("${PHONY_OUTPUT}" PROPERTIES SYMBOLIC TRUE) +add_custom_command( + OUTPUT ${FLUTTER_LIBRARY} ${FLUTTER_LIBRARY_HEADERS} + ${CPP_WRAPPER_SOURCES_CORE} ${CPP_WRAPPER_SOURCES_PLUGIN} + ${CPP_WRAPPER_SOURCES_APP} + ${PHONY_OUTPUT} + COMMAND ${CMAKE_COMMAND} -E env + ${FLUTTER_TOOL_ENVIRONMENT} + "${FLUTTER_ROOT}/packages/flutter_tools/bin/tool_backend.bat" + ${FLUTTER_TARGET_PLATFORM} $ + VERBATIM +) +add_custom_target(flutter_assemble DEPENDS + "${FLUTTER_LIBRARY}" + ${FLUTTER_LIBRARY_HEADERS} + ${CPP_WRAPPER_SOURCES_CORE} + ${CPP_WRAPPER_SOURCES_PLUGIN} + ${CPP_WRAPPER_SOURCES_APP} +) diff --git a/windows/flutter/generated_plugin_registrant.cc b/windows/flutter/generated_plugin_registrant.cc new file mode 100644 index 0000000..8d54613 --- /dev/null +++ b/windows/flutter/generated_plugin_registrant.cc @@ -0,0 +1,20 @@ +// +// Generated file. Do not edit. +// + +// clang-format off + +#include "generated_plugin_registrant.h" + +#include +#include +#include + +void RegisterPlugins(flutter::PluginRegistry* registry) { + EmojiPickerFlutterPluginCApiRegisterWithRegistrar( + registry->GetRegistrarForPlugin("EmojiPickerFlutterPluginCApi")); + FlutterSecureStorageWindowsPluginRegisterWithRegistrar( + registry->GetRegistrarForPlugin("FlutterSecureStorageWindowsPlugin")); + PermissionHandlerWindowsPluginRegisterWithRegistrar( + registry->GetRegistrarForPlugin("PermissionHandlerWindowsPlugin")); +} diff --git a/windows/flutter/generated_plugin_registrant.h b/windows/flutter/generated_plugin_registrant.h new file mode 100644 index 0000000..dc139d8 --- /dev/null +++ b/windows/flutter/generated_plugin_registrant.h @@ -0,0 +1,15 @@ +// +// Generated file. Do not edit. +// + +// clang-format off + +#ifndef GENERATED_PLUGIN_REGISTRANT_ +#define GENERATED_PLUGIN_REGISTRANT_ + +#include + +// Registers Flutter plugins. +void RegisterPlugins(flutter::PluginRegistry* registry); + +#endif // GENERATED_PLUGIN_REGISTRANT_ diff --git a/windows/flutter/generated_plugins.cmake b/windows/flutter/generated_plugins.cmake new file mode 100644 index 0000000..138b578 --- /dev/null +++ b/windows/flutter/generated_plugins.cmake @@ -0,0 +1,26 @@ +# +# Generated file, do not edit. +# + +list(APPEND FLUTTER_PLUGIN_LIST + emoji_picker_flutter + flutter_secure_storage_windows + permission_handler_windows +) + +list(APPEND FLUTTER_FFI_PLUGIN_LIST +) + +set(PLUGIN_BUNDLED_LIBRARIES) + +foreach(plugin ${FLUTTER_PLUGIN_LIST}) + add_subdirectory(flutter/ephemeral/.plugin_symlinks/${plugin}/windows plugins/${plugin}) + target_link_libraries(${BINARY_NAME} PRIVATE ${plugin}_plugin) + list(APPEND PLUGIN_BUNDLED_LIBRARIES $) + list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${plugin}_bundled_libraries}) +endforeach(plugin) + +foreach(ffi_plugin ${FLUTTER_FFI_PLUGIN_LIST}) + add_subdirectory(flutter/ephemeral/.plugin_symlinks/${ffi_plugin}/windows plugins/${ffi_plugin}) + list(APPEND PLUGIN_BUNDLED_LIBRARIES ${${ffi_plugin}_bundled_libraries}) +endforeach(ffi_plugin) diff --git a/windows/runner/CMakeLists.txt b/windows/runner/CMakeLists.txt new file mode 100644 index 0000000..394917c --- /dev/null +++ b/windows/runner/CMakeLists.txt @@ -0,0 +1,40 @@ +cmake_minimum_required(VERSION 3.14) +project(runner LANGUAGES CXX) + +# Define the application target. To change its name, change BINARY_NAME in the +# top-level CMakeLists.txt, not the value here, or `flutter run` will no longer +# work. +# +# Any new source files that you add to the application should be added here. +add_executable(${BINARY_NAME} WIN32 + "flutter_window.cpp" + "main.cpp" + "utils.cpp" + "win32_window.cpp" + "${FLUTTER_MANAGED_DIR}/generated_plugin_registrant.cc" + "Runner.rc" + "runner.exe.manifest" +) + +# Apply the standard set of build settings. This can be removed for applications +# that need different build settings. +apply_standard_settings(${BINARY_NAME}) + +# Add preprocessor definitions for the build version. +target_compile_definitions(${BINARY_NAME} PRIVATE "FLUTTER_VERSION=\"${FLUTTER_VERSION}\"") +target_compile_definitions(${BINARY_NAME} PRIVATE "FLUTTER_VERSION_MAJOR=${FLUTTER_VERSION_MAJOR}") +target_compile_definitions(${BINARY_NAME} PRIVATE "FLUTTER_VERSION_MINOR=${FLUTTER_VERSION_MINOR}") +target_compile_definitions(${BINARY_NAME} PRIVATE "FLUTTER_VERSION_PATCH=${FLUTTER_VERSION_PATCH}") +target_compile_definitions(${BINARY_NAME} PRIVATE "FLUTTER_VERSION_BUILD=${FLUTTER_VERSION_BUILD}") + +# Disable Windows macros that collide with C++ standard library functions. +target_compile_definitions(${BINARY_NAME} PRIVATE "NOMINMAX") + +# Add dependency libraries and include directories. Add any application-specific +# dependencies here. +target_link_libraries(${BINARY_NAME} PRIVATE flutter flutter_wrapper_app) +target_link_libraries(${BINARY_NAME} PRIVATE "dwmapi.lib") +target_include_directories(${BINARY_NAME} PRIVATE "${CMAKE_SOURCE_DIR}") + +# Run the Flutter tool portions of the build. This must not be removed. +add_dependencies(${BINARY_NAME} flutter_assemble) diff --git a/windows/runner/Runner.rc b/windows/runner/Runner.rc new file mode 100644 index 0000000..5cd677d --- /dev/null +++ b/windows/runner/Runner.rc @@ -0,0 +1,121 @@ +// Microsoft Visual C++ generated resource script. +// +#pragma code_page(65001) +#include "resource.h" + +#define APSTUDIO_READONLY_SYMBOLS +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 2 resource. +// +#include "winres.h" + +///////////////////////////////////////////////////////////////////////////// +#undef APSTUDIO_READONLY_SYMBOLS + +///////////////////////////////////////////////////////////////////////////// +// English (United States) resources + +#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) +LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US + +#ifdef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// TEXTINCLUDE +// + +1 TEXTINCLUDE +BEGIN + "resource.h\0" +END + +2 TEXTINCLUDE +BEGIN + "#include ""winres.h""\r\n" + "\0" +END + +3 TEXTINCLUDE +BEGIN + "\r\n" + "\0" +END + +#endif // APSTUDIO_INVOKED + + +///////////////////////////////////////////////////////////////////////////// +// +// Icon +// + +// Icon with lowest ID value placed first to ensure application icon +// remains consistent on all systems. +IDI_APP_ICON ICON "resources\\app_icon.ico" + + +///////////////////////////////////////////////////////////////////////////// +// +// Version +// + +#if defined(FLUTTER_VERSION_MAJOR) && defined(FLUTTER_VERSION_MINOR) && defined(FLUTTER_VERSION_PATCH) && defined(FLUTTER_VERSION_BUILD) +#define VERSION_AS_NUMBER FLUTTER_VERSION_MAJOR,FLUTTER_VERSION_MINOR,FLUTTER_VERSION_PATCH,FLUTTER_VERSION_BUILD +#else +#define VERSION_AS_NUMBER 1,0,0,0 +#endif + +#if defined(FLUTTER_VERSION) +#define VERSION_AS_STRING FLUTTER_VERSION +#else +#define VERSION_AS_STRING "1.0.0" +#endif + +VS_VERSION_INFO VERSIONINFO + FILEVERSION VERSION_AS_NUMBER + PRODUCTVERSION VERSION_AS_NUMBER + FILEFLAGSMASK VS_FFI_FILEFLAGSMASK +#ifdef _DEBUG + FILEFLAGS VS_FF_DEBUG +#else + FILEFLAGS 0x0L +#endif + FILEOS VOS__WINDOWS32 + FILETYPE VFT_APP + FILESUBTYPE 0x0L +BEGIN + BLOCK "StringFileInfo" + BEGIN + BLOCK "040904e4" + BEGIN + VALUE "CompanyName", "com.example" "\0" + VALUE "FileDescription", "connect" "\0" + VALUE "FileVersion", VERSION_AS_STRING "\0" + VALUE "InternalName", "connect" "\0" + VALUE "LegalCopyright", "Copyright (C) 2024 com.example. All rights reserved." "\0" + VALUE "OriginalFilename", "connect.exe" "\0" + VALUE "ProductName", "connect" "\0" + VALUE "ProductVersion", VERSION_AS_STRING "\0" + END + END + BLOCK "VarFileInfo" + BEGIN + VALUE "Translation", 0x409, 1252 + END +END + +#endif // English (United States) resources +///////////////////////////////////////////////////////////////////////////// + + + +#ifndef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 3 resource. +// + + +///////////////////////////////////////////////////////////////////////////// +#endif // not APSTUDIO_INVOKED diff --git a/windows/runner/flutter_window.cpp b/windows/runner/flutter_window.cpp new file mode 100644 index 0000000..955ee30 --- /dev/null +++ b/windows/runner/flutter_window.cpp @@ -0,0 +1,71 @@ +#include "flutter_window.h" + +#include + +#include "flutter/generated_plugin_registrant.h" + +FlutterWindow::FlutterWindow(const flutter::DartProject& project) + : project_(project) {} + +FlutterWindow::~FlutterWindow() {} + +bool FlutterWindow::OnCreate() { + if (!Win32Window::OnCreate()) { + return false; + } + + RECT frame = GetClientArea(); + + // The size here must match the window dimensions to avoid unnecessary surface + // creation / destruction in the startup path. + flutter_controller_ = std::make_unique( + frame.right - frame.left, frame.bottom - frame.top, project_); + // Ensure that basic setup of the controller was successful. + if (!flutter_controller_->engine() || !flutter_controller_->view()) { + return false; + } + RegisterPlugins(flutter_controller_->engine()); + SetChildContent(flutter_controller_->view()->GetNativeWindow()); + + flutter_controller_->engine()->SetNextFrameCallback([&]() { + this->Show(); + }); + + // Flutter can complete the first frame before the "show window" callback is + // registered. The following call ensures a frame is pending to ensure the + // window is shown. It is a no-op if the first frame hasn't completed yet. + flutter_controller_->ForceRedraw(); + + return true; +} + +void FlutterWindow::OnDestroy() { + if (flutter_controller_) { + flutter_controller_ = nullptr; + } + + Win32Window::OnDestroy(); +} + +LRESULT +FlutterWindow::MessageHandler(HWND hwnd, UINT const message, + WPARAM const wparam, + LPARAM const lparam) noexcept { + // Give Flutter, including plugins, an opportunity to handle window messages. + if (flutter_controller_) { + std::optional result = + flutter_controller_->HandleTopLevelWindowProc(hwnd, message, wparam, + lparam); + if (result) { + return *result; + } + } + + switch (message) { + case WM_FONTCHANGE: + flutter_controller_->engine()->ReloadSystemFonts(); + break; + } + + return Win32Window::MessageHandler(hwnd, message, wparam, lparam); +} diff --git a/windows/runner/flutter_window.h b/windows/runner/flutter_window.h new file mode 100644 index 0000000..6da0652 --- /dev/null +++ b/windows/runner/flutter_window.h @@ -0,0 +1,33 @@ +#ifndef RUNNER_FLUTTER_WINDOW_H_ +#define RUNNER_FLUTTER_WINDOW_H_ + +#include +#include + +#include + +#include "win32_window.h" + +// A window that does nothing but host a Flutter view. +class FlutterWindow : public Win32Window { + public: + // Creates a new FlutterWindow hosting a Flutter view running |project|. + explicit FlutterWindow(const flutter::DartProject& project); + virtual ~FlutterWindow(); + + protected: + // Win32Window: + bool OnCreate() override; + void OnDestroy() override; + LRESULT MessageHandler(HWND window, UINT const message, WPARAM const wparam, + LPARAM const lparam) noexcept override; + + private: + // The project to run. + flutter::DartProject project_; + + // The Flutter instance hosted by this window. + std::unique_ptr flutter_controller_; +}; + +#endif // RUNNER_FLUTTER_WINDOW_H_ diff --git a/windows/runner/main.cpp b/windows/runner/main.cpp new file mode 100644 index 0000000..e5e5d90 --- /dev/null +++ b/windows/runner/main.cpp @@ -0,0 +1,43 @@ +#include +#include +#include + +#include "flutter_window.h" +#include "utils.h" + +int APIENTRY wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev, + _In_ wchar_t *command_line, _In_ int show_command) { + // Attach to console when present (e.g., 'flutter run') or create a + // new console when running with a debugger. + if (!::AttachConsole(ATTACH_PARENT_PROCESS) && ::IsDebuggerPresent()) { + CreateAndAttachConsole(); + } + + // Initialize COM, so that it is available for use in the library and/or + // plugins. + ::CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED); + + flutter::DartProject project(L"data"); + + std::vector command_line_arguments = + GetCommandLineArguments(); + + project.set_dart_entrypoint_arguments(std::move(command_line_arguments)); + + FlutterWindow window(project); + Win32Window::Point origin(10, 10); + Win32Window::Size size(1280, 720); + if (!window.Create(L"connect", origin, size)) { + return EXIT_FAILURE; + } + window.SetQuitOnClose(true); + + ::MSG msg; + while (::GetMessage(&msg, nullptr, 0, 0)) { + ::TranslateMessage(&msg); + ::DispatchMessage(&msg); + } + + ::CoUninitialize(); + return EXIT_SUCCESS; +} diff --git a/windows/runner/resource.h b/windows/runner/resource.h new file mode 100644 index 0000000..66a65d1 --- /dev/null +++ b/windows/runner/resource.h @@ -0,0 +1,16 @@ +//{{NO_DEPENDENCIES}} +// Microsoft Visual C++ generated include file. +// Used by Runner.rc +// +#define IDI_APP_ICON 101 + +// Next default values for new objects +// +#ifdef APSTUDIO_INVOKED +#ifndef APSTUDIO_READONLY_SYMBOLS +#define _APS_NEXT_RESOURCE_VALUE 102 +#define _APS_NEXT_COMMAND_VALUE 40001 +#define _APS_NEXT_CONTROL_VALUE 1001 +#define _APS_NEXT_SYMED_VALUE 101 +#endif +#endif diff --git a/windows/runner/resources/app_icon.ico b/windows/runner/resources/app_icon.ico new file mode 100644 index 0000000000000000000000000000000000000000..c04e20caf6370ebb9253ad831cc31de4a9c965f6 GIT binary patch literal 33772 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 literal 0 HcmV?d00001 diff --git a/windows/runner/runner.exe.manifest b/windows/runner/runner.exe.manifest new file mode 100644 index 0000000..153653e --- /dev/null +++ b/windows/runner/runner.exe.manifest @@ -0,0 +1,14 @@ + + + + + PerMonitorV2 + + + + + + + + + diff --git a/windows/runner/utils.cpp b/windows/runner/utils.cpp new file mode 100644 index 0000000..3a0b465 --- /dev/null +++ b/windows/runner/utils.cpp @@ -0,0 +1,65 @@ +#include "utils.h" + +#include +#include +#include +#include + +#include + +void CreateAndAttachConsole() { + if (::AllocConsole()) { + FILE *unused; + if (freopen_s(&unused, "CONOUT$", "w", stdout)) { + _dup2(_fileno(stdout), 1); + } + if (freopen_s(&unused, "CONOUT$", "w", stderr)) { + _dup2(_fileno(stdout), 2); + } + std::ios::sync_with_stdio(); + FlutterDesktopResyncOutputStreams(); + } +} + +std::vector GetCommandLineArguments() { + // Convert the UTF-16 command line arguments to UTF-8 for the Engine to use. + int argc; + wchar_t** argv = ::CommandLineToArgvW(::GetCommandLineW(), &argc); + if (argv == nullptr) { + return std::vector(); + } + + std::vector command_line_arguments; + + // Skip the first argument as it's the binary name. + for (int i = 1; i < argc; i++) { + command_line_arguments.push_back(Utf8FromUtf16(argv[i])); + } + + ::LocalFree(argv); + + return command_line_arguments; +} + +std::string Utf8FromUtf16(const wchar_t* utf16_string) { + if (utf16_string == nullptr) { + return std::string(); + } + unsigned int target_length = ::WideCharToMultiByte( + CP_UTF8, WC_ERR_INVALID_CHARS, utf16_string, + -1, nullptr, 0, nullptr, nullptr) + -1; // remove the trailing null character + int input_length = (int)wcslen(utf16_string); + std::string utf8_string; + if (target_length == 0 || target_length > utf8_string.max_size()) { + return utf8_string; + } + utf8_string.resize(target_length); + int converted_length = ::WideCharToMultiByte( + CP_UTF8, WC_ERR_INVALID_CHARS, utf16_string, + input_length, utf8_string.data(), target_length, nullptr, nullptr); + if (converted_length == 0) { + return std::string(); + } + return utf8_string; +} diff --git a/windows/runner/utils.h b/windows/runner/utils.h new file mode 100644 index 0000000..3879d54 --- /dev/null +++ b/windows/runner/utils.h @@ -0,0 +1,19 @@ +#ifndef RUNNER_UTILS_H_ +#define RUNNER_UTILS_H_ + +#include +#include + +// Creates a console for the process, and redirects stdout and stderr to +// it for both the runner and the Flutter library. +void CreateAndAttachConsole(); + +// Takes a null-terminated wchar_t* encoded in UTF-16 and returns a std::string +// encoded in UTF-8. Returns an empty std::string on failure. +std::string Utf8FromUtf16(const wchar_t* utf16_string); + +// Gets the command line arguments passed in as a std::vector, +// encoded in UTF-8. Returns an empty std::vector on failure. +std::vector GetCommandLineArguments(); + +#endif // RUNNER_UTILS_H_ diff --git a/windows/runner/win32_window.cpp b/windows/runner/win32_window.cpp new file mode 100644 index 0000000..60608d0 --- /dev/null +++ b/windows/runner/win32_window.cpp @@ -0,0 +1,288 @@ +#include "win32_window.h" + +#include +#include + +#include "resource.h" + +namespace { + +/// Window attribute that enables dark mode window decorations. +/// +/// Redefined in case the developer's machine has a Windows SDK older than +/// version 10.0.22000.0. +/// See: https://docs.microsoft.com/windows/win32/api/dwmapi/ne-dwmapi-dwmwindowattribute +#ifndef DWMWA_USE_IMMERSIVE_DARK_MODE +#define DWMWA_USE_IMMERSIVE_DARK_MODE 20 +#endif + +constexpr const wchar_t kWindowClassName[] = L"FLUTTER_RUNNER_WIN32_WINDOW"; + +/// Registry key for app theme preference. +/// +/// A value of 0 indicates apps should use dark mode. A non-zero or missing +/// value indicates apps should use light mode. +constexpr const wchar_t kGetPreferredBrightnessRegKey[] = + L"Software\\Microsoft\\Windows\\CurrentVersion\\Themes\\Personalize"; +constexpr const wchar_t kGetPreferredBrightnessRegValue[] = L"AppsUseLightTheme"; + +// The number of Win32Window objects that currently exist. +static int g_active_window_count = 0; + +using EnableNonClientDpiScaling = BOOL __stdcall(HWND hwnd); + +// Scale helper to convert logical scaler values to physical using passed in +// scale factor +int Scale(int source, double scale_factor) { + return static_cast(source * scale_factor); +} + +// Dynamically loads the |EnableNonClientDpiScaling| from the User32 module. +// This API is only needed for PerMonitor V1 awareness mode. +void EnableFullDpiSupportIfAvailable(HWND hwnd) { + HMODULE user32_module = LoadLibraryA("User32.dll"); + if (!user32_module) { + return; + } + auto enable_non_client_dpi_scaling = + reinterpret_cast( + GetProcAddress(user32_module, "EnableNonClientDpiScaling")); + if (enable_non_client_dpi_scaling != nullptr) { + enable_non_client_dpi_scaling(hwnd); + } + FreeLibrary(user32_module); +} + +} // namespace + +// Manages the Win32Window's window class registration. +class WindowClassRegistrar { + public: + ~WindowClassRegistrar() = default; + + // Returns the singleton registrar instance. + static WindowClassRegistrar* GetInstance() { + if (!instance_) { + instance_ = new WindowClassRegistrar(); + } + return instance_; + } + + // Returns the name of the window class, registering the class if it hasn't + // previously been registered. + const wchar_t* GetWindowClass(); + + // Unregisters the window class. Should only be called if there are no + // instances of the window. + void UnregisterWindowClass(); + + private: + WindowClassRegistrar() = default; + + static WindowClassRegistrar* instance_; + + bool class_registered_ = false; +}; + +WindowClassRegistrar* WindowClassRegistrar::instance_ = nullptr; + +const wchar_t* WindowClassRegistrar::GetWindowClass() { + if (!class_registered_) { + WNDCLASS window_class{}; + window_class.hCursor = LoadCursor(nullptr, IDC_ARROW); + window_class.lpszClassName = kWindowClassName; + window_class.style = CS_HREDRAW | CS_VREDRAW; + window_class.cbClsExtra = 0; + window_class.cbWndExtra = 0; + window_class.hInstance = GetModuleHandle(nullptr); + window_class.hIcon = + LoadIcon(window_class.hInstance, MAKEINTRESOURCE(IDI_APP_ICON)); + window_class.hbrBackground = 0; + window_class.lpszMenuName = nullptr; + window_class.lpfnWndProc = Win32Window::WndProc; + RegisterClass(&window_class); + class_registered_ = true; + } + return kWindowClassName; +} + +void WindowClassRegistrar::UnregisterWindowClass() { + UnregisterClass(kWindowClassName, nullptr); + class_registered_ = false; +} + +Win32Window::Win32Window() { + ++g_active_window_count; +} + +Win32Window::~Win32Window() { + --g_active_window_count; + Destroy(); +} + +bool Win32Window::Create(const std::wstring& title, + const Point& origin, + const Size& size) { + Destroy(); + + const wchar_t* window_class = + WindowClassRegistrar::GetInstance()->GetWindowClass(); + + const POINT target_point = {static_cast(origin.x), + static_cast(origin.y)}; + HMONITOR monitor = MonitorFromPoint(target_point, MONITOR_DEFAULTTONEAREST); + UINT dpi = FlutterDesktopGetDpiForMonitor(monitor); + double scale_factor = dpi / 96.0; + + HWND window = CreateWindow( + window_class, title.c_str(), WS_OVERLAPPEDWINDOW, + Scale(origin.x, scale_factor), Scale(origin.y, scale_factor), + Scale(size.width, scale_factor), Scale(size.height, scale_factor), + nullptr, nullptr, GetModuleHandle(nullptr), this); + + if (!window) { + return false; + } + + UpdateTheme(window); + + return OnCreate(); +} + +bool Win32Window::Show() { + return ShowWindow(window_handle_, SW_SHOWNORMAL); +} + +// static +LRESULT CALLBACK Win32Window::WndProc(HWND const window, + UINT const message, + WPARAM const wparam, + LPARAM const lparam) noexcept { + if (message == WM_NCCREATE) { + auto window_struct = reinterpret_cast(lparam); + SetWindowLongPtr(window, GWLP_USERDATA, + reinterpret_cast(window_struct->lpCreateParams)); + + auto that = static_cast(window_struct->lpCreateParams); + EnableFullDpiSupportIfAvailable(window); + that->window_handle_ = window; + } else if (Win32Window* that = GetThisFromHandle(window)) { + return that->MessageHandler(window, message, wparam, lparam); + } + + return DefWindowProc(window, message, wparam, lparam); +} + +LRESULT +Win32Window::MessageHandler(HWND hwnd, + UINT const message, + WPARAM const wparam, + LPARAM const lparam) noexcept { + switch (message) { + case WM_DESTROY: + window_handle_ = nullptr; + Destroy(); + if (quit_on_close_) { + PostQuitMessage(0); + } + return 0; + + case WM_DPICHANGED: { + auto newRectSize = reinterpret_cast(lparam); + LONG newWidth = newRectSize->right - newRectSize->left; + LONG newHeight = newRectSize->bottom - newRectSize->top; + + SetWindowPos(hwnd, nullptr, newRectSize->left, newRectSize->top, newWidth, + newHeight, SWP_NOZORDER | SWP_NOACTIVATE); + + return 0; + } + case WM_SIZE: { + RECT rect = GetClientArea(); + if (child_content_ != nullptr) { + // Size and position the child window. + MoveWindow(child_content_, rect.left, rect.top, rect.right - rect.left, + rect.bottom - rect.top, TRUE); + } + return 0; + } + + case WM_ACTIVATE: + if (child_content_ != nullptr) { + SetFocus(child_content_); + } + return 0; + + case WM_DWMCOLORIZATIONCOLORCHANGED: + UpdateTheme(hwnd); + return 0; + } + + return DefWindowProc(window_handle_, message, wparam, lparam); +} + +void Win32Window::Destroy() { + OnDestroy(); + + if (window_handle_) { + DestroyWindow(window_handle_); + window_handle_ = nullptr; + } + if (g_active_window_count == 0) { + WindowClassRegistrar::GetInstance()->UnregisterWindowClass(); + } +} + +Win32Window* Win32Window::GetThisFromHandle(HWND const window) noexcept { + return reinterpret_cast( + GetWindowLongPtr(window, GWLP_USERDATA)); +} + +void Win32Window::SetChildContent(HWND content) { + child_content_ = content; + SetParent(content, window_handle_); + RECT frame = GetClientArea(); + + MoveWindow(content, frame.left, frame.top, frame.right - frame.left, + frame.bottom - frame.top, true); + + SetFocus(child_content_); +} + +RECT Win32Window::GetClientArea() { + RECT frame; + GetClientRect(window_handle_, &frame); + return frame; +} + +HWND Win32Window::GetHandle() { + return window_handle_; +} + +void Win32Window::SetQuitOnClose(bool quit_on_close) { + quit_on_close_ = quit_on_close; +} + +bool Win32Window::OnCreate() { + // No-op; provided for subclasses. + return true; +} + +void Win32Window::OnDestroy() { + // No-op; provided for subclasses. +} + +void Win32Window::UpdateTheme(HWND const window) { + DWORD light_mode; + DWORD light_mode_size = sizeof(light_mode); + LSTATUS result = RegGetValue(HKEY_CURRENT_USER, kGetPreferredBrightnessRegKey, + kGetPreferredBrightnessRegValue, + RRF_RT_REG_DWORD, nullptr, &light_mode, + &light_mode_size); + + if (result == ERROR_SUCCESS) { + BOOL enable_dark_mode = light_mode == 0; + DwmSetWindowAttribute(window, DWMWA_USE_IMMERSIVE_DARK_MODE, + &enable_dark_mode, sizeof(enable_dark_mode)); + } +} diff --git a/windows/runner/win32_window.h b/windows/runner/win32_window.h new file mode 100644 index 0000000..e901dde --- /dev/null +++ b/windows/runner/win32_window.h @@ -0,0 +1,102 @@ +#ifndef RUNNER_WIN32_WINDOW_H_ +#define RUNNER_WIN32_WINDOW_H_ + +#include + +#include +#include +#include + +// A class abstraction for a high DPI-aware Win32 Window. Intended to be +// inherited from by classes that wish to specialize with custom +// rendering and input handling +class Win32Window { + public: + struct Point { + unsigned int x; + unsigned int y; + Point(unsigned int x, unsigned int y) : x(x), y(y) {} + }; + + struct Size { + unsigned int width; + unsigned int height; + Size(unsigned int width, unsigned int height) + : width(width), height(height) {} + }; + + Win32Window(); + virtual ~Win32Window(); + + // Creates a win32 window with |title| that is positioned and sized using + // |origin| and |size|. New windows are created on the default monitor. Window + // sizes are specified to the OS in physical pixels, hence to ensure a + // consistent size this function will scale the inputted width and height as + // as appropriate for the default monitor. The window is invisible until + // |Show| is called. Returns true if the window was created successfully. + bool Create(const std::wstring& title, const Point& origin, const Size& size); + + // Show the current window. Returns true if the window was successfully shown. + bool Show(); + + // Release OS resources associated with window. + void Destroy(); + + // Inserts |content| into the window tree. + void SetChildContent(HWND content); + + // Returns the backing Window handle to enable clients to set icon and other + // window properties. Returns nullptr if the window has been destroyed. + HWND GetHandle(); + + // If true, closing this window will quit the application. + void SetQuitOnClose(bool quit_on_close); + + // Return a RECT representing the bounds of the current client area. + RECT GetClientArea(); + + protected: + // Processes and route salient window messages for mouse handling, + // size change and DPI. Delegates handling of these to member overloads that + // inheriting classes can handle. + virtual LRESULT MessageHandler(HWND window, + UINT const message, + WPARAM const wparam, + LPARAM const lparam) noexcept; + + // Called when CreateAndShow is called, allowing subclass window-related + // setup. Subclasses should return false if setup fails. + virtual bool OnCreate(); + + // Called when Destroy is called. + virtual void OnDestroy(); + + private: + friend class WindowClassRegistrar; + + // OS callback called by message pump. Handles the WM_NCCREATE message which + // is passed when the non-client area is being created and enables automatic + // non-client DPI scaling so that the non-client area automatically + // responds to changes in DPI. All other messages are handled by + // MessageHandler. + static LRESULT CALLBACK WndProc(HWND const window, + UINT const message, + WPARAM const wparam, + LPARAM const lparam) noexcept; + + // Retrieves a class instance pointer for |window| + static Win32Window* GetThisFromHandle(HWND const window) noexcept; + + // Update the window frame's theme to match the system theme. + static void UpdateTheme(HWND const window); + + bool quit_on_close_ = false; + + // window handle for top level window. + HWND window_handle_ = nullptr; + + // window handle for hosted content. + HWND child_content_ = nullptr; +}; + +#endif // RUNNER_WIN32_WINDOW_H_