├── .drone.yml ├── .gitattributes ├── .github └── workflows │ ├── issue.yml │ └── pull_request.yml ├── .gitignore ├── .gitlab-ci.yml ├── .metadata ├── .vscode ├── launch.json └── settings.json ├── CHANGELOG.md ├── LICENSE ├── README.md ├── android ├── .classpath ├── .gitignore ├── .settings │ └── org.eclipse.buildship.core.prefs ├── build.gradle ├── build.gradle.tpl ├── gradle.properties ├── gradle │ └── wrapper │ │ └── gradle-wrapper.properties ├── proguard-android.txt ├── proguard-rules.pro ├── settings.gradle └── src │ └── main │ ├── AndroidManifest.xml │ └── java │ └── com │ └── finogeeks │ └── mop │ ├── MopEventStream.java │ ├── MopPlugin.java │ ├── MopPluginDelegate.java │ ├── api │ ├── AbsApi.java │ ├── ApisManager.java │ ├── BaseApi.java │ ├── EmptyApi.java │ └── mop │ │ ├── AppletHandlerModule.java │ │ ├── AppletManageModule.java │ │ ├── AppletModule.java │ │ ├── BaseModule.java │ │ ├── ExtensionApiModule.java │ │ ├── InitSDKModule.java │ │ ├── SmSignModule.java │ │ ├── VersionModule.java │ │ ├── WXQrCodeModule.java │ │ └── util │ │ └── InitUtils.java │ ├── constants │ └── Constants.java │ ├── impls │ └── MyUserProfileHandler.java │ ├── interfaces │ ├── Event.java │ ├── FlutterInterface.java │ ├── IApi.java │ ├── ICallback.java │ └── ILifecycle.java │ ├── service │ └── MopPluginService.java │ └── utils │ ├── AppletUtils.java │ └── GsonUtil.java ├── bundle.sh ├── example ├── .gitignore ├── .metadata ├── README.md ├── analysis_options.yaml ├── android │ ├── .gitignore │ ├── .project │ ├── .settings │ │ └── org.eclipse.buildship.core.prefs │ ├── app │ │ ├── .classpath │ │ ├── .project │ │ ├── .settings │ │ │ └── org.eclipse.buildship.core.prefs │ │ ├── build.gradle │ │ └── src │ │ │ ├── debug │ │ │ └── AndroidManifest.xml │ │ │ ├── main │ │ │ ├── AndroidManifest.xml │ │ │ ├── java │ │ │ │ └── com │ │ │ │ │ └── finogeeks │ │ │ │ │ └── mop_example │ │ │ │ │ ├── CustomLoadingPage.java │ │ │ │ │ ├── MainActivity.java │ │ │ │ │ └── MainApplication.java │ │ │ └── res │ │ │ │ ├── drawable-v21 │ │ │ │ └── launch_background.xml │ │ │ │ ├── drawable │ │ │ │ └── launch_background.xml │ │ │ │ ├── layout │ │ │ │ ├── layout_custom_loading_page.xml │ │ │ │ └── layout_custom_loading_page_failure.xml │ │ │ │ ├── mipmap-hdpi │ │ │ │ └── ic_launcher.png │ │ │ │ ├── mipmap-mdpi │ │ │ │ └── ic_launcher.png │ │ │ │ ├── mipmap-xhdpi │ │ │ │ └── ic_launcher.png │ │ │ │ ├── mipmap-xxhdpi │ │ │ │ └── ic_launcher.png │ │ │ │ ├── mipmap-xxxhdpi │ │ │ │ └── ic_launcher.png │ │ │ │ ├── values-night │ │ │ │ └── styles.xml │ │ │ │ └── values │ │ │ │ └── styles.xml │ │ │ └── profile │ │ │ └── AndroidManifest.xml │ ├── build.gradle │ ├── gradle.properties │ ├── gradle │ │ └── wrapper │ │ │ └── gradle-wrapper.properties │ └── settings.gradle ├── ios │ ├── .gitignore │ ├── Flutter │ │ ├── AppFrameworkInfo.plist │ │ ├── Debug.xcconfig │ │ └── Release.xcconfig │ ├── Podfile │ ├── Podfile.lock │ ├── Runner.xcodeproj │ │ ├── project.pbxproj │ │ ├── project.xcworkspace │ │ │ ├── contents.xcworkspacedata │ │ │ └── xcshareddata │ │ │ │ ├── IDEWorkspaceChecks.plist │ │ │ │ └── WorkspaceSettings.xcsettings │ │ └── xcshareddata │ │ │ └── xcschemes │ │ │ └── Runner.xcscheme │ ├── Runner.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ ├── IDEWorkspaceChecks.plist │ │ │ └── WorkspaceSettings.xcsettings │ └── Runner │ │ ├── AppDelegate.swift │ │ ├── Assets.xcassets │ │ ├── AppIcon.appiconset │ │ │ ├── Contents.json │ │ │ ├── Icon-App-1024x1024@1x.png │ │ │ ├── Icon-App-20x20@1x.png │ │ │ ├── Icon-App-20x20@2x.png │ │ │ ├── Icon-App-20x20@3x.png │ │ │ ├── Icon-App-29x29@1x.png │ │ │ ├── Icon-App-29x29@2x.png │ │ │ ├── Icon-App-29x29@3x.png │ │ │ ├── Icon-App-40x40@1x.png │ │ │ ├── Icon-App-40x40@2x.png │ │ │ ├── Icon-App-40x40@3x.png │ │ │ ├── Icon-App-60x60@2x.png │ │ │ ├── Icon-App-60x60@3x.png │ │ │ ├── Icon-App-76x76@1x.png │ │ │ ├── Icon-App-76x76@2x.png │ │ │ └── Icon-App-83.5x83.5@2x.png │ │ ├── Contents.json │ │ ├── LaunchImage.imageset │ │ │ ├── Contents.json │ │ │ ├── LaunchImage.png │ │ │ ├── LaunchImage@2x.png │ │ │ ├── LaunchImage@3x.png │ │ │ └── README.md │ │ ├── minipro_list_collect.imageset │ │ │ ├── Contents.json │ │ │ ├── minipro_list_collect@2x.png │ │ │ └── minipro_list_collect@3x.png │ │ └── minipro_list_service.imageset │ │ │ ├── Contents.json │ │ │ ├── minipro_list_service@2x.png │ │ │ └── minipro_list_service@3x.png │ │ ├── Base.lproj │ │ ├── LaunchScreen.storyboard │ │ └── Main.storyboard │ │ ├── FlutterMethodChannelHandler.h │ │ ├── FlutterMethodChannelHandler.m │ │ ├── Info.plist │ │ ├── LoadingView.h │ │ ├── LoadingView.m │ │ └── Runner-Bridging-Header.h ├── lib │ ├── main.dart │ └── test_page.dart ├── pubspec.lock ├── pubspec.yaml └── test │ └── widget_test.dart ├── ios ├── .gitignore ├── Assets │ └── .gitkeep ├── Classes │ ├── Api │ │ ├── MOPAppletDelegate.h │ │ ├── MOPAppletDelegate.m │ │ ├── MOPButtonOpenTypeDelegate.h │ │ ├── MOPButtonOpenTypeDelegate.m │ │ ├── MOP_addWebExtentionApi.h │ │ ├── MOP_addWebExtentionApi.m │ │ ├── MOP_callJS.h │ │ ├── MOP_callJS.m │ │ ├── MOP_changeUserId.h │ │ ├── MOP_changeUserId.m │ │ ├── MOP_clearApplets.h │ │ ├── MOP_clearApplets.m │ │ ├── MOP_closeAllApplets.h │ │ ├── MOP_closeAllApplets.m │ │ ├── MOP_closeApplet.h │ │ ├── MOP_closeApplet.m │ │ ├── MOP_currentApplet.h │ │ ├── MOP_currentApplet.m │ │ ├── MOP_finishRunningApplet.h │ │ ├── MOP_finishRunningApplet.m │ │ ├── MOP_initSDK.h │ │ ├── MOP_initSDK.m │ │ ├── MOP_initialize.h │ │ ├── MOP_initialize.m │ │ ├── MOP_openApplet.h │ │ ├── MOP_openApplet.m │ │ ├── MOP_parseAppletInfoFromWXQrCode.h │ │ ├── MOP_parseAppletInfoFromWXQrCode.m │ │ ├── MOP_qrcodeOpenApplet.h │ │ ├── MOP_qrcodeOpenApplet.m │ │ ├── MOP_registerAppletHandler.h │ │ ├── MOP_registerAppletHandler.m │ │ ├── MOP_registerExtensionApi.h │ │ ├── MOP_registerExtensionApi.m │ │ ├── MOP_removeAllUsedApplets.h │ │ ├── MOP_removeAllUsedApplets.m │ │ ├── MOP_removeApplet.h │ │ ├── MOP_removeApplet.m │ │ ├── MOP_removeUsedApplet.h │ │ ├── MOP_removeUsedApplet.m │ │ ├── MOP_scanOpenApplet.h │ │ ├── MOP_scanOpenApplet.m │ │ ├── MOP_sdkVersion.h │ │ ├── MOP_sdkVersion.m │ │ ├── MOP_sendCustomEvent.h │ │ ├── MOP_sendCustomEvent.m │ │ ├── MOP_setFinStoreConfigs.h │ │ ├── MOP_setFinStoreConfigs.m │ │ ├── MOP_showBotomSheetModel.h │ │ ├── MOP_showBotomSheetModel.m │ │ ├── MOP_smsign.h │ │ ├── MOP_smsign.m │ │ ├── MOP_startApplet.h │ │ ├── MOP_startApplet.m │ │ ├── MOP_webViewBounces.h │ │ └── MOP_webViewBounces.m │ ├── Model │ │ ├── MopCustomMenuModel.h │ │ └── MopCustomMenuModel.m │ ├── MopPlugin.h │ ├── MopPlugin.m │ └── Utils │ │ ├── MOPApiConverter.h │ │ ├── MOPApiConverter.m │ │ ├── MOPApiRequest.h │ │ ├── MOPApiRequest.m │ │ ├── MOPBaseApi.h │ │ ├── MOPBaseApi.m │ │ ├── MOPTools.h │ │ ├── MOPTools.m │ │ ├── MopShareView.h │ │ ├── MopShareView.m │ │ ├── UIView+MOPFATToast.h │ │ └── UIView+MOPFATToast.m ├── mop.podspec └── mop.podspec.tpl ├── lib ├── api.dart └── mop.dart ├── publish.sh ├── pubspec.lock ├── pubspec.tpl.yaml ├── pubspec.yaml ├── tag.sh ├── test └── mop_test.dart ├── trigger.sh └── update_version.sh /.drone.yml: -------------------------------------------------------------------------------- 1 | clone: 2 | git: 3 | image: plugins/git 4 | tags: true 5 | pipeline: 6 | build: 7 | image: docker.finogeeks.club/build/ubuntu-scp 8 | pull: true 9 | commands: 10 | - bash trigger.sh 11 | when: 12 | event: tag 13 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | *.* linguist-language=dart 2 | -------------------------------------------------------------------------------- /.github/workflows/issue.yml: -------------------------------------------------------------------------------- 1 | name: Notify 2 | on: 3 | issues: 4 | types: [opened] 5 | issue_comment: 6 | types: [created] 7 | jobs: 8 | build: 9 | runs-on: ubuntu-latest 10 | steps: 11 | - uses: actions/checkout@v2 12 | - name: Notify 13 | run: curl --location --request POST 'https://api.finogeeks.club/api/v1/finstore/webhooks/61b331d79b3dad0001f72fa2/postreceive?nonce=jhd2QyrArsc' --header "Content-Type:application/json" --data-raw '{"msg":"仓库 ${{github.repository}} 有新的 issue"}' 14 | -------------------------------------------------------------------------------- /.github/workflows/pull_request.yml: -------------------------------------------------------------------------------- 1 | name: Notify 2 | on: 3 | pull_request: 4 | branches: [ master ] 5 | jobs: 6 | build: 7 | runs-on: ubuntu-latest 8 | steps: 9 | - uses: actions/checkout@v2 10 | - name: Notify 11 | run: curl --location --request POST 'https://api.finogeeks.club/api/v1/finstore/webhooks/61b331d79b3dad0001f72fa2/postreceive?nonce=jhd2QyrArsc' --header "Content-Type:application/json" --data-raw '{"msg":"仓库 ${{github.repository}} 有新的 PR ${{ github.event.pull_request._links.html.href }}"}' 12 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .idea 2 | .DS_Store 3 | .dart_tool/ 4 | 5 | .packages 6 | .pub/ 7 | 8 | # Files and directories created by pub 9 | .dart_tool/ 10 | .packages 11 | # If you're building an application, you may want to check-in your pubspec.lock 12 | #pubspec.lock 13 | 14 | # Directory created by dartdoc 15 | # If you don't generate documentation locally you can remove this line. 16 | doc/api/ 17 | 18 | # Avoid committing generated Javascript files: 19 | *.dart.js 20 | *.info.json # Produced by the --dump-info flag. 21 | *.js # When generated by dart2js. Don't specify *.js if your 22 | # project includes source files written in JavaScript. 23 | *.js_ 24 | *.js.deps 25 | *.js.map 26 | **/*.lock 27 | 28 | *.iml 29 | .gradle 30 | /local.properties 31 | /.idea/workspace.xml 32 | /.idea/libraries 33 | .DS_Store 34 | /build 35 | /captures 36 | example/ios/Podfile.lock 37 | example/pubspec.lock 38 | pubspec.lock 39 | 40 | 41 | android/bin/ 42 | android/.project 43 | -------------------------------------------------------------------------------- /.gitlab-ci.yml: -------------------------------------------------------------------------------- 1 | stages: 2 | - build 3 | variables: 4 | LC_ALL: "en_US.UTF-8" 5 | LANG: "en_US.UTF-8" 6 | GITLAB_VERSION: $GITLAB_VERSION 7 | GITLAB_IOS_VERSION: $GITLAB_IOS_VERSION 8 | GITLAB_ANDROID_VERSION: $GITLAB_ANDROID_VERSION 9 | 10 | workflow: 11 | rules: 12 | - if: '$GITLAB_VERSION != null && $GITLAB_VERSION != ""' 13 | - when: never 14 | 15 | build: 16 | stage: build 17 | script: 18 | - | 19 | echo "检查变量值:" 20 | echo "Version: $GITLAB_VERSION" 21 | echo "iOS Version: $GITLAB_IOS_VERSION" 22 | echo "Android Version: $GITLAB_ANDROID_VERSION" 23 | 24 | sh bundle.sh $GITLAB_VERSION $GITLAB_IOS_VERSION $GITLAB_ANDROID_VERSION $CI_COMMIT_REF_NAME 25 | tags: 26 | - mac-studio 27 | only: 28 | - web 29 | - api 30 | - pipelines 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /.metadata: -------------------------------------------------------------------------------- 1 | # This file tracks properties of this Flutter project. 2 | # Used by Flutter tool to assess capabilities and perform upgrades etc. 3 | # 4 | # This file should be version controlled and should not be manually edited. 5 | 6 | version: 7 | revision: 1aedbb1835bd6eb44550293d57d4d124f19901f0 8 | channel: stable 9 | 10 | project_type: plugin 11 | -------------------------------------------------------------------------------- /.vscode/launch.json: -------------------------------------------------------------------------------- 1 | { 2 | // Use IntelliSense to learn about possible attributes. 3 | // Hover to view descriptions of existing attributes. 4 | // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 5 | "version": "0.2.0", 6 | "configurations": [ 7 | { 8 | "name": "Flutter", 9 | "request": "launch", 10 | "type": "dart", 11 | "cwd": "${workspaceFolder}/example" 12 | } 13 | ] 14 | } 15 | -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "java.configuration.updateBuildConfiguration": "interactive" 3 | } -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | ## 2.35.7 2 | Release 3 | ## 2.22.4 4 | Release 5 | ## 2.22.2 6 | Release 7 | ## 2.22.1 8 | Release 9 | ## 2.21.1 10 | Release 11 | ## 2.21.1 12 | Release 13 | ## 14 | Release 15 | ## 2.20.17 16 | Release 17 | ## 1.1.0 18 | Release 19 | ## 1.0.8 20 | Release 21 | ## 1.0.0 22 | Release 23 | ## 0.7.1 24 | 升级版本 25 | ## 0.7.0 26 | 适配运行时新接口 27 | ## 0.6.1 28 | 适配运行时新接口 29 | ## 0.6.0 30 | 增加api接口 31 | ## 0.5.0 32 | ## 0.4.0 33 | 支持小程序最新依赖 34 | ## 0.3.0 35 | ## 0.2.0 36 | 37 | ## 0.1.1 38 | 39 | ## 0.1.0 40 | 41 | * TODO: Describe initial release. 42 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2020 finogeeks 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /android/.classpath: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /android/.gitignore: -------------------------------------------------------------------------------- 1 | *.iml 2 | .gradle 3 | /local.properties 4 | /.idea/workspace.xml 5 | /.idea/libraries 6 | .DS_Store 7 | /build 8 | /captures 9 | -------------------------------------------------------------------------------- /android/.settings/org.eclipse.buildship.core.prefs: -------------------------------------------------------------------------------- 1 | arguments=--init-script /var/folders/tx/98mydjws12b717spn4mx1wd80000gn/T/db3b08fc4a9ef609cb16b96b200fa13e563f396e9bb1ed0905fdab7bc3bc513b.gradle --init-script /var/folders/tx/98mydjws12b717spn4mx1wd80000gn/T/52cde0cfcf3e28b8b7510e992210d9614505e0911af0c190bd590d7158574963.gradle 2 | auto.sync=false 3 | build.scans.enabled=false 4 | connection.gradle.distribution=GRADLE_DISTRIBUTION(WRAPPER) 5 | connection.project.dir= 6 | eclipse.preferences.version=1 7 | gradle.user.home= 8 | java.home=/Library/Java/JavaVirtualMachines/jdk-1.8.jdk/Contents/Home 9 | jvm.arguments= 10 | offline.mode=false 11 | override.workspace.settings=true 12 | show.console.view=true 13 | show.executions.view=true 14 | -------------------------------------------------------------------------------- /android/build.gradle: -------------------------------------------------------------------------------- 1 | 2 | apply plugin: 'com.android.library' 3 | 4 | apply plugin: 'kotlin-android' 5 | apply plugin: 'kotlin-kapt' 6 | apply plugin: 'kotlin-android-extensions' 7 | 8 | group 'com.finogeeks.mop' 9 | version '1.0' 10 | 11 | buildscript { 12 | repositories { 13 | google() 14 | jcenter() 15 | maven { 16 | url "https://gradle.finogeeks.club/repository/finogeeks/" 17 | credentials { 18 | username "finclip" 19 | password "Abcd@@1234" 20 | } 21 | } 22 | maven { 23 | url "https://gradle.finogeeks.club/repository/applet/" 24 | credentials { 25 | username "finclip" 26 | password "Abcd@@1234" 27 | } 28 | } 29 | maven { url "https://jitpack.io" } 30 | 31 | } 32 | 33 | dependencies { 34 | classpath 'com.android.tools.build:gradle:3.5.3' 35 | classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.3.61" 36 | 37 | } 38 | } 39 | 40 | rootProject.allprojects { 41 | repositories { 42 | google() 43 | jcenter() 44 | maven { 45 | url "https://gradle.finogeeks.club/repository/finogeeks/" 46 | credentials { 47 | username "finclip" 48 | password "Abcd@@1234" 49 | } 50 | } 51 | maven { 52 | url "https://gradle.finogeeks.club/repository/applet/" 53 | credentials { 54 | username "finclip" 55 | password "Abcd@@1234" 56 | } 57 | } 58 | maven { url "https://jitpack.io" } 59 | 60 | } 61 | } 62 | 63 | 64 | android { 65 | compileSdkVersion 28 66 | 67 | defaultConfig { 68 | minSdkVersion 21 69 | testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" 70 | } 71 | buildTypes { 72 | release { 73 | minifyEnabled false 74 | proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' 75 | } 76 | } 77 | 78 | compileOptions { 79 | sourceCompatibility JavaVersion.VERSION_1_8 80 | targetCompatibility JavaVersion.VERSION_1_8 81 | } 82 | lintOptions { 83 | disable 'InvalidPackage' 84 | } 85 | } 86 | 87 | kapt { 88 | arguments { 89 | arg("moduleName", project.getName()) 90 | } 91 | } 92 | dependencies { 93 | implementation fileTree(include: ['*.jar'], dir: 'libs') 94 | implementation 'com.finogeeks.lib:finapplet:2.48.7' 95 | implementation 'com.finogeeks.mop:plugins:2.48.7' 96 | } -------------------------------------------------------------------------------- /android/build.gradle.tpl: -------------------------------------------------------------------------------- 1 | 2 | apply plugin: 'com.android.library' 3 | 4 | apply plugin: 'kotlin-android' 5 | apply plugin: 'kotlin-kapt' 6 | apply plugin: 'kotlin-android-extensions' 7 | 8 | group 'com.finogeeks.mop' 9 | version '1.0' 10 | 11 | buildscript { 12 | repositories { 13 | google() 14 | jcenter() 15 | maven { 16 | url "https://gradle.finogeeks.club/repository/finogeeks/" 17 | credentials { 18 | username "finclip" 19 | password "Abcd@@1234" 20 | } 21 | } 22 | maven { 23 | url "https://gradle.finogeeks.club/repository/applet/" 24 | credentials { 25 | username "finclip" 26 | password "Abcd@@1234" 27 | } 28 | } 29 | maven { url "https://jitpack.io" } 30 | 31 | } 32 | 33 | dependencies { 34 | classpath 'com.android.tools.build:gradle:3.5.3' 35 | classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.3.61" 36 | 37 | } 38 | } 39 | 40 | rootProject.allprojects { 41 | repositories { 42 | google() 43 | jcenter() 44 | maven { 45 | url "https://gradle.finogeeks.club/repository/finogeeks/" 46 | credentials { 47 | username "finclip" 48 | password "Abcd@@1234" 49 | } 50 | } 51 | maven { 52 | url "https://gradle.finogeeks.club/repository/applet/" 53 | credentials { 54 | username "finclip" 55 | password "Abcd@@1234" 56 | } 57 | } 58 | maven { url "https://jitpack.io" } 59 | 60 | } 61 | } 62 | 63 | 64 | android { 65 | compileSdkVersion 28 66 | 67 | defaultConfig { 68 | minSdkVersion 21 69 | testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" 70 | } 71 | buildTypes { 72 | release { 73 | minifyEnabled false 74 | proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' 75 | } 76 | } 77 | 78 | compileOptions { 79 | sourceCompatibility JavaVersion.VERSION_1_8 80 | targetCompatibility JavaVersion.VERSION_1_8 81 | } 82 | lintOptions { 83 | disable 'InvalidPackage' 84 | } 85 | } 86 | 87 | kapt { 88 | arguments { 89 | arg("moduleName", project.getName()) 90 | } 91 | } 92 | dependencies { 93 | implementation fileTree(include: ['*.jar'], dir: 'libs') 94 | implementation 'com.finogeeks.lib:finapplet:__finapplet_version__' 95 | implementation 'com.finogeeks.mop:plugins:__finapplet_version__' 96 | } -------------------------------------------------------------------------------- /android/gradle.properties: -------------------------------------------------------------------------------- 1 | org.gradle.jvmargs=-Xmx1536M 2 | android.useAndroidX=true 3 | android.enableJetifier=true 4 | -------------------------------------------------------------------------------- /android/gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | distributionBase=GRADLE_USER_HOME 2 | distributionPath=wrapper/dists 3 | zipStoreBase=GRADLE_USER_HOME 4 | zipStorePath=wrapper/dists 5 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.7-all.zip 6 | -------------------------------------------------------------------------------- /android/proguard-android.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/android/proguard-android.txt -------------------------------------------------------------------------------- /android/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | -keep class com.finogeeks.** {*;} 2 | 3 | # tbs 4 | -keep class com.tencent.smtt.** {*;} 5 | -keep class com.tencent.tbs.** {*;} -------------------------------------------------------------------------------- /android/settings.gradle: -------------------------------------------------------------------------------- 1 | rootProject.name = 'mop' 2 | -------------------------------------------------------------------------------- /android/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 4 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/MopEventStream.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | import io.flutter.plugin.common.EventChannel; 7 | 8 | public class MopEventStream implements EventChannel.StreamHandler { 9 | EventChannel.EventSink mEventSlink; 10 | 11 | @Override 12 | public void onListen(Object o, EventChannel.EventSink eventSink) { 13 | mEventSlink = eventSink; 14 | } 15 | 16 | @Override 17 | public void onCancel(Object o) { 18 | mEventSlink = null; 19 | } 20 | 21 | public void send(String channel, String event, Object body) { 22 | if (mEventSlink != null) { 23 | Map map = new HashMap<>(); 24 | map.put("channel", channel); 25 | map.put("event", event); 26 | map.put("body", body); 27 | mEventSlink.success(map); 28 | } 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/MopPlugin.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop; 2 | 3 | import android.app.Activity; 4 | import android.content.Intent; 5 | import android.util.Log; 6 | import androidx.lifecycle.Lifecycle; 7 | 8 | import com.finogeeks.mop.interfaces.Event; 9 | import com.finogeeks.mop.interfaces.FlutterInterface; 10 | import com.finogeeks.mop.interfaces.ICallback; 11 | import com.finogeeks.mop.service.MopPluginService; 12 | 13 | import java.util.HashMap; 14 | import java.util.Map; 15 | 16 | import io.flutter.embedding.engine.plugins.FlutterPlugin; 17 | import io.flutter.embedding.engine.plugins.activity.ActivityAware; 18 | import io.flutter.embedding.engine.plugins.activity.ActivityPluginBinding; 19 | import io.flutter.embedding.engine.plugins.lifecycle.FlutterLifecycleAdapter; 20 | import io.flutter.plugin.common.EventChannel; 21 | import io.flutter.plugin.common.MethodCall; 22 | import io.flutter.plugin.common.MethodChannel; 23 | import io.flutter.plugin.common.MethodChannel.MethodCallHandler; 24 | import io.flutter.plugin.common.MethodChannel.Result; 25 | import io.flutter.plugin.common.PluginRegistry; 26 | import io.flutter.plugin.common.PluginRegistry.Registrar; 27 | 28 | /** 29 | * MopPlugin 30 | */ 31 | public class MopPlugin implements FlutterPlugin, MethodCallHandler, ActivityAware { 32 | private static final String LOG_TAG = MopPlugin.class.getSimpleName(); 33 | 34 | private static final String CHANNEL = "mop"; 35 | private static final String EVENT_CHANNEL = "plugins.mop.finogeeks.com/mop_event"; 36 | 37 | private final FlutterInterface flutterInterface = new FlutterInterface(); 38 | private final MopPluginDelegate delegate = new MopPluginDelegate(); 39 | private final MopEventStream mopEventStream = new MopEventStream(); 40 | 41 | // These are null when not using v2 embedding. 42 | private FlutterPluginBinding flutterPluginBinding; 43 | private MethodChannel channel; 44 | private EventChannel eventChannel; 45 | private Lifecycle lifecycle; 46 | 47 | /** 48 | * Plugin registration. 49 | */ 50 | @SuppressWarnings("deprecation") 51 | public static void registerWith(Registrar registrar) { 52 | MethodChannel channel = new MethodChannel(registrar.messenger(), CHANNEL); 53 | MopPluginDelegate delegate = new MopPluginDelegate(); 54 | final MopPlugin plugin = new MopPlugin(); 55 | channel.setMethodCallHandler(plugin); 56 | registrar.addActivityResultListener(delegate); 57 | 58 | EventChannel eventChannel = new EventChannel(registrar.messenger(), EVENT_CHANNEL); 59 | final MopEventStream mopEventStream = new MopEventStream(); 60 | eventChannel.setStreamHandler(mopEventStream); 61 | MopPluginService.getInstance().initialize(registrar.activity(), mopEventStream, channel); 62 | } 63 | 64 | @Override 65 | public void onMethodCall(MethodCall call, final Result result) { 66 | ICallback callback = new ICallback() { 67 | @Override 68 | public void onSuccess(Object data) { 69 | Map obj = new HashMap(); 70 | 71 | obj.put("success", true); 72 | if (data != null) 73 | obj.put("data", data); 74 | obj.put("retMsg", "ok"); 75 | result.success(obj); 76 | } 77 | 78 | @Override 79 | public void onFail(Object error) { 80 | Map obj = new HashMap(); 81 | obj.put("success", false); 82 | obj.put("retMsg", error == null ? "" : error); 83 | result.success(obj); 84 | } 85 | 86 | @Override 87 | public void onCancel(Object cancel) { 88 | result.notImplemented(); 89 | } 90 | 91 | @Override 92 | public void startActivityForResult(Intent intent, int requestCode) { 93 | 94 | } 95 | }; 96 | Log.d(LOG_TAG, "mopplugin: invoke " + call.method); 97 | Event event = new Event(call.method, call.arguments, callback); 98 | delegate.setEvent(event); 99 | this.flutterInterface.invokeHandler(event); 100 | // if (call.method.equals("getPlatformVersion")) { 101 | // result.success("Android " + android.os.Build.VERSION.RELEASE); 102 | // } else { 103 | // result.notImplemented(); 104 | // } 105 | } 106 | 107 | @Override 108 | public void onAttachedToEngine(FlutterPluginBinding binding) { 109 | this.flutterPluginBinding = binding; 110 | channel = new MethodChannel(binding.getFlutterEngine().getDartExecutor(), CHANNEL); 111 | channel.setMethodCallHandler(this); 112 | EventChannel eventChannel = new EventChannel(binding.getFlutterEngine().getDartExecutor(), EVENT_CHANNEL); 113 | eventChannel.setStreamHandler(mopEventStream); 114 | } 115 | 116 | @Override 117 | public void onDetachedFromEngine(FlutterPluginBinding binding) { 118 | this.flutterPluginBinding = null; 119 | } 120 | 121 | @Override 122 | public void onAttachedToActivity(ActivityPluginBinding binding) { 123 | binding.addActivityResultListener(delegate); 124 | lifecycle = FlutterLifecycleAdapter.getActivityLifecycle(binding); 125 | setServicesFromActivity(binding.getActivity()); 126 | channel.setMethodCallHandler(this); 127 | } 128 | 129 | @Override 130 | public void onDetachedFromActivityForConfigChanges() { 131 | lifecycle = null; 132 | } 133 | 134 | @Override 135 | public void onReattachedToActivityForConfigChanges(ActivityPluginBinding binding) { 136 | binding.addActivityResultListener(delegate); 137 | lifecycle = FlutterLifecycleAdapter.getActivityLifecycle(binding); 138 | setServicesFromActivity(binding.getActivity()); 139 | } 140 | 141 | @Override 142 | public void onDetachedFromActivity() { 143 | lifecycle = null; 144 | channel.setMethodCallHandler(null); 145 | } 146 | 147 | private void setServicesFromActivity(Activity activity) { 148 | if (activity == null) 149 | return; 150 | MopPluginService.getInstance().initialize(activity, mopEventStream, channel); 151 | } 152 | } 153 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/MopPluginDelegate.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop; 2 | 3 | import android.app.Activity; 4 | import android.content.Intent; 5 | 6 | import com.finogeeks.mop.constants.Constants; 7 | import com.finogeeks.mop.interfaces.Event; 8 | import com.finogeeks.mop.service.MopPluginService; 9 | 10 | import io.flutter.plugin.common.PluginRegistry; 11 | 12 | public class MopPluginDelegate implements PluginRegistry.ActivityResultListener { 13 | private Event mEvent; 14 | 15 | public Event getEvent() { 16 | return mEvent; 17 | } 18 | 19 | public void setEvent(Event event) { 20 | this.mEvent = event; 21 | } 22 | 23 | @Override 24 | public boolean onActivityResult(int requestCode, int resultCode, Intent data) { 25 | if (requestCode == Constants.REQUEST_CODE_CHOOSE || requestCode == Constants.REQUEST_CODE_LOCATION_CHOOSE) { 26 | MopPluginService.getInstance().getApisManager().getApiInstance(mEvent).onActivityResult(requestCode, 27 | resultCode, data, mEvent.getCallback()); 28 | } 29 | return true; 30 | } 31 | 32 | } -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/AbsApi.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api; 2 | 3 | import android.content.Intent; 4 | 5 | import com.finogeeks.mop.interfaces.IApi; 6 | import com.finogeeks.mop.interfaces.ICallback; 7 | 8 | public abstract class AbsApi implements IApi { 9 | 10 | @Override 11 | public void onCreate() { 12 | 13 | } 14 | 15 | @Override 16 | public void onDestroy() { 17 | 18 | } 19 | 20 | @Override 21 | public void onActivityResult(int requestCode, int resultCode, Intent data, ICallback callback) { 22 | 23 | } 24 | @Override 25 | public void onNewIntent(Intent intent) { 26 | 27 | } 28 | @Override 29 | public void onResume() { 30 | 31 | } 32 | @Override 33 | public void onPause() { 34 | 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/ApisManager.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api; 2 | 3 | import android.app.Activity; 4 | import android.text.TextUtils; 5 | 6 | import com.finogeeks.mop.api.mop.AppletHandlerModule; 7 | import com.finogeeks.mop.api.mop.AppletManageModule; 8 | import com.finogeeks.mop.api.mop.AppletModule; 9 | import com.finogeeks.mop.api.mop.BaseModule; 10 | import com.finogeeks.mop.api.mop.ExtensionApiModule; 11 | import com.finogeeks.mop.api.mop.InitSDKModule; 12 | import com.finogeeks.mop.api.mop.VersionModule; 13 | import com.finogeeks.mop.api.mop.SmSignModule; 14 | import com.finogeeks.mop.api.mop.WXQrCodeModule; 15 | import com.finogeeks.mop.interfaces.Event; 16 | import com.finogeeks.mop.interfaces.IApi; 17 | 18 | import java.util.HashMap; 19 | import java.util.Map; 20 | 21 | public class ApisManager { 22 | 23 | 24 | private final static String TAG = ApisManager.class.getSimpleName(); 25 | 26 | public static final int SUCCESS = 0x10; 27 | public static final int FAIL = 0x11; 28 | public static final int CANCEL = 0x12; 29 | public static final int PENDING = 0x13; 30 | 31 | private final IApi EMPTY_API = new EmptyApi(); 32 | private final Map APIS = new HashMap<>(); 33 | private Activity mActivity; 34 | 35 | public ApisManager(Activity activity) { 36 | mActivity = activity; 37 | initSdkApi(activity); 38 | } 39 | 40 | /** 41 | * api功能调用 42 | * 43 | * @param event 封装了api名称,参数及回调函数id的对象 44 | */ 45 | public IApi getApiInstance(Event event) { 46 | IApi api = APIS.get(event.getName()); 47 | if (api != null) { 48 | return api; 49 | } 50 | return null; 51 | 52 | } 53 | 54 | /** 55 | * api功能调用 56 | * 57 | * @param event 封装了api名称,参数及回调函数id的对象 58 | */ 59 | public void invoke(Event event) { 60 | IApi api = APIS.get(event.getName()); 61 | if (api != null) { 62 | api.invoke(event.getName(), event.getParam(), event.getCallback()); 63 | return; 64 | } 65 | 66 | } 67 | 68 | private void initSdkApi(Activity activity) { 69 | add(new InitSDKModule(activity)); 70 | add(new BaseModule(activity)); 71 | add(new AppletModule(activity)); 72 | add(new AppletManageModule(activity)); 73 | add(new AppletHandlerModule(activity)); 74 | add(new ExtensionApiModule(activity)); 75 | add(new VersionModule(activity)); 76 | add(new SmSignModule(activity)); 77 | add(new WXQrCodeModule(activity)); 78 | } 79 | 80 | private void add(IApi api) { 81 | if (api != null && api.apis() != null && api.apis().length > 0) { 82 | String[] apiNames = api.apis(); 83 | for (String name : apiNames) { 84 | if (!TextUtils.isEmpty(name)) { 85 | APIS.put(name, api); 86 | } 87 | } 88 | } 89 | } 90 | 91 | } 92 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/BaseApi.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api; 2 | 3 | import android.content.Context; 4 | import android.os.Handler; 5 | import android.os.Looper; 6 | 7 | public abstract class BaseApi extends AbsApi { 8 | 9 | 10 | protected static final String TAG = "InnerApi"; 11 | 12 | protected static final Handler HANDLER = new Handler(Looper.getMainLooper()); 13 | 14 | private Context mContext; 15 | 16 | public BaseApi(Context context) { 17 | mContext = context; 18 | } 19 | 20 | public Context getContext() { 21 | return mContext; 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/EmptyApi.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api; 2 | 3 | import android.content.Intent; 4 | 5 | import com.finogeeks.mop.interfaces.IApi; 6 | import com.finogeeks.mop.interfaces.ICallback; 7 | 8 | import java.util.Map; 9 | 10 | public class EmptyApi implements IApi { 11 | 12 | 13 | @Override 14 | public void onCreate() { 15 | 16 | } 17 | 18 | @Override 19 | public void onDestroy() { 20 | 21 | } 22 | 23 | @Override 24 | public void onActivityResult(int requestCode, int resultCode, Intent data, ICallback callback) { 25 | 26 | } 27 | @Override 28 | public void onNewIntent(Intent data) { 29 | 30 | } 31 | @Override 32 | public void onResume() { 33 | 34 | } 35 | @Override 36 | public void onPause() { 37 | 38 | } 39 | 40 | @Override 41 | public String[] apis() { 42 | return null; 43 | } 44 | 45 | @Override 46 | public void invoke(String event, Map param, ICallback callback) { 47 | 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/mop/BaseModule.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api.mop; 2 | 3 | import android.app.Application; 4 | import android.content.Context; 5 | import android.text.TextUtils; 6 | import android.util.Log; 7 | 8 | import com.finogeeks.lib.applet.client.FinAppClient; 9 | import com.finogeeks.lib.applet.client.FinAppConfig; 10 | import com.finogeeks.lib.applet.client.FinStoreConfig; 11 | import com.finogeeks.lib.applet.interfaces.FinCallback; 12 | import com.finogeeks.mop.api.BaseApi; 13 | import com.finogeeks.mop.api.mop.util.InitUtils; 14 | import com.finogeeks.mop.interfaces.ICallback; 15 | import com.finogeeks.mop.service.MopPluginService; 16 | import com.finogeeks.xlog.XLogLevel; 17 | import com.google.gson.Gson; 18 | 19 | import java.io.File; 20 | import java.util.ArrayList; 21 | import java.util.List; 22 | import java.util.Map; 23 | 24 | public class BaseModule extends BaseApi { 25 | private final static String TAG = "BaseModule"; 26 | 27 | public BaseModule(Context context) { 28 | super(context); 29 | } 30 | 31 | @Override 32 | public void onCreate() { 33 | super.onCreate(); 34 | 35 | } 36 | 37 | @Override 38 | public String[] apis() { 39 | return new String[]{"initialize"}; 40 | } 41 | 42 | @Override 43 | public void invoke(String event, Map param, final ICallback callback) { 44 | 45 | if (FinAppClient.INSTANCE.isFinAppProcess(super.getContext())) { 46 | // 小程序进程不执行任何初始化操作 47 | return; 48 | } 49 | String appkey = String.valueOf(param.get("appkey")); 50 | String secret = String.valueOf(param.get("secret")); 51 | String apiServer = "https://api.finclip.com"; 52 | String apiPrefix = "/api/v1/mop/"; 53 | String cryptType = (String) param.get("cryptType"); 54 | if (cryptType == null || cryptType.isEmpty()) { 55 | cryptType = "MD5"; 56 | } 57 | if (param.get("apiServer") != null) { 58 | apiServer = String.valueOf(param.get("apiServer")); 59 | } 60 | if (param.get("apiPrefix") != null) { 61 | apiPrefix = String.valueOf(param.get("apiPrefix")); 62 | if (!apiPrefix.endsWith("/")) { 63 | apiPrefix = apiPrefix + "/"; 64 | } 65 | } 66 | Boolean disablePermission = (Boolean) param.get("disablePermission"); 67 | if (disablePermission == null) { 68 | disablePermission = false; 69 | } 70 | 71 | String userId = ""; 72 | if (param.get("userId") != null) { 73 | userId = (String) param.get("userId"); 74 | } 75 | 76 | Boolean encryptServerData = (Boolean) param.get("encryptServerData"); 77 | if (encryptServerData == null) encryptServerData = false; 78 | Boolean debug = (Boolean) param.get("debug"); 79 | if (debug == null) debug = false; 80 | Boolean bindAppletWithMainProcess = (Boolean) param.get("bindAppletWithMainProcess"); 81 | if (bindAppletWithMainProcess == null) bindAppletWithMainProcess = false; 82 | Integer pageCountLimit = (Integer) param.get("pageCountLimit"); 83 | if (pageCountLimit == null) { 84 | pageCountLimit = 0; 85 | } 86 | 87 | String customWebViewUserAgent = (String) param.get("customWebViewUserAgent"); 88 | Integer appletIntervalUpdateLimit = (Integer) param.get("appletIntervalUpdateLimit"); 89 | Integer maxRunningApplet = (Integer) param.get("maxRunningApplet"); 90 | Gson gson = new Gson(); 91 | List finStoreConfigs = null; 92 | if (param.get("finStoreConfigs") != null) { 93 | finStoreConfigs = new ArrayList<>(); 94 | List> configs = (List>) param.get("finStoreConfigs"); 95 | for (Map config : configs) { 96 | for (String key : config.keySet()) { 97 | String sdkKey = (String) config.get("sdkKey"); 98 | String sdkSecret = (String) config.get("sdkSecret"); 99 | String apiUrl = (String) config.get("apiServer"); 100 | String apmUrl = (String) config.get("apmServer"); 101 | if (apmUrl == null) apmUrl = ""; 102 | String fingerprint = (String) config.get("fingerprint"); 103 | if (fingerprint == null) fingerprint = ""; 104 | String encryptType = (String) config.get("cryptType"); 105 | Boolean encryptServerData1 = (Boolean) config.get("encryptServerData"); 106 | Boolean enablePreloadFramework = (Boolean) config.get("enablePreloadFramework"); 107 | //凡泰助手里,服务器是https://api.finclip.com,默认开启预加载基础库 108 | if(!TextUtils.isEmpty(apiServer) && apiServer.equals("https://api.finclip.com")) { 109 | enablePreloadFramework = true; 110 | } 111 | 112 | if (encryptServerData1 == null) encryptServerData1 = false; 113 | finStoreConfigs.add(new FinStoreConfig(sdkKey, sdkSecret, apiUrl, apmUrl, "", fingerprint, encryptType, encryptServerData1, enablePreloadFramework)); 114 | } 115 | } 116 | } 117 | 118 | // uiConfig 119 | FinAppConfig.UIConfig uiConfig = InitUtils.createUIConfigFromMap((Map) param.get("uiConfig")); 120 | 121 | FinAppConfig.Builder builder = new FinAppConfig.Builder() 122 | .setSdkKey(appkey) 123 | .setSdkSecret(secret) 124 | .setApiUrl(apiServer) 125 | .setApiPrefix(apiPrefix) 126 | .setEncryptionType(cryptType) 127 | .setEncryptServerData(encryptServerData) 128 | .setUserId(userId) 129 | .setDebugMode(debug) 130 | .setDisableRequestPermissions(disablePermission) 131 | .setBindAppletWithMainProcess(bindAppletWithMainProcess) 132 | .setPageCountLimit(pageCountLimit); 133 | 134 | if (customWebViewUserAgent != null) 135 | builder.setCustomWebViewUserAgent(customWebViewUserAgent); 136 | if (appletIntervalUpdateLimit != null) 137 | builder.setAppletIntervalUpdateLimit(appletIntervalUpdateLimit); 138 | if (maxRunningApplet != null) builder.setMaxRunningApplet(maxRunningApplet); 139 | if (finStoreConfigs != null) builder.setFinStoreConfigs(finStoreConfigs); 140 | if (uiConfig != null) builder.setUiConfig(uiConfig); 141 | 142 | FinAppConfig config = builder.build(); 143 | Log.d(TAG, "config:" + gson.toJson(config)); 144 | 145 | final Application application = MopPluginService.getInstance().getActivity().getApplication(); 146 | // SDK初始化结果回调,用于接收SDK初始化状态 147 | FinCallback cb = new FinCallback() { 148 | @Override 149 | public void onSuccess(Object result) { 150 | // SDK初始化成功 151 | callback.onSuccess(null); 152 | } 153 | 154 | @Override 155 | public void onError(int code, String error) { 156 | // SDK初始化失败 157 | callback.onFail(null); 158 | // Toast.makeText(MopPluginService.getInstance().getContext(), "SDK初始化失败", Toast.LENGTH_SHORT).show(); 159 | } 160 | 161 | @Override 162 | public void onProgress(int status, String error) { 163 | 164 | } 165 | }; 166 | FinAppClient.INSTANCE.init(application, config, cb); 167 | } 168 | } -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/mop/ExtensionApiModule.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api.mop; 2 | 3 | import android.content.Context; 4 | import android.os.Handler; 5 | import android.os.Looper; 6 | import android.util.Log; 7 | 8 | import com.finogeeks.lib.applet.client.FinAppClient; 9 | import com.finogeeks.lib.applet.modules.log.FLog; 10 | import com.finogeeks.mop.api.BaseApi; 11 | import com.finogeeks.mop.interfaces.ICallback; 12 | import com.finogeeks.mop.service.MopPluginService; 13 | import com.finogeeks.mop.utils.GsonUtil; 14 | 15 | import org.json.JSONException; 16 | import org.json.JSONObject; 17 | 18 | import java.util.HashMap; 19 | import java.util.Map; 20 | 21 | import io.flutter.plugin.common.MethodChannel; 22 | 23 | 24 | public class ExtensionApiModule extends BaseApi { 25 | 26 | private static final String TAG = "ExtensionApiModule"; 27 | 28 | private Handler handler = new Handler(Looper.getMainLooper()); 29 | 30 | public ExtensionApiModule(Context context) { 31 | super(context); 32 | } 33 | 34 | @Override 35 | public String[] apis() { 36 | return new String[]{"registerExtensionApi","addWebExtentionApi"}; 37 | } 38 | 39 | @Override 40 | public void invoke(String s, Map param, ICallback iCallback) { 41 | if(s.equals("registerExtensionApi")) { 42 | MethodChannel channel = MopPluginService.getInstance().getMethodChannel(); 43 | String name = (String) param.get("name"); 44 | Log.d(TAG, "registerExtensionApi:" + name); 45 | FinAppClient.INSTANCE.getExtensionApiManager().registerApi(new com.finogeeks.lib.applet.api.BaseApi(getContext()) { 46 | @Override 47 | public String[] apis() { 48 | return new String[]{name}; 49 | } 50 | 51 | @Override 52 | public void invoke(String s, JSONObject jsonObject, com.finogeeks.lib.applet.interfaces.ICallback iCallback) { 53 | Log.d("MopPlugin", "invoke extensionApi:" + s + ",params:" + jsonObject); 54 | Map params = GsonUtil.gson.fromJson(jsonObject.toString(), HashMap.class); 55 | handler.post(() -> { 56 | channel.invokeMethod("extensionApi:" + name, params, new MethodChannel.Result() { 57 | @Override 58 | public void success(Object result) { 59 | String json = GsonUtil.gson.toJson(result); 60 | FLog.d(ExtensionApiModule.TAG, "channel invokeMethod:" + name 61 | + " success, result=" + result + ", json=" + json); 62 | JSONObject ret = null; 63 | if (json != null && !json.equals("null")) { 64 | try { 65 | ret = new JSONObject(json); 66 | if (ret.has("errMsg")) { 67 | String errMsg = ret.getString("errMsg"); 68 | if (errMsg.startsWith(name + ":fail")) { 69 | iCallback.onFail(ret); 70 | return; 71 | } 72 | } 73 | } catch (JSONException e) { 74 | e.printStackTrace(); 75 | } 76 | } 77 | 78 | iCallback.onSuccess(ret); 79 | } 80 | 81 | @Override 82 | public void error(String errorCode, String errorMessage, Object errorDetails) { 83 | FLog.e(ExtensionApiModule.TAG, "channel invokeMethod:" + name 84 | + " error, errorCode=" + errorCode 85 | + ", errorMessage=" + errorMessage 86 | + ", errorDetails=" + errorDetails); 87 | iCallback.onFail(); 88 | } 89 | 90 | @Override 91 | public void notImplemented() { 92 | iCallback.onFail(); 93 | } 94 | }); 95 | }); 96 | } 97 | }); 98 | }else if(s.equals("addWebExtentionApi")){ 99 | MethodChannel channel = MopPluginService.getInstance().getMethodChannel(); 100 | String name = (String) param.get("name"); 101 | Log.d(TAG, "addWebExtentionApi:" + name); 102 | FinAppClient.INSTANCE.getExtensionWebApiManager().registerApi(new com.finogeeks.lib.applet.api.BaseApi(getContext()) { 103 | @Override 104 | public String[] apis() { 105 | return new String[]{name}; 106 | } 107 | 108 | @Override 109 | public void invoke(String s, JSONObject jsonObject, com.finogeeks.lib.applet.interfaces.ICallback iCallback) { 110 | Log.d("MopPlugin", "invoke webextensionApi:" + s + ",params:" + jsonObject); 111 | Map params = GsonUtil.gson.fromJson(jsonObject.toString(), HashMap.class); 112 | handler.post(() -> { 113 | channel.invokeMethod("webExtentionApi:" + name, params, new MethodChannel.Result() { 114 | @Override 115 | public void success(Object result) { 116 | String json = GsonUtil.gson.toJson(result); 117 | FLog.d(ExtensionApiModule.TAG, "channel invokeMethod:" + name 118 | + " success, result=" + result + ", json=" + json); 119 | JSONObject ret = null; 120 | if (json != null && !json.equals("null")) { 121 | try { 122 | ret = new JSONObject(json); 123 | if (ret.has("errMsg")) { 124 | String errMsg = ret.getString("errMsg"); 125 | if (errMsg.startsWith(name + ":fail")) { 126 | iCallback.onFail(ret); 127 | return; 128 | } 129 | } 130 | } catch (JSONException e) { 131 | e.printStackTrace(); 132 | } 133 | } 134 | 135 | iCallback.onSuccess(ret); 136 | } 137 | 138 | @Override 139 | public void error(String errorCode, String errorMessage, Object errorDetails) { 140 | FLog.e(ExtensionApiModule.TAG, "channel invokeMethod:" + name 141 | + " error, errorCode=" + errorCode 142 | + ", errorMessage=" + errorMessage 143 | + ", errorDetails=" + errorDetails); 144 | iCallback.onFail(); 145 | } 146 | 147 | @Override 148 | public void notImplemented() { 149 | iCallback.onFail(); 150 | } 151 | }); 152 | }); 153 | } 154 | }); 155 | } 156 | 157 | } 158 | } 159 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/mop/SmSignModule.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api.mop; 2 | 3 | import android.content.Context; 4 | 5 | import com.finogeeks.finclip.sdkcore.manager.FinClipSDKCoreManager; 6 | import com.finogeeks.lib.applet.client.FinAppClient; 7 | import com.finogeeks.lib.applet.db.entity.FinApplet; 8 | import com.finogeeks.mop.api.BaseApi; 9 | import com.finogeeks.mop.interfaces.ICallback; 10 | 11 | import java.util.HashMap; 12 | import java.util.Map; 13 | 14 | public class SmSignModule extends BaseApi { 15 | 16 | public SmSignModule(Context context) { 17 | super(context); 18 | } 19 | 20 | @Override 21 | public String[] apis() { 22 | return new String[]{"smsign"}; 23 | } 24 | 25 | @Override 26 | public void invoke(String event, Map param, ICallback callback) { 27 | String text = (String) param.get("plainText"); 28 | String result = new FinClipSDKCoreManager.Builder().build().messageDigestBySM(text); 29 | Map res = new HashMap<>(); 30 | res.put("data", result); 31 | callback.onSuccess(res); 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/mop/VersionModule.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api.mop; 2 | 3 | 4 | import android.content.Context; 5 | 6 | import com.finogeeks.lib.applet.BuildConfig; 7 | import com.finogeeks.mop.api.BaseApi; 8 | import com.finogeeks.mop.interfaces.ICallback; 9 | 10 | import java.util.Map; 11 | 12 | public class VersionModule extends BaseApi { 13 | 14 | public VersionModule(Context context) { 15 | super(context); 16 | } 17 | 18 | @Override 19 | public String[] apis() { 20 | return new String[]{"sdkVersion"}; 21 | } 22 | 23 | @Override 24 | public void invoke(String event, Map param, ICallback callback) { 25 | callback.onSuccess(BuildConfig.VERSION_NAME); 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/api/mop/WXQrCodeModule.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.api.mop; 2 | 3 | import android.content.Context; 4 | 5 | import com.finogeeks.lib.applet.client.FinAppClient; 6 | import com.finogeeks.lib.applet.modules.callback.FinSimpleCallback; 7 | import com.finogeeks.lib.applet.sdk.model.ParsedAppletInfo; 8 | import com.finogeeks.mop.api.BaseApi; 9 | import com.finogeeks.mop.interfaces.ICallback; 10 | 11 | import org.jetbrains.annotations.Nullable; 12 | 13 | import java.util.HashMap; 14 | import java.util.Map; 15 | 16 | public class WXQrCodeModule extends BaseApi { 17 | 18 | public WXQrCodeModule(Context context) { 19 | super(context); 20 | } 21 | 22 | @Override 23 | public String[] apis() { 24 | return new String[]{"parseAppletInfoFromWXQrCode"}; 25 | } 26 | 27 | @Override 28 | public void invoke(String event, Map param, ICallback callback) { 29 | String qrCode = (String) param.get("qrCode"); 30 | String apiServer = (String) param.get("apiServer"); 31 | FinAppClient.INSTANCE.getAppletApiManager().parseAppletInfoFromWXQrCode( 32 | qrCode, 33 | apiServer, 34 | new FinSimpleCallback() { 35 | @Override 36 | public void onSuccess(ParsedAppletInfo appletInfo) { 37 | HashMap map = new HashMap<>(); 38 | map.put("appId", appletInfo != null ? appletInfo.getAppId() : null); 39 | callback.onSuccess(map); 40 | } 41 | 42 | @Override 43 | public void onError(int code, @Nullable String error) { 44 | callback.onFail(code + ", " + error); 45 | } 46 | }); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/constants/Constants.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.constants; 2 | 3 | /** 4 | * 全局常量池 5 | */ 6 | public class Constants { 7 | public static final int REQUEST_CODE_CHOOSE = 0x1000000; 8 | public static final int REQUEST_CODE_LOCATION_CHOOSE = 0x1000001; 9 | public static final int REQUEST_CODE_LOCATION_PREVIEW = 0x1000002; 10 | public static final int REQUEST_CODE_SELECT_DOCUMENT = 0x1000003; 11 | } 12 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/impls/MyUserProfileHandler.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.impls; 2 | 3 | import android.content.Context; 4 | import android.os.Handler; 5 | import android.os.Looper; 6 | import android.util.Log; 7 | 8 | import com.finogeeks.lib.applet.client.FinAppInfo; 9 | import com.finogeeks.lib.applet.modules.userprofile.IUserProfileHandler; 10 | import com.finogeeks.mop.service.MopPluginService; 11 | 12 | import java.util.Map; 13 | 14 | import org.jetbrains.annotations.NotNull; 15 | import org.json.JSONObject; 16 | 17 | import io.flutter.plugin.common.MethodChannel; 18 | 19 | public class MyUserProfileHandler implements IUserProfileHandler { 20 | private static final String TAG = "MyUserProfileHandler"; 21 | 22 | private Handler handler = new Handler(Looper.getMainLooper()); 23 | 24 | @Override 25 | public void getUserProfileWithAppletInfo(@NotNull Context context, @NotNull FinAppInfo finAppInfo, @NotNull UserProfileCallback callback) { 26 | MethodChannel channel = MopPluginService.getInstance().getMethodChannel(); 27 | Log.d(TAG, "getUserProfileWithAppletInfo:"); 28 | new Handler(Looper.getMainLooper()).post(() -> { 29 | channel.invokeMethod("extensionApi:getUserProfile", null, new MethodChannel.Result() { 30 | @Override 31 | public void success(Object mapResult) { 32 | JSONObject result = null; 33 | try { 34 | result = new JSONObject((Map) mapResult); 35 | } catch (Exception e) { 36 | 37 | } 38 | 39 | if (result == null) { 40 | callback.onError(null); 41 | } else { 42 | callback.onSuccess(result); 43 | } 44 | } 45 | 46 | @Override 47 | public void error(String errorCode, String errorMessage, Object errorDetails) { 48 | callback.onError(null); 49 | } 50 | 51 | @Override 52 | public void notImplemented() { 53 | callback.onError(null); 54 | } 55 | }); 56 | }); 57 | } 58 | } 59 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/interfaces/Event.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.interfaces; 2 | 3 | 4 | import java.util.Map; 5 | 6 | public final class Event { 7 | 8 | private String name; 9 | private Object param; 10 | private ICallback callback; 11 | 12 | 13 | public Event(String name, Object param, ICallback callback) { 14 | this.name = name; 15 | this.param = param; 16 | this.callback = callback; 17 | } 18 | 19 | public String getName() { 20 | return name; 21 | } 22 | 23 | public Map getParam() { 24 | if (param instanceof Map) { 25 | 26 | return (Map)param; 27 | } 28 | return null; 29 | } 30 | 31 | public ICallback getCallback() { 32 | return callback; 33 | } 34 | 35 | } -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/interfaces/FlutterInterface.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.interfaces; 2 | 3 | import android.os.Handler; 4 | import android.os.Looper; 5 | 6 | import com.finogeeks.mop.service.MopPluginService; 7 | 8 | 9 | public class FlutterInterface { 10 | private static final String TAG = FlutterInterface.class.getSimpleName(); 11 | 12 | private Handler mHandler = new Handler(Looper.getMainLooper()); 13 | 14 | public void invokeHandler(final Event event) { 15 | 16 | mHandler.post(new Runnable() { 17 | @Override 18 | public void run() { 19 | MopPluginService.getInstance().getApisManager().invoke(event); 20 | } 21 | }); 22 | } 23 | } -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/interfaces/IApi.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.interfaces; 2 | 3 | import java.util.Map; 4 | 5 | /** 6 | * Api接口,实现相应功能的Api需实现此接口 7 | */ 8 | public interface IApi extends ILifecycle { 9 | 10 | /** 11 | * @return 支持可调用的api名称的数组 12 | */ 13 | String[] apis(); 14 | 15 | /** 16 | * 接收到对应的api调用时,会调用此方法,在此方法中处理api调用的功能逻辑 17 | * 18 | * @param event 事件名称,即api名称 19 | * @param param 参数 20 | * @param callback 回调接口 21 | */ 22 | void invoke(String event, Map param, ICallback callback); 23 | } -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/interfaces/ICallback.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.interfaces; 2 | 3 | import android.content.Intent; 4 | 5 | /** 6 | * Api回调接口 7 | */ 8 | public interface ICallback { 9 | 10 | /** 11 | * Api调用成功 12 | * 13 | * @param data Api调用返回的结果 14 | */ 15 | void onSuccess(T data); 16 | 17 | /** 18 | * Api调用失败 19 | */ 20 | void onFail(T error); 21 | 22 | /** 23 | * Api调用取消 24 | */ 25 | void onCancel(T cancel); 26 | 27 | /** 28 | * 回调{@link android.app.Activity#startActivityForResult(Intent, int)}方法 29 | * 30 | * @param intent 31 | * @param requestCode 32 | */ 33 | void startActivityForResult(Intent intent, int requestCode); 34 | 35 | } -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/interfaces/ILifecycle.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.interfaces; 2 | 3 | import android.app.Activity; 4 | import android.content.Intent; 5 | import android.os.Bundle; 6 | 7 | /** 8 | * 绑定{@link Activity}生命周期的回调接口 9 | */ 10 | public interface ILifecycle { 11 | 12 | /** 13 | * 当{@link Activity#onCreate(Bundle)}方法调用时回调. 14 | */ 15 | void onCreate(); 16 | 17 | /** 18 | * 当{@link Activity#onDestroy()}方法调用时回调. 19 | */ 20 | void onDestroy(); 21 | 22 | /** 23 | * 当{@link Activity#onActivityResult(int, int, Intent)}方法调用时回调. 24 | */ 25 | void onActivityResult(int requestCode, int resultCode, Intent data, ICallback callback); 26 | 27 | /** 28 | * 当{@link Activity#onNewIntent(Intent)}方法调用时回调. 29 | */ 30 | void onNewIntent(Intent intent); 31 | /** 32 | * 当{@link Activity#onResume()}方法调用时回调. 33 | */ 34 | void onResume(); 35 | /** 36 | * 当{@link Activity#onResume()}方法调用时回调. 37 | */ 38 | void onPause(); 39 | } -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/service/MopPluginService.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.service; 2 | 3 | import android.app.Activity; 4 | import android.content.Context; 5 | 6 | import com.finogeeks.mop.MopEventStream; 7 | import com.finogeeks.mop.api.ApisManager; 8 | 9 | import io.flutter.plugin.common.MethodChannel; 10 | 11 | public class MopPluginService { 12 | private final static String TAG = MopPluginService.class.getSimpleName(); 13 | private static volatile MopPluginService _instance = null; 14 | 15 | private ApisManager apisManager; 16 | private MopEventStream mopEventStream; 17 | 18 | 19 | private Context mContext; 20 | private Activity mActivity; 21 | private MethodChannel mMethodChannel; 22 | 23 | MopPluginService() { 24 | } 25 | 26 | public static MopPluginService getInstance() { 27 | if (_instance == null) { 28 | synchronized (MopPluginService.class) { 29 | if (_instance == null) { 30 | _instance = new MopPluginService(); 31 | } 32 | } 33 | } 34 | return _instance; 35 | } 36 | 37 | public ApisManager getApisManager() { 38 | return this.apisManager; 39 | } 40 | 41 | public MopEventStream getMopEventStream() { 42 | return this.mopEventStream; 43 | } 44 | 45 | public void initialize(Activity activity, MopEventStream mopEventStream, MethodChannel methodChannel) { 46 | this.mopEventStream = mopEventStream; 47 | this.mContext = activity.getApplicationContext(); 48 | this.apisManager = new ApisManager(activity); 49 | this.mActivity = activity; 50 | this.mMethodChannel = methodChannel; 51 | 52 | 53 | } 54 | 55 | public Context getContext() { 56 | return mContext; 57 | } 58 | 59 | public Activity getActivity() { 60 | return mActivity; 61 | } 62 | 63 | public MethodChannel getMethodChannel() { 64 | return mMethodChannel; 65 | } 66 | } 67 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/utils/AppletUtils.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.utils; 2 | 3 | import android.content.Context; 4 | 5 | import com.finogeeks.lib.applet.client.FinAppClient; 6 | import com.finogeeks.lib.applet.client.FinAppProcessClient; 7 | import com.finogeeks.lib.applet.main.FinAppHomeActivity; 8 | import com.finogeeks.mop.interfaces.ICallback; 9 | 10 | public class AppletUtils { 11 | public static void moveCurrentAppletToFront(Context context, ICallback callback) { 12 | try { 13 | if (FinAppClient.INSTANCE.isFinAppProcess(context)) { 14 | FinAppHomeActivity activity = (FinAppHomeActivity) FinAppProcessClient.INSTANCE.getAppletProcessActivity(); 15 | if (activity != null) { 16 | activity.moveTaskToFront(); 17 | } 18 | } else { 19 | String currentAppletId = FinAppClient.INSTANCE.getAppletApiManager().getCurrentAppletId(); 20 | if (currentAppletId != null) { 21 | FinAppClient.INSTANCE.getAppletApiManager().moveTaskToFront(currentAppletId); 22 | } 23 | } 24 | if (callback != null) { 25 | callback.onSuccess(null); 26 | } 27 | } catch (Exception e) { 28 | e.printStackTrace(); 29 | if (callback != null) { 30 | callback.onFail(null); 31 | } 32 | } 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /android/src/main/java/com/finogeeks/mop/utils/GsonUtil.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop.utils; 2 | 3 | import com.google.gson.Gson; 4 | import com.google.gson.reflect.TypeToken; 5 | 6 | import java.util.Map; 7 | 8 | public class GsonUtil { 9 | public static Gson gson = new Gson(); 10 | 11 | public static Map toMap(Object object) { 12 | String str = gson.toJson(object); 13 | if (str != null) { 14 | return gson.fromJson(str, new TypeToken>() { 15 | }.getType()); 16 | } 17 | return null; 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /bundle.sh: -------------------------------------------------------------------------------- 1 | export LANG=en_US.UTF-8 2 | export FASTLANE_DISABLE_COLORS=1 3 | 4 | 5 | export version="$1" 6 | export iosVersion="$2" 7 | export androidVersion="$3" 8 | export branch=$4 9 | 10 | #version=`git describe --abbrev=0 --tags | tr -d '\\n' | tr -d '\\t'` 11 | 12 | echo "当前版本号:${version}" 13 | echo "依赖的iOS:${iosVersion}" 14 | echo "依赖的Android:${androidVersion}" 15 | echo "branch: $branch" 16 | 17 | git reset --hard 18 | #git checkout ${version} 19 | 20 | # 更新 pubspec.yaml 21 | cp -r pubspec.tpl.yaml pubspec.yaml 22 | sed -i "" "s/__mop_flutter_sdk_version__/${version}/g" pubspec.yaml 23 | 24 | iosVersionExist=false 25 | androidVersionExist=false 26 | 27 | # 更新iOS podspec 28 | if [[ -n "$iosVersion" && "$iosVersion" != "none" ]]; then 29 | iosVersionExist=true 30 | echo "更新mop.podspec====>" 31 | cp -r ios/mop.podspec.tpl ios/mop.podspec 32 | sed -i "" "s/__finapplet_version__/${iosVersion}/g" ios/mop.podspec 33 | else 34 | echo "跳过 iOS podspec 更新(未设置版本号)" 35 | fi 36 | 37 | # 更新android gradle 38 | if [[ -n "$androidVersion" && "$androidVersion" != "none" ]]; then 39 | androidVersionExist=true 40 | echo "更新build.gradle====>" 41 | cp -r android/build.gradle.tpl android/build.gradle 42 | sed -i "" "s/__finapplet_version__/${androidVersion}/g" android/build.gradle 43 | else 44 | echo "跳过 Android gradle 更新(未设置版本号)" 45 | fi 46 | 47 | git remote add ssh-origin ssh://git@gitlab.finogeeks.club:2233/finclipsdk/finclip-flutter-sdk.git 48 | 49 | git add . 50 | git commit -m "release: version:$version" 51 | git push ssh-origin HEAD:refs/heads/${branch} 52 | 53 | # 主要发布流程 54 | do_publish() { 55 | cat pubspec.yaml 56 | 57 | git add . 58 | git commit -m "release: version:$version" 59 | git tag -d ${version} 60 | git push ssh-origin --delete tag ${version} 61 | git tag -a ${version} -m 'FinClip-Flutter-SDK发版' 62 | git push ssh-origin --tags -f 63 | 64 | 65 | export http_proxy=http://127.0.0.1:1087 66 | export https_proxy=http://127.0.0.1:1087 67 | 68 | 69 | flutter packages pub publish --dry-run --server=https://pub.dartlang.org 70 | 71 | flutter packages pub publish --server=https://pub.dartlang.org --force 72 | 73 | unset http_proxy 74 | unset https_proxy 75 | 76 | # 在执行 GitHub 相关操作之前添加分支检查 77 | if [ "$branch" = "master" ]; then 78 | echo "当前在 master 分支,继续执行 GitHub 推送..." 79 | git remote add github ssh://git@github.com/finogeeks/mop-flutter-sdk.git 80 | 81 | #git push github HEAD:refs/heads/master --tags 82 | 83 | git push github HEAD:refs/heads/master 84 | else 85 | echo "当前分支是 ${branch},不是 master 分支,跳过 GitHub 推送操作" 86 | fi 87 | } 88 | 89 | echo "iosVersionExist: $iosVersionExist" 90 | echo "androidVersionExist: $androidVersionExist" 91 | 92 | # 使用更明确的条件判断 93 | if [ "$iosVersionExist" = "true" ] && [ "$androidVersionExist" = "true" ]; then 94 | echo "新版本号均有设置--通过" 95 | do_publish 96 | else 97 | echo " ❌❌❌ android or ios version not set, exit" 98 | fi 99 | 100 | 101 | -------------------------------------------------------------------------------- /example/.gitignore: -------------------------------------------------------------------------------- 1 | # Miscellaneous 2 | *.class 3 | *.log 4 | *.pyc 5 | *.swp 6 | .DS_Store 7 | .atom/ 8 | .buildlog/ 9 | .history 10 | .svn/ 11 | 12 | # IntelliJ related 13 | *.iml 14 | *.ipr 15 | *.iws 16 | .idea/ 17 | 18 | # The .vscode folder contains launch configuration and tasks you configure in 19 | # VS Code which you may wish to be included in version control, so this line 20 | # is commented out by default. 21 | #.vscode/ 22 | 23 | # Flutter/Dart/Pub related 24 | **/doc/api/ 25 | **/ios/Flutter/.last_build_id 26 | .dart_tool/ 27 | .flutter-plugins 28 | .flutter-plugins-dependencies 29 | .packages 30 | .pub-cache/ 31 | .pub/ 32 | /build/ 33 | 34 | # Web related 35 | lib/generated_plugin_registrant.dart 36 | 37 | # Symbolication related 38 | app.*.symbols 39 | 40 | # Obfuscation related 41 | app.*.map.json 42 | 43 | # Android Studio will place build artifacts here 44 | /android/app/debug 45 | /android/app/profile 46 | /android/app/release 47 | -------------------------------------------------------------------------------- /example/.metadata: -------------------------------------------------------------------------------- 1 | # This file tracks properties of this Flutter project. 2 | # Used by Flutter tool to assess capabilities and perform upgrades etc. 3 | # 4 | # This file should be version controlled and should not be manually edited. 5 | 6 | version: 7 | revision: ffb2ecea5223acdd139a5039be2f9c796962833d 8 | channel: stable 9 | 10 | project_type: app 11 | -------------------------------------------------------------------------------- /example/README.md: -------------------------------------------------------------------------------- 1 | # mop_example 2 | 3 | Demonstrates how to use the mop plugin. 4 | 5 | ## Getting Started 6 | 7 | This project is a starting point for a Flutter application. 8 | 9 | A few resources to get you started if this is your first Flutter project: 10 | 11 | - [Lab: Write your first Flutter app](https://flutter.dev/docs/get-started/codelab) 12 | - [Cookbook: Useful Flutter samples](https://flutter.dev/docs/cookbook) 13 | 14 | For help getting started with Flutter, view our 15 | [online documentation](https://flutter.dev/docs), which offers tutorials, 16 | samples, guidance on mobile development, and a full API reference. 17 | -------------------------------------------------------------------------------- /example/analysis_options.yaml: -------------------------------------------------------------------------------- 1 | # This file configures the analyzer, which statically analyzes Dart code to 2 | # check for errors, warnings, and lints. 3 | # 4 | # The issues identified by the analyzer are surfaced in the UI of Dart-enabled 5 | # IDEs (https://dart.dev/tools#ides-and-editors). The analyzer can also be 6 | # invoked from the command line by running `flutter analyze`. 7 | 8 | # The following line activates a set of recommended lints for Flutter apps, 9 | # packages, and plugins designed to encourage good coding practices. 10 | include: package:flutter_lints/flutter.yaml 11 | 12 | linter: 13 | # The lint rules applied to this project can be customized in the 14 | # section below to disable rules from the `package:flutter_lints/flutter.yaml` 15 | # included above or to enable additional rules. A list of all available lints 16 | # and their documentation is published at 17 | # https://dart-lang.github.io/linter/lints/index.html. 18 | # 19 | # Instead of disabling a lint rule for the entire project in the 20 | # section below, it can also be suppressed for a single line of code 21 | # or a specific dart file by using the `// ignore: name_of_lint` and 22 | # `// ignore_for_file: name_of_lint` syntax on the line or in the file 23 | # producing the lint. 24 | rules: 25 | # avoid_print: false # Uncomment to disable the `avoid_print` rule 26 | # prefer_single_quotes: true # Uncomment to enable the `prefer_single_quotes` rule 27 | 28 | # Additional information about this file can be found at 29 | # https://dart.dev/guides/language/analysis-options 30 | -------------------------------------------------------------------------------- /example/android/.gitignore: -------------------------------------------------------------------------------- 1 | gradle-wrapper.jar 2 | /.gradle 3 | /captures/ 4 | /gradlew 5 | /gradlew.bat 6 | /local.properties 7 | GeneratedPluginRegistrant.java 8 | 9 | # Remember to never publicly share your keystore. 10 | # See https://flutter.dev/docs/deployment/android#reference-the-keystore-from-the-app 11 | key.properties 12 | **/*.keystore 13 | **/*.jks 14 | -------------------------------------------------------------------------------- /example/android/.project: -------------------------------------------------------------------------------- 1 | 2 | 3 | android 4 | Project android created by Buildship. 5 | 6 | 7 | 8 | 9 | org.eclipse.buildship.core.gradleprojectbuilder 10 | 11 | 12 | 13 | 14 | 15 | org.eclipse.buildship.core.gradleprojectnature 16 | 17 | 18 | 19 | 1680241888118 20 | 21 | 30 22 | 23 | org.eclipse.core.resources.regexFilterMatcher 24 | node_modules|\.git|__CREATED_BY_JAVA_LANGUAGE_SERVER__ 25 | 26 | 27 | 28 | 29 | -------------------------------------------------------------------------------- /example/android/.settings/org.eclipse.buildship.core.prefs: -------------------------------------------------------------------------------- 1 | arguments=--init-script /var/folders/tx/98mydjws12b717spn4mx1wd80000gn/T/d146c9752a26f79b52047fb6dc6ed385d064e120494f96f08ca63a317c41f94c.gradle --init-script /var/folders/tx/98mydjws12b717spn4mx1wd80000gn/T/52cde0cfcf3e28b8b7510e992210d9614505e0911af0c190bd590d7158574963.gradle 2 | auto.sync=false 3 | build.scans.enabled=false 4 | connection.gradle.distribution=GRADLE_DISTRIBUTION(WRAPPER) 5 | connection.project.dir= 6 | eclipse.preferences.version=1 7 | gradle.user.home= 8 | java.home=/Library/Java/JavaVirtualMachines/jdk-1.8.jdk/Contents/Home 9 | jvm.arguments= 10 | offline.mode=false 11 | override.workspace.settings=true 12 | show.console.view=true 13 | show.executions.view=true 14 | -------------------------------------------------------------------------------- /example/android/app/.classpath: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /example/android/app/.project: -------------------------------------------------------------------------------- 1 | 2 | 3 | app 4 | Project app created by Buildship. 5 | 6 | 7 | 8 | 9 | org.eclipse.jdt.core.javabuilder 10 | 11 | 12 | 13 | 14 | org.eclipse.buildship.core.gradleprojectbuilder 15 | 16 | 17 | 18 | 19 | 20 | org.eclipse.jdt.core.javanature 21 | org.eclipse.buildship.core.gradleprojectnature 22 | 23 | 24 | 25 | 1680241888252 26 | 27 | 30 28 | 29 | org.eclipse.core.resources.regexFilterMatcher 30 | node_modules|\.git|__CREATED_BY_JAVA_LANGUAGE_SERVER__ 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /example/android/app/.settings/org.eclipse.buildship.core.prefs: -------------------------------------------------------------------------------- 1 | connection.project.dir=.. 2 | eclipse.preferences.version=1 3 | -------------------------------------------------------------------------------- /example/android/app/build.gradle: -------------------------------------------------------------------------------- 1 | def localProperties = new Properties() 2 | def localPropertiesFile = rootProject.file('local.properties') 3 | if (localPropertiesFile.exists()) { 4 | localPropertiesFile.withReader('UTF-8') { reader -> 5 | localProperties.load(reader) 6 | } 7 | } 8 | 9 | def flutterRoot = localProperties.getProperty('flutter.sdk') 10 | if (flutterRoot == null) { 11 | throw new GradleException("Flutter SDK not found. Define location with flutter.sdk in the local.properties file.") 12 | } 13 | 14 | def flutterVersionCode = localProperties.getProperty('flutter.versionCode') 15 | if (flutterVersionCode == null) { 16 | flutterVersionCode = '1' 17 | } 18 | 19 | def flutterVersionName = localProperties.getProperty('flutter.versionName') 20 | if (flutterVersionName == null) { 21 | flutterVersionName = '1.0' 22 | } 23 | 24 | apply plugin: 'com.android.application' 25 | apply from: "$flutterRoot/packages/flutter_tools/gradle/flutter.gradle" 26 | 27 | android { 28 | compileSdkVersion 33 29 | compileOptions { 30 | sourceCompatibility JavaVersion.VERSION_1_8 31 | targetCompatibility JavaVersion.VERSION_1_8 32 | } 33 | 34 | defaultConfig { 35 | // TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html). 36 | applicationId "com.finogeeks.finosprite" 37 | minSdkVersion 21 38 | targetSdkVersion 30 39 | versionCode flutterVersionCode.toInteger() 40 | versionName flutterVersionName 41 | } 42 | 43 | buildTypes { 44 | release { 45 | // TODO: Add your own signing config for the release build. 46 | // Signing with the debug keys for now, so `flutter run --release` works. 47 | signingConfig signingConfigs.debug 48 | } 49 | } 50 | packagingOptions { 51 | // libsdkcore.so、libyuvutil.so是被加固过的,不能被压缩,否则加载动态库时会报错 52 | doNotStrip "*/x86/libsdkcore.so" 53 | doNotStrip "*/x86_64/libsdkcore.so" 54 | doNotStrip "*/armeabi/libsdkcore.so" 55 | doNotStrip "*/armeabi-v7a/libsdkcore.so" 56 | doNotStrip "*/arm64-v8a/libsdkcore.so" 57 | 58 | doNotStrip "*/x86/libfin-yuvutil.so" 59 | doNotStrip "*/x86_64/libfin-yuvutil.so" 60 | doNotStrip "*/armeabi/libfin-yuvutil.so" 61 | doNotStrip "*/armeabi-v7a/libfin-yuvutil.so" 62 | doNotStrip "*/arm64-v8a/libfin-yuvutil.so" 63 | 64 | exclude 'META-INF/beans.xml' 65 | } 66 | } 67 | 68 | flutter { 69 | source '../..' 70 | } 71 | 72 | dependencies { 73 | def sdk_version = "2.48.5" 74 | compileOnly "com.finogeeks.lib:finapplet:${sdk_version}" 75 | implementation "com.finogeeks.mop:plugins:${sdk_version}" 76 | } 77 | -------------------------------------------------------------------------------- /example/android/app/src/debug/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /example/android/app/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 7 | 14 | 18 | 22 | 27 | 31 | 32 | 33 | 34 | 35 | 36 | 38 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /example/android/app/src/main/java/com/finogeeks/mop_example/CustomLoadingPage.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop_example; 2 | 3 | import android.content.Context; 4 | import android.widget.TextView; 5 | 6 | import com.finogeeks.lib.applet.modules.appletloadinglayout.IFinAppletLoadingPage; 7 | 8 | import androidx.annotation.NonNull; 9 | 10 | public class CustomLoadingPage extends IFinAppletLoadingPage { 11 | public CustomLoadingPage(@NonNull Context context) { 12 | super(context); 13 | } 14 | 15 | @Override 16 | public int getFailureLayoutRes() { 17 | return R.layout.layout_custom_loading_page_failure; 18 | } 19 | 20 | @Override 21 | public int getLoadingLayoutRes() { 22 | return R.layout.layout_custom_loading_page; 23 | } 24 | 25 | @Override 26 | public void onLoadingFailure(@NonNull String s) { 27 | ((TextView)getFailureLayout().findViewById(R.id.failMsg)).setText(s); 28 | } 29 | 30 | @Override 31 | public void onLoadingFailure(@NonNull String s, @NonNull String s1) { 32 | ((TextView)getFailureLayout().findViewById(R.id.failTitle)).setText(s); 33 | ((TextView)getFailureLayout().findViewById(R.id.failMsg)).setText(s1); 34 | } 35 | 36 | @Override 37 | public void onUpdate(@NonNull String s, @NonNull String s1) { 38 | ((TextView)getLoadingLayout().findViewById(R.id.loadingTitle)).setText(s); 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /example/android/app/src/main/java/com/finogeeks/mop_example/MainActivity.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop_example; 2 | 3 | import io.flutter.embedding.android.FlutterActivity; 4 | 5 | public class MainActivity extends FlutterActivity { 6 | } 7 | -------------------------------------------------------------------------------- /example/android/app/src/main/java/com/finogeeks/mop_example/MainApplication.java: -------------------------------------------------------------------------------- 1 | package com.finogeeks.mop_example; 2 | 3 | import android.app.AlertDialog; 4 | import android.app.Application; 5 | import android.app.Dialog; 6 | import android.content.Context; 7 | // import android.support.annotation.NonNull; 8 | import androidx.annotation.NonNull; 9 | 10 | import com.finogeeks.lib.applet.client.FinAppClient; 11 | import com.finogeeks.lib.applet.client.FinAppProcessClient; 12 | import com.finogeeks.lib.applet.sdk.api.IAppletProcessApiManager; 13 | import com.finogeeks.lib.applet.sdk.api.IAppletProcessHandler; 14 | 15 | public class MainApplication extends Application { 16 | 17 | @Override 18 | public void onCreate() { 19 | super.onCreate(); 20 | 21 | initProcessHandler(); 22 | } 23 | 24 | private void initProcessHandler() { 25 | if (!FinAppClient.INSTANCE.isFinAppProcess(this)) { 26 | return; 27 | } 28 | 29 | // FinAppProcessClient.INSTANCE.getAppletProcessApiManager().setAppletProcessHandler(new IAppletProcessHandler(){ 30 | // @Override 31 | // public boolean onNavigationBarMoreButtonClicked(@NonNull Context context, @NonNull String appId) { 32 | // // 在这里弹出自定义的更多视图 33 | // new AlertDialog.Builder(context) 34 | // .setTitle("更多视图") 35 | // .setMessage(appId) 36 | // .setPositiveButton("菜单", null) 37 | // .setNegativeButton("取消", null) 38 | // .show(); 39 | 40 | // // 返回true表示要自行处理更多视图;返回false表示使用默认的更多视图 41 | // return true; 42 | // } 43 | // }); 44 | } 45 | } -------------------------------------------------------------------------------- /example/android/app/src/main/res/drawable-v21/launch_background.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 12 | 13 | -------------------------------------------------------------------------------- /example/android/app/src/main/res/drawable/launch_background.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 12 | 13 | -------------------------------------------------------------------------------- /example/android/app/src/main/res/layout/layout_custom_loading_page.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 13 | 21 | -------------------------------------------------------------------------------- /example/android/app/src/main/res/layout/layout_custom_loading_page_failure.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 15 | 23 | -------------------------------------------------------------------------------- /example/android/app/src/main/res/mipmap-hdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/android/app/src/main/res/mipmap-hdpi/ic_launcher.png -------------------------------------------------------------------------------- /example/android/app/src/main/res/mipmap-mdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/android/app/src/main/res/mipmap-mdpi/ic_launcher.png -------------------------------------------------------------------------------- /example/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png -------------------------------------------------------------------------------- /example/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /example/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /example/android/app/src/main/res/values-night/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 9 | 15 | 18 | 19 | -------------------------------------------------------------------------------- /example/android/app/src/main/res/values/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 9 | 15 | 18 | 19 | -------------------------------------------------------------------------------- /example/android/app/src/profile/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 3 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /example/android/build.gradle: -------------------------------------------------------------------------------- 1 | buildscript { 2 | repositories { 3 | google() 4 | mavenCentral() 5 | } 6 | 7 | dependencies { 8 | classpath 'com.android.tools.build:gradle:4.1.0' 9 | classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.5.31" 10 | } 11 | } 12 | 13 | allprojects { 14 | repositories { 15 | google() 16 | mavenCentral() 17 | } 18 | } 19 | 20 | rootProject.buildDir = '../build' 21 | subprojects { 22 | project.buildDir = "${rootProject.buildDir}/${project.name}" 23 | project.evaluationDependsOn(':app') 24 | } 25 | 26 | task clean(type: Delete) { 27 | delete rootProject.buildDir 28 | } 29 | -------------------------------------------------------------------------------- /example/android/gradle.properties: -------------------------------------------------------------------------------- 1 | org.gradle.jvmargs=-Xmx1536M 2 | android.useAndroidX=true 3 | android.enableJetifier=true 4 | -------------------------------------------------------------------------------- /example/android/gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | #Fri Jun 23 08:50:38 CEST 2017 2 | distributionBase=GRADLE_USER_HOME 3 | distributionPath=wrapper/dists 4 | zipStoreBase=GRADLE_USER_HOME 5 | zipStorePath=wrapper/dists 6 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.7-all.zip 7 | -------------------------------------------------------------------------------- /example/android/settings.gradle: -------------------------------------------------------------------------------- 1 | include ':app' 2 | 3 | def localPropertiesFile = new File(rootProject.projectDir, "local.properties") 4 | def properties = new Properties() 5 | 6 | assert localPropertiesFile.exists() 7 | localPropertiesFile.withReader("UTF-8") { reader -> properties.load(reader) } 8 | 9 | def flutterSdkPath = properties.getProperty("flutter.sdk") 10 | assert flutterSdkPath != null, "flutter.sdk not set in local.properties" 11 | apply from: "$flutterSdkPath/packages/flutter_tools/gradle/app_plugin_loader.gradle" 12 | -------------------------------------------------------------------------------- /example/ios/.gitignore: -------------------------------------------------------------------------------- 1 | *.mode1v3 2 | *.mode2v3 3 | *.moved-aside 4 | *.pbxuser 5 | *.perspectivev3 6 | **/*sync/ 7 | .sconsign.dblite 8 | .tags* 9 | **/.vagrant/ 10 | **/DerivedData/ 11 | Icon? 12 | **/Pods/ 13 | **/.symlinks/ 14 | profile 15 | xcuserdata 16 | **/.generated/ 17 | Flutter/App.framework 18 | Flutter/Flutter.framework 19 | Flutter/Flutter.podspec 20 | Flutter/Generated.xcconfig 21 | Flutter/ephemeral/ 22 | Flutter/app.flx 23 | Flutter/app.zip 24 | Flutter/flutter_assets/ 25 | Flutter/flutter_export_environment.sh 26 | ServiceDefinitions.json 27 | Runner/GeneratedPluginRegistrant.* 28 | 29 | # Exceptions to above rules. 30 | !default.mode1v3 31 | !default.mode2v3 32 | !default.pbxuser 33 | !default.perspectivev3 34 | -------------------------------------------------------------------------------- /example/ios/Flutter/AppFrameworkInfo.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | App 9 | CFBundleIdentifier 10 | io.flutter.flutter.app 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | App 15 | CFBundlePackageType 16 | FMWK 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleSignature 20 | ???? 21 | CFBundleVersion 22 | 1.0 23 | MinimumOSVersion 24 | 9.0 25 | 26 | 27 | -------------------------------------------------------------------------------- /example/ios/Flutter/Debug.xcconfig: -------------------------------------------------------------------------------- 1 | #include? "Pods/Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig" 2 | #include "Generated.xcconfig" 3 | -------------------------------------------------------------------------------- /example/ios/Flutter/Release.xcconfig: -------------------------------------------------------------------------------- 1 | #include? "Pods/Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig" 2 | #include "Generated.xcconfig" 3 | -------------------------------------------------------------------------------- /example/ios/Podfile: -------------------------------------------------------------------------------- 1 | # Uncomment this line to define a global platform for your project 2 | platform :ios, '9.0' 3 | 4 | source 'ssh://gitlab.finogeeks.club/finclip-ios/DevPods' 5 | source 'ssh://gitlab.finogeeks.club/finclip-ios/FinPods' 6 | 7 | # CocoaPods analytics sends network stats synchronously affecting flutter build latency. 8 | ENV['COCOAPODS_DISABLE_STATS'] = 'true' 9 | 10 | project 'Runner', { 11 | 'Debug' => :debug, 12 | 'Profile' => :release, 13 | 'Release' => :release, 14 | } 15 | 16 | def flutter_root 17 | generated_xcode_build_settings_path = File.expand_path(File.join('..', 'Flutter', 'Generated.xcconfig'), __FILE__) 18 | unless File.exist?(generated_xcode_build_settings_path) 19 | raise "#{generated_xcode_build_settings_path} must exist. If you're running pod install manually, make sure flutter pub get is executed first" 20 | end 21 | 22 | File.foreach(generated_xcode_build_settings_path) do |line| 23 | matches = line.match(/FLUTTER_ROOT\=(.*)/) 24 | return matches[1].strip if matches 25 | end 26 | raise "FLUTTER_ROOT not found in #{generated_xcode_build_settings_path}. Try deleting Generated.xcconfig, then run flutter pub get" 27 | end 28 | 29 | require File.expand_path(File.join('packages', 'flutter_tools', 'bin', 'podhelper'), flutter_root) 30 | 31 | flutter_ios_podfile_setup 32 | 33 | target 'Runner' do 34 | use_frameworks! 35 | use_modular_headers! 36 | 37 | flutter_install_all_ios_pods File.dirname(File.realpath(__FILE__)) 38 | end 39 | 40 | post_install do |installer| 41 | installer.pods_project.targets.each do |target| 42 | flutter_additional_ios_build_settings(target) 43 | target.build_configurations.each do |config| 44 | config.build_settings['EXCLUDED_ARCHS[sdk=iphonesimulator*]'] = 'arm64' 45 | if config.name == "Debug" 46 | config.build_settings['ONLY_ACTIVE_ARCH'] = 'YES' 47 | else 48 | config.build_settings['ONLY_ACTIVE_ARCH'] = 'NO' 49 | end 50 | end 51 | end 52 | end 53 | -------------------------------------------------------------------------------- /example/ios/Podfile.lock: -------------------------------------------------------------------------------- 1 | PODS: 2 | - FinApplet (2.45.1) 3 | - FinAppletExt (2.45.1): 4 | - FinApplet (= 2.45.1) 5 | - Flutter (1.0.0) 6 | - mop (0.1.1): 7 | - FinApplet (= 2.45.1) 8 | - FinAppletExt (= 2.45.1) 9 | - Flutter 10 | 11 | DEPENDENCIES: 12 | - Flutter (from `Flutter`) 13 | - mop (from `.symlinks/plugins/mop/ios`) 14 | 15 | SPEC REPOS: 16 | ssh://gitlab.finogeeks.club/finclip-ios/FinPods: 17 | - FinApplet 18 | - FinAppletExt 19 | 20 | EXTERNAL SOURCES: 21 | Flutter: 22 | :path: Flutter 23 | mop: 24 | :path: ".symlinks/plugins/mop/ios" 25 | 26 | SPEC CHECKSUMS: 27 | FinApplet: eea27894485c871a94b2ded79a8fe1e84d7ffcc9 28 | FinAppletExt: 231dde4c4ed3862b70179c3dfac7406090ace955 29 | Flutter: 50d75fe2f02b26cc09d224853bb45737f8b3214a 30 | mop: afa40651ec188a85a27c068d5afa2a97c6a53a01 31 | 32 | PODFILE CHECKSUM: 2da0220ee5ba22a2dfcec42dfe5b17d05f3c3da9 33 | 34 | COCOAPODS: 1.15.2 35 | -------------------------------------------------------------------------------- /example/ios/Runner.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /example/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /example/ios/Runner.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | PreviewsEnabled 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /example/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 24 | 25 | 30 | 31 | 32 | 33 | 39 | 40 | 41 | 42 | 43 | 44 | 54 | 56 | 62 | 63 | 64 | 65 | 66 | 67 | 73 | 75 | 81 | 82 | 83 | 84 | 86 | 87 | 90 | 91 | 92 | -------------------------------------------------------------------------------- /example/ios/Runner.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /example/ios/Runner.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /example/ios/Runner.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | PreviewsEnabled 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /example/ios/Runner/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | import UIKit 2 | import Flutter 3 | 4 | @UIApplicationMain 5 | @objc class AppDelegate: FlutterAppDelegate { 6 | 7 | var channelHander : FlutterMethodChannelHandler? 8 | 9 | override func application( 10 | _ application: UIApplication, 11 | didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]? 12 | ) -> Bool { 13 | 14 | let controller : FlutterViewController = window?.rootViewController as! FlutterViewController 15 | channelHander = FlutterMethodChannelHandler(messenger: controller) 16 | GeneratedPluginRegistrant.register(with: self) 17 | return super.application(application, didFinishLaunchingWithOptions: launchOptions) 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "size" : "20x20", 5 | "idiom" : "iphone", 6 | "filename" : "Icon-App-20x20@2x.png", 7 | "scale" : "2x" 8 | }, 9 | { 10 | "size" : "20x20", 11 | "idiom" : "iphone", 12 | "filename" : "Icon-App-20x20@3x.png", 13 | "scale" : "3x" 14 | }, 15 | { 16 | "size" : "29x29", 17 | "idiom" : "iphone", 18 | "filename" : "Icon-App-29x29@1x.png", 19 | "scale" : "1x" 20 | }, 21 | { 22 | "size" : "29x29", 23 | "idiom" : "iphone", 24 | "filename" : "Icon-App-29x29@2x.png", 25 | "scale" : "2x" 26 | }, 27 | { 28 | "size" : "29x29", 29 | "idiom" : "iphone", 30 | "filename" : "Icon-App-29x29@3x.png", 31 | "scale" : "3x" 32 | }, 33 | { 34 | "size" : "40x40", 35 | "idiom" : "iphone", 36 | "filename" : "Icon-App-40x40@2x.png", 37 | "scale" : "2x" 38 | }, 39 | { 40 | "size" : "40x40", 41 | "idiom" : "iphone", 42 | "filename" : "Icon-App-40x40@3x.png", 43 | "scale" : "3x" 44 | }, 45 | { 46 | "size" : "60x60", 47 | "idiom" : "iphone", 48 | "filename" : "Icon-App-60x60@2x.png", 49 | "scale" : "2x" 50 | }, 51 | { 52 | "size" : "60x60", 53 | "idiom" : "iphone", 54 | "filename" : "Icon-App-60x60@3x.png", 55 | "scale" : "3x" 56 | }, 57 | { 58 | "size" : "20x20", 59 | "idiom" : "ipad", 60 | "filename" : "Icon-App-20x20@1x.png", 61 | "scale" : "1x" 62 | }, 63 | { 64 | "size" : "20x20", 65 | "idiom" : "ipad", 66 | "filename" : "Icon-App-20x20@2x.png", 67 | "scale" : "2x" 68 | }, 69 | { 70 | "size" : "29x29", 71 | "idiom" : "ipad", 72 | "filename" : "Icon-App-29x29@1x.png", 73 | "scale" : "1x" 74 | }, 75 | { 76 | "size" : "29x29", 77 | "idiom" : "ipad", 78 | "filename" : "Icon-App-29x29@2x.png", 79 | "scale" : "2x" 80 | }, 81 | { 82 | "size" : "40x40", 83 | "idiom" : "ipad", 84 | "filename" : "Icon-App-40x40@1x.png", 85 | "scale" : "1x" 86 | }, 87 | { 88 | "size" : "40x40", 89 | "idiom" : "ipad", 90 | "filename" : "Icon-App-40x40@2x.png", 91 | "scale" : "2x" 92 | }, 93 | { 94 | "size" : "76x76", 95 | "idiom" : "ipad", 96 | "filename" : "Icon-App-76x76@1x.png", 97 | "scale" : "1x" 98 | }, 99 | { 100 | "size" : "76x76", 101 | "idiom" : "ipad", 102 | "filename" : "Icon-App-76x76@2x.png", 103 | "scale" : "2x" 104 | }, 105 | { 106 | "size" : "83.5x83.5", 107 | "idiom" : "ipad", 108 | "filename" : "Icon-App-83.5x83.5@2x.png", 109 | "scale" : "2x" 110 | }, 111 | { 112 | "size" : "1024x1024", 113 | "idiom" : "ios-marketing", 114 | "filename" : "Icon-App-1024x1024@1x.png", 115 | "scale" : "1x" 116 | } 117 | ], 118 | "info" : { 119 | "version" : 1, 120 | "author" : "xcode" 121 | } 122 | } 123 | -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-1024x1024@1x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-1024x1024@1x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "author" : "xcode", 4 | "version" : 1 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/LaunchImage.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "LaunchImage.png", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "filename" : "LaunchImage@2x.png", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "filename" : "LaunchImage@3x.png", 16 | "scale" : "3x" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/LaunchImage.imageset/LaunchImage@3x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/LaunchImage.imageset/README.md: -------------------------------------------------------------------------------- 1 | # Launch Screen Assets 2 | 3 | You can customize the launch screen with your own desired assets by replacing the image files in this directory. 4 | 5 | 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. -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/minipro_list_collect.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "filename" : "minipro_list_collect@2x.png", 9 | "idiom" : "universal", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "filename" : "minipro_list_collect@3x.png", 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "author" : "xcode", 20 | "version" : 1 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/minipro_list_collect.imageset/minipro_list_collect@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/minipro_list_collect.imageset/minipro_list_collect@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/minipro_list_collect.imageset/minipro_list_collect@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/minipro_list_collect.imageset/minipro_list_collect@3x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/minipro_list_service.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "filename" : "minipro_list_service@2x.png", 9 | "idiom" : "universal", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "filename" : "minipro_list_service@3x.png", 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "author" : "xcode", 20 | "version" : 1 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/minipro_list_service.imageset/minipro_list_service@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/minipro_list_service.imageset/minipro_list_service@2x.png -------------------------------------------------------------------------------- /example/ios/Runner/Assets.xcassets/minipro_list_service.imageset/minipro_list_service@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/example/ios/Runner/Assets.xcassets/minipro_list_service.imageset/minipro_list_service@3x.png -------------------------------------------------------------------------------- /example/ios/Runner/Base.lproj/LaunchScreen.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | -------------------------------------------------------------------------------- /example/ios/Runner/Base.lproj/Main.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /example/ios/Runner/FlutterMethodChannelHandler.h: -------------------------------------------------------------------------------- 1 | // 2 | // FlutterMethodChannelHandler.h 3 | // Runner 4 | // 5 | // Created by Haley on 2023/4/10. 6 | // 7 | 8 | #import 9 | #import 10 | 11 | @interface FlutterMethodChannelHandler : NSObject 12 | 13 | - (instancetype)initWithMessenger:(NSObject *)messenger; 14 | 15 | @end 16 | 17 | -------------------------------------------------------------------------------- /example/ios/Runner/FlutterMethodChannelHandler.m: -------------------------------------------------------------------------------- 1 | // 2 | // FlutterMethodChannelHandler.m 3 | // Runner 4 | // 5 | // Created by Haley on 2023/4/10. 6 | // 7 | 8 | #import "FlutterMethodChannelHandler.h" 9 | 10 | #import 11 | 12 | @interface FlutterMethodChannelHandler () 13 | 14 | @property (nonatomic,strong) FlutterMethodChannel *channel; 15 | 16 | @end 17 | 18 | @implementation FlutterMethodChannelHandler 19 | 20 | - (instancetype)initWithMessenger:(NSObject*)messenger 21 | { 22 | self = [super init]; 23 | if (self) { 24 | [self setupChannelWithMessenger:messenger]; 25 | } 26 | 27 | return self; 28 | } 29 | 30 | - (void)setupChannelWithMessenger:(NSObject*)messenger 31 | { 32 | _channel = [FlutterMethodChannel methodChannelWithName:@"com.message.flutter_to_app" binaryMessenger:messenger]; 33 | 34 | [_channel setMethodCallHandler:^(FlutterMethodCall * _Nonnull call, FlutterResult _Nonnull result) { 35 | NSLog(@"收到Flutter消息:%@", call.method); 36 | if ([call.method isEqualToString:@"showCustomMoreView"]) { 37 | NSString *appId = call.arguments[@"appId"]; 38 | // 弹出自定义的更多视图 39 | UIViewController *viewController = [[UIApplication sharedApplication] fat_topViewController]; 40 | 41 | UIAlertController *alertViewController = [UIAlertController alertControllerWithTitle:@"更多视图" message:appId preferredStyle:UIAlertControllerStyleActionSheet]; 42 | [alertViewController addAction:[UIAlertAction actionWithTitle:@"转发" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) { 43 | 44 | }]]; 45 | [alertViewController addAction:[UIAlertAction actionWithTitle:@"取消" style:UIAlertActionStyleCancel handler:^(UIAlertAction * _Nonnull action) { 46 | 47 | }]]; 48 | [viewController presentViewController:alertViewController animated:YES completion:nil]; 49 | } 50 | }]; 51 | } 52 | 53 | @end 54 | -------------------------------------------------------------------------------- /example/ios/Runner/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CADisableMinimumFrameDurationOnPhone 6 | 7 | CFBundleDevelopmentRegion 8 | $(DEVELOPMENT_LANGUAGE) 9 | CFBundleExecutable 10 | $(EXECUTABLE_NAME) 11 | CFBundleIdentifier 12 | $(PRODUCT_BUNDLE_IDENTIFIER) 13 | CFBundleInfoDictionaryVersion 14 | 6.0 15 | CFBundleName 16 | mop_example 17 | CFBundlePackageType 18 | APPL 19 | CFBundleShortVersionString 20 | $(FLUTTER_BUILD_NAME) 21 | CFBundleSignature 22 | ???? 23 | CFBundleVersion 24 | $(FLUTTER_BUILD_NUMBER) 25 | LSRequiresIPhoneOS 26 | 27 | UILaunchStoryboardName 28 | LaunchScreen 29 | UIMainStoryboardFile 30 | Main 31 | UISupportedInterfaceOrientations 32 | 33 | UIInterfaceOrientationPortrait 34 | UIInterfaceOrientationLandscapeLeft 35 | UIInterfaceOrientationLandscapeRight 36 | 37 | UISupportedInterfaceOrientations~ipad 38 | 39 | UIInterfaceOrientationPortrait 40 | UIInterfaceOrientationPortraitUpsideDown 41 | UIInterfaceOrientationLandscapeLeft 42 | UIInterfaceOrientationLandscapeRight 43 | 44 | UIViewControllerBasedStatusBarAppearance 45 | 46 | 47 | 48 | -------------------------------------------------------------------------------- /example/ios/Runner/LoadingView.h: -------------------------------------------------------------------------------- 1 | // 2 | // LoadingView.h 3 | // Runner 4 | // 5 | // Created by Haley on 2023/4/9. 6 | // 7 | 8 | #import 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface LoadingView : FATBaseLoadingView 13 | 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /example/ios/Runner/LoadingView.m: -------------------------------------------------------------------------------- 1 | // 2 | // LoadingView.m 3 | // Runner 4 | // 5 | // Created by Haley on 2023/4/9. 6 | // 7 | 8 | #import "LoadingView.h" 9 | 10 | @implementation LoadingView 11 | 12 | - (instancetype)initWithFrame:(CGRect)frame { 13 | if ([super initWithFrame:frame]) { 14 | self.loadingView.padding = 5; 15 | self.loadingView.dotView.backgroundColor = [UIColor redColor]; 16 | self.loadingView.animation.duration = 2; 17 | self.titleLabel.textColor = [UIColor redColor]; 18 | } 19 | return self; 20 | } 21 | - (void)layoutSubviews 22 | { 23 | [super layoutSubviews]; 24 | 25 | // 修改小程序logo应该是从管理后台上传新的小程序图标,因为更多面板、关于页面也会展示小程序logo,只改这里只是loding页面生效 26 | self.bottomImageView.hidden = YES; 27 | } 28 | 29 | @end 30 | -------------------------------------------------------------------------------- /example/ios/Runner/Runner-Bridging-Header.h: -------------------------------------------------------------------------------- 1 | #import "GeneratedPluginRegistrant.h" 2 | #import "FlutterMethodChannelHandler.h" 3 | -------------------------------------------------------------------------------- /example/lib/test_page.dart: -------------------------------------------------------------------------------- 1 | import 'package:flutter/material.dart'; 2 | import 'package:mop/mop.dart'; 3 | 4 | class TestPage extends StatefulWidget { 5 | @override 6 | _TestPageState createState() => _TestPageState(); 7 | } 8 | 9 | class _TestPageState extends State { 10 | final TextEditingController _controller1 = TextEditingController(text: '5f72e3559a6a7900019b5baa'); 11 | final TextEditingController _controller2 = TextEditingController(); 12 | final TextEditingController _controller3 = TextEditingController(text: 'key1=value2&name=zhangsan'); 13 | final TextEditingController _controller4 = TextEditingController(text: 'https://api.finclip.com/api/v1/mop/runtime/applet/-f-f1362bb056a265aa--'); 14 | 15 | int _selectedRadio = 0; 16 | 17 | void _handleRadioValueChange(int? value) { 18 | setState(() { 19 | _selectedRadio = value!; 20 | }); 21 | } 22 | 23 | void _handleButtonPress() { 24 | // 在这里处理按钮点击事件 25 | String appId = _controller1.text.trim(); 26 | String path = _controller2.text.trim(); 27 | String query = _controller3.text.trim(); 28 | 29 | int index = _selectedRadio; 30 | FCReLaunchMode mode = FCReLaunchMode.PARAMS_EXIST; 31 | if (index == 1) { 32 | mode = FCReLaunchMode.ONLY_PARAMS_DIFF; 33 | } else if (index == 2) { 34 | mode = FCReLaunchMode.ALWAYS; 35 | } else if (index == 3) { 36 | mode = FCReLaunchMode.NEVER; 37 | } 38 | 39 | Map? startParams = {}; 40 | if (path.length > 0) { 41 | startParams["path"] = path; 42 | } 43 | if (query.length > 0) { 44 | startParams["query"] = query; 45 | } 46 | 47 | RemoteAppletRequest request = RemoteAppletRequest( 48 | apiServer: 'https://api.finclip.com', 49 | appletId: appId, 50 | reLaunchMode: mode, 51 | startParams: startParams); 52 | Mop.instance.startApplet(request); 53 | } 54 | 55 | void _handleqrCodeButtonPress() { 56 | String qrcode = _controller4.text.trim(); 57 | int index = _selectedRadio; 58 | FCReLaunchMode mode = FCReLaunchMode.PARAMS_EXIST; 59 | if (index == 1) { 60 | mode = FCReLaunchMode.ONLY_PARAMS_DIFF; 61 | } else if (index == 2) { 62 | mode = FCReLaunchMode.ALWAYS; 63 | } else if (index == 3) { 64 | mode = FCReLaunchMode.NEVER; 65 | } 66 | QRCodeAppletRequest qrcodeRequest = QRCodeAppletRequest(qrcode, reLaunchMode: mode); 67 | Mop.instance.qrcodeStartApplet(qrcodeRequest); 68 | } 69 | 70 | @override 71 | Widget build(BuildContext context) { 72 | return Scaffold( 73 | appBar: AppBar( 74 | title: Text('测试页面'), 75 | ), 76 | body: Padding( 77 | padding: const EdgeInsets.all(16.0), 78 | child: Column( 79 | children: [ 80 | _buildTextField(_controller1, '小程序id'), 81 | _buildTextField(_controller2, '输入path'), 82 | _buildTextField(_controller3, '输入query'), 83 | _buildTextField(_controller4, '二维码地址'), 84 | SizedBox(height: 10), 85 | Column( 86 | children: [ 87 | _buildRadioTile(0, 'ParamExist'), 88 | _buildRadioTile(1, 'OnlyParamDiff'), 89 | _buildRadioTile(2, 'Always'), 90 | _buildRadioTile(3, 'Never'), 91 | ], 92 | ), 93 | SizedBox(height: 10), 94 | ElevatedButton( 95 | onPressed: _handleButtonPress, 96 | child: Text('打开小程序'), 97 | ), 98 | SizedBox(height: 10), 99 | ElevatedButton( 100 | onPressed: _handleqrCodeButtonPress, 101 | child: Text('二维码打开小程序'), 102 | ), 103 | ], 104 | ), 105 | ), 106 | ); 107 | } 108 | 109 | Widget _buildTextField(TextEditingController controller, String hintText) { 110 | return TextField( 111 | controller: controller, 112 | decoration: InputDecoration( 113 | hintText: hintText, 114 | border: OutlineInputBorder(), 115 | contentPadding: EdgeInsets.symmetric(vertical: 12.0, horizontal: 16.0), 116 | ), 117 | ); 118 | } 119 | 120 | Widget _buildRadioTile(int value, String title) { 121 | return GestureDetector( 122 | onTap: () => _handleRadioValueChange(value), 123 | child: Row( 124 | children: [ 125 | Radio( 126 | value: value, 127 | groupValue: _selectedRadio, 128 | onChanged: _handleRadioValueChange, 129 | ), 130 | Text(title), 131 | ], 132 | ), 133 | ); 134 | } 135 | 136 | } 137 | -------------------------------------------------------------------------------- /example/pubspec.lock: -------------------------------------------------------------------------------- 1 | # Generated by pub 2 | # See https://dart.dev/tools/pub/glossary#lockfile 3 | packages: 4 | async: 5 | dependency: transitive 6 | description: 7 | name: async 8 | url: "https://pub.flutter-io.cn" 9 | source: hosted 10 | version: "2.8.2" 11 | boolean_selector: 12 | dependency: transitive 13 | description: 14 | name: boolean_selector 15 | url: "https://pub.flutter-io.cn" 16 | source: hosted 17 | version: "2.1.0" 18 | characters: 19 | dependency: transitive 20 | description: 21 | name: characters 22 | url: "https://pub.flutter-io.cn" 23 | source: hosted 24 | version: "1.2.0" 25 | charcode: 26 | dependency: transitive 27 | description: 28 | name: charcode 29 | url: "https://pub.flutter-io.cn" 30 | source: hosted 31 | version: "1.3.1" 32 | clock: 33 | dependency: transitive 34 | description: 35 | name: clock 36 | url: "https://pub.flutter-io.cn" 37 | source: hosted 38 | version: "1.1.0" 39 | collection: 40 | dependency: transitive 41 | description: 42 | name: collection 43 | url: "https://pub.flutter-io.cn" 44 | source: hosted 45 | version: "1.16.0" 46 | cupertino_icons: 47 | dependency: "direct main" 48 | description: 49 | name: cupertino_icons 50 | url: "https://pub.flutter-io.cn" 51 | source: hosted 52 | version: "1.0.5" 53 | fake_async: 54 | dependency: transitive 55 | description: 56 | name: fake_async 57 | url: "https://pub.flutter-io.cn" 58 | source: hosted 59 | version: "1.3.0" 60 | flutter: 61 | dependency: "direct main" 62 | description: flutter 63 | source: sdk 64 | version: "0.0.0" 65 | flutter_lints: 66 | dependency: "direct dev" 67 | description: 68 | name: flutter_lints 69 | url: "https://pub.flutter-io.cn" 70 | source: hosted 71 | version: "1.0.4" 72 | flutter_plugin_android_lifecycle: 73 | dependency: transitive 74 | description: 75 | name: flutter_plugin_android_lifecycle 76 | url: "https://pub.flutter-io.cn" 77 | source: hosted 78 | version: "2.0.14" 79 | flutter_test: 80 | dependency: "direct dev" 81 | description: flutter 82 | source: sdk 83 | version: "0.0.0" 84 | lints: 85 | dependency: transitive 86 | description: 87 | name: lints 88 | url: "https://pub.flutter-io.cn" 89 | source: hosted 90 | version: "1.0.1" 91 | matcher: 92 | dependency: transitive 93 | description: 94 | name: matcher 95 | url: "https://pub.flutter-io.cn" 96 | source: hosted 97 | version: "0.12.11" 98 | material_color_utilities: 99 | dependency: transitive 100 | description: 101 | name: material_color_utilities 102 | url: "https://pub.flutter-io.cn" 103 | source: hosted 104 | version: "0.1.4" 105 | meta: 106 | dependency: transitive 107 | description: 108 | name: meta 109 | url: "https://pub.flutter-io.cn" 110 | source: hosted 111 | version: "1.7.0" 112 | mop: 113 | dependency: "direct main" 114 | description: 115 | path: ".." 116 | relative: true 117 | source: path 118 | version: "2.45.1" 119 | path: 120 | dependency: transitive 121 | description: 122 | name: path 123 | url: "https://pub.flutter-io.cn" 124 | source: hosted 125 | version: "1.8.1" 126 | sky_engine: 127 | dependency: transitive 128 | description: flutter 129 | source: sdk 130 | version: "0.0.99" 131 | source_span: 132 | dependency: transitive 133 | description: 134 | name: source_span 135 | url: "https://pub.flutter-io.cn" 136 | source: hosted 137 | version: "1.8.2" 138 | stack_trace: 139 | dependency: transitive 140 | description: 141 | name: stack_trace 142 | url: "https://pub.flutter-io.cn" 143 | source: hosted 144 | version: "1.10.0" 145 | stream_channel: 146 | dependency: transitive 147 | description: 148 | name: stream_channel 149 | url: "https://pub.flutter-io.cn" 150 | source: hosted 151 | version: "2.1.0" 152 | string_scanner: 153 | dependency: transitive 154 | description: 155 | name: string_scanner 156 | url: "https://pub.flutter-io.cn" 157 | source: hosted 158 | version: "1.1.0" 159 | term_glyph: 160 | dependency: transitive 161 | description: 162 | name: term_glyph 163 | url: "https://pub.flutter-io.cn" 164 | source: hosted 165 | version: "1.2.0" 166 | test_api: 167 | dependency: transitive 168 | description: 169 | name: test_api 170 | url: "https://pub.flutter-io.cn" 171 | source: hosted 172 | version: "0.4.9" 173 | vector_math: 174 | dependency: transitive 175 | description: 176 | name: vector_math 177 | url: "https://pub.flutter-io.cn" 178 | source: hosted 179 | version: "2.1.2" 180 | sdks: 181 | dart: ">=2.17.0 <3.0.0" 182 | flutter: ">=3.0.0" 183 | -------------------------------------------------------------------------------- /example/pubspec.yaml: -------------------------------------------------------------------------------- 1 | name: mop_example 2 | description: Demonstrates how to use the mop plugin. 3 | publish_to: 'none' 4 | 5 | environment: 6 | sdk: '>=2.12.0 <3.0.0' 7 | 8 | dependencies: 9 | flutter: 10 | sdk: flutter 11 | 12 | mop: 13 | # When depending on this package from a real application you should use: 14 | # mop: ^x.y.z 15 | # See https://dart.dev/tools/pub/dependencies#version-constraints 16 | # The example app is bundled with the plugin so we use a path dependency on 17 | # the parent directory to use the current plugin's version. 18 | path: ../ 19 | 20 | # The following adds the Cupertino Icons font to your application. 21 | # Use with the CupertinoIcons class for iOS style icons. 22 | cupertino_icons: ^1.0.2 23 | 24 | dev_dependencies: 25 | flutter_test: 26 | sdk: flutter 27 | 28 | # The "flutter_lints" package below contains a set of recommended lints to 29 | # encourage good coding practices. The lint set provided by the package is 30 | # activated in the `analysis_options.yaml` file located at the root of your 31 | # package. See that file for information about deactivating specific lint 32 | # rules and activating additional ones. 33 | flutter_lints: ^1.0.0 34 | 35 | # For information on the generic Dart part of this file, see the 36 | # following page: https://dart.dev/tools/pub/pubspec 37 | 38 | # The following section is specific to Flutter. 39 | flutter: 40 | 41 | # The following line ensures that the Material Icons font is 42 | # included with your application, so that you can use the icons in 43 | # the material Icons class. 44 | uses-material-design: true 45 | 46 | # To add assets to your application, add an assets section, like this: 47 | # assets: 48 | # - images/a_dot_burr.jpeg 49 | # - images/a_dot_ham.jpeg 50 | 51 | # An image asset can refer to one or more resolution-specific "variants", see 52 | # https://flutter.dev/assets-and-images/#resolution-aware. 53 | 54 | # For details regarding adding assets from package dependencies, see 55 | # https://flutter.dev/assets-and-images/#from-packages 56 | 57 | # To add custom fonts to your application, add a fonts section here, 58 | # in this "flutter" section. Each entry in this list should have a 59 | # "family" key with the font family name, and a "fonts" key with a 60 | # list giving the asset and other descriptors for the font. For 61 | # example: 62 | # fonts: 63 | # - family: Schyler 64 | # fonts: 65 | # - asset: fonts/Schyler-Regular.ttf 66 | # - asset: fonts/Schyler-Italic.ttf 67 | # style: italic 68 | # - family: Trajan Pro 69 | # fonts: 70 | # - asset: fonts/TrajanPro.ttf 71 | # - asset: fonts/TrajanPro_Bold.ttf 72 | # weight: 700 73 | # 74 | # For details regarding fonts from package dependencies, 75 | # see https://flutter.dev/custom-fonts/#from-packages 76 | -------------------------------------------------------------------------------- /example/test/widget_test.dart: -------------------------------------------------------------------------------- 1 | // This is a basic Flutter widget test. 2 | // 3 | // To perform an interaction with a widget in your test, use the WidgetTester 4 | // utility that Flutter provides. For example, you can send tap and scroll 5 | // gestures. You can also use WidgetTester to find child widgets in the widget 6 | // tree, read text, and verify that the values of widget properties are correct. 7 | 8 | import 'package:flutter/material.dart'; 9 | import 'package:flutter_test/flutter_test.dart'; 10 | 11 | import 'package:mop_example/main.dart'; 12 | 13 | void main() { 14 | testWidgets('Verify Platform version', (WidgetTester tester) async { 15 | // Build our app and trigger a frame. 16 | await tester.pumpWidget(MyApp()); 17 | 18 | // Verify that platform version is retrieved. 19 | expect( 20 | find.byWidgetPredicate( 21 | (Widget widget) => widget is Text && 22 | widget.data!.startsWith('Running on:'), 23 | ), 24 | findsOneWidget, 25 | ); 26 | }); 27 | } 28 | -------------------------------------------------------------------------------- /ios/.gitignore: -------------------------------------------------------------------------------- 1 | .idea/ 2 | .vagrant/ 3 | .sconsign.dblite 4 | .svn/ 5 | 6 | .DS_Store 7 | *.swp 8 | profile 9 | 10 | DerivedData/ 11 | build/ 12 | GeneratedPluginRegistrant.h 13 | GeneratedPluginRegistrant.m 14 | 15 | .generated/ 16 | 17 | *.pbxuser 18 | *.mode1v3 19 | *.mode2v3 20 | *.perspectivev3 21 | 22 | !default.pbxuser 23 | !default.mode1v3 24 | !default.mode2v3 25 | !default.perspectivev3 26 | 27 | xcuserdata 28 | 29 | *.moved-aside 30 | 31 | *.pyc 32 | *sync/ 33 | Icon? 34 | .tags* 35 | 36 | /Flutter/Generated.xcconfig 37 | /Flutter/flutter_export_environment.sh -------------------------------------------------------------------------------- /ios/Assets/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/finogeeks/mop-flutter-sdk/135505fc16269edfa622ba9b4aec1d9e5c028084/ios/Assets/.gitkeep -------------------------------------------------------------------------------- /ios/Classes/Api/MOPAppletDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOPAppletDelegate.h 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/20. 6 | // 7 | 8 | #import 9 | #import 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOPAppletDelegate : NSObject 14 | 15 | + (instancetype)instance; 16 | 17 | @property (nonatomic, copy) void (^bindGetPhoneNumbers)(NSDictionary *dic); 18 | 19 | @end 20 | 21 | NS_ASSUME_NONNULL_END 22 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOPButtonOpenTypeDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOPButtonOpenTypeDelegate.h 3 | // mop 4 | // 5 | // Created by vhcan on 2023/6/28. 6 | // 7 | 8 | #import 9 | #import 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOPButtonOpenTypeDelegate : NSObject 14 | 15 | + (instancetype)instance; 16 | 17 | @end 18 | 19 | NS_ASSUME_NONNULL_END 20 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOPButtonOpenTypeDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOPButtonOpenTypeDelegate.m 3 | // mop 4 | // 5 | // Created by vhcan on 2023/6/28. 6 | // 7 | 8 | #import "MOPButtonOpenTypeDelegate.h" 9 | #import "MopPlugin.h" 10 | #import "MopCustomMenuModel.h" 11 | #import 12 | #import 13 | 14 | @implementation MOPButtonOpenTypeDelegate 15 | 16 | + (instancetype)instance 17 | { 18 | static MOPButtonOpenTypeDelegate *_instance; 19 | static dispatch_once_t once; 20 | dispatch_once(&once, ^{ 21 | _instance = [[self alloc] init]; 22 | }); 23 | return _instance; 24 | } 25 | 26 | - (BOOL)getUserInfoWithAppletInfo:(FATAppletInfo *)appletInfo bindGetUserInfo:(void (^)(NSDictionary *result))bindGetUserInfo 27 | { 28 | FlutterMethodChannel *channel = [[MopPlugin instance] methodChannel]; 29 | NSLog(@"getUserInfoWithAppletInfo:%@", channel); 30 | [channel invokeMethod:@"extensionApi:getUserInfo" arguments:nil result:^(id _Nullable result) { 31 | NSDictionary *userInfo; 32 | if (![result isKindOfClass:[NSDictionary class]]) { 33 | userInfo = @{@"errMsg":@"getUserInfo:fail return value format invalid"}; 34 | } else { 35 | userInfo = result; 36 | } 37 | bindGetUserInfo(userInfo); 38 | }]; 39 | return YES; 40 | } 41 | 42 | - (BOOL)getUserProfileWithAppletInfo:(FATAppletInfo *)appletInfo 43 | bindGetUserProfile:(void (^)(NSDictionary *result))bindGetUserProfile 44 | { 45 | FlutterMethodChannel *channel = [[MopPlugin instance] methodChannel]; 46 | [channel invokeMethod:@"extensionApi:getUserProfile" 47 | arguments:nil 48 | result:^(id result) { 49 | if (!bindGetUserProfile) { 50 | return; 51 | } 52 | if ([result isKindOfClass:NSDictionary.class]) { 53 | bindGetUserProfile(result); 54 | } else { 55 | bindGetUserProfile(@{@"fatErrCode": @"fail"}); 56 | } 57 | 58 | }]; 59 | return YES; 60 | } 61 | 62 | @end 63 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_addWebExtentionApi.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOB_addWebExtentionApi.h 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_addWebExtentionApi : MOPBaseApi 13 | @property(nonatomic, copy) NSString* name; 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_addWebExtentionApi.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOB_addWebExtentionApi.m 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOP_addWebExtentionApi.h" 9 | #import "MopPlugin.h" 10 | #import 11 | 12 | @implementation MOP_addWebExtentionApi 13 | 14 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 15 | { 16 | NSLog(@"MOB_addWebExtentionApi"); 17 | FlutterMethodChannel *channel = [[MopPlugin instance] methodChannel]; 18 | [[FATClient sharedClient] fat_registerWebApi:self.name handle:^(id param, FATExtensionApiCallback callback) { 19 | NSLog(@"invoke webExtentionApi:"); 20 | NSLog(@"%@",self.name); 21 | NSLog(@"%@",param); 22 | NSString* api = [@"webExtentionApi:" stringByAppendingString:self.name]; 23 | [channel invokeMethod:api arguments:param result:^(id _Nullable result) { 24 | NSLog(@"webExtentionApi reslut:%@",result); 25 | // 先判断是否flutter发生错误 26 | BOOL isFlutterError = [result isKindOfClass:[FlutterError class]] || result == FlutterMethodNotImplemented; 27 | if (isFlutterError) { 28 | NSLog(@"webExtentionApi reslut:fail"); 29 | callback(FATExtensionCodeFailure,nil); 30 | return; 31 | } 32 | // 再判断回调是否为失败 33 | BOOL hasError = [[result allKeys] containsObject:@"errMsg"]; 34 | if (hasError) { 35 | NSString *errMsg = result[@"errMsg"]; 36 | NSString *errPrefix = [NSString stringWithFormat:@"%@:fail", self.name]; 37 | BOOL isFail = [errMsg hasPrefix:errPrefix]; 38 | if (isFail) { 39 | NSLog(@"webExtentionApi reslut:fail"); 40 | callback(FATExtensionCodeFailure,nil); 41 | return; 42 | } 43 | } 44 | // 其他的按成功处理 45 | NSLog(@"webExtentionApi callback:%@",result); 46 | callback(FATExtensionCodeSuccess,result); 47 | }]; 48 | 49 | }]; 50 | success(@{}); 51 | 52 | } 53 | @end 54 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_callJS.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_callJS.h 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_callJS : MOPBaseApi 13 | @property (nonatomic, copy) NSString *eventName; 14 | @property (nonatomic, copy) NSString *nativeViewId; 15 | @property (nonatomic, copy) NSDictionary *eventData; 16 | @end 17 | 18 | NS_ASSUME_NONNULL_END 19 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_callJS.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_callJS.m 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOP_callJS.h" 9 | 10 | @implementation MOP_callJS 11 | 12 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 13 | { 14 | if (!self.eventData || !self.eventName || !self.nativeViewId) { 15 | failure(@{@"errMsg": @"callJS:fail"}); 16 | return; 17 | } 18 | 19 | NSNumber *numberId = @(_nativeViewId.integerValue); 20 | [[FATClient sharedClient].nativeViewManager sendEvent:_eventName nativeViewId:numberId detail:_eventData completion:^(id result, NSError *error) { 21 | if (error) { 22 | failure(@{@"errMsg": @"callJS:fail"}); 23 | } else { 24 | success(result); 25 | } 26 | }]; 27 | } 28 | @end 29 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_changeUserId.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_changeUserId.h 3 | // mop 4 | // 5 | // Created by 滔 on 2023/3/23. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_changeUserId : MOPBaseApi 13 | @property (nonatomic, copy) NSString *userId; 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_changeUserId.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_changeUserId.m 3 | // mop 4 | // 5 | // Created by 滔 on 2023/3/23. 6 | // 7 | 8 | #import "MOP_changeUserId.h" 9 | #import 10 | 11 | @implementation MOP_changeUserId 12 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 13 | { 14 | [FATClient sharedClient].config.currentUserId = self.userId; 15 | success(@{}); 16 | } 17 | @end 18 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_clearApplets.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_clearApplets.h 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/16. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_clearApplets : MOPBaseApi 13 | 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_clearApplets.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_clearApplets.m 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/16. 6 | // 7 | 8 | #import "MOP_clearApplets.h" 9 | #import 10 | 11 | @implementation MOP_clearApplets 12 | 13 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 14 | { 15 | NSLog(@"clearApplets"); 16 | [[FATClient sharedClient] closeAllAppletsWithCompletion:^{ 17 | [[FATClient sharedClient] clearMemoryCache]; 18 | success(@{}); 19 | }]; 20 | } 21 | 22 | @end 23 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_closeAllApplets.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_closeAllApplets.h 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/16. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_closeAllApplets : MOPBaseApi 13 | 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_closeAllApplets.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_closeAllApplets.m 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/16. 6 | // 7 | 8 | #import "MOP_closeAllApplets.h" 9 | #import 10 | 11 | @implementation MOP_closeAllApplets 12 | 13 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 14 | { 15 | NSLog(@"closeAllApplets"); 16 | [[FATClient sharedClient] closeAllAppletsWithCompletion:nil]; 17 | success(@{}); 18 | } 19 | 20 | @end 21 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_closeApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_closeApplet.h 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_closeApplet : MOPBaseApi 13 | @property (nonatomic, copy) NSString *appletId; 14 | @property (nonatomic, assign) BOOL animated; 15 | @end 16 | 17 | NS_ASSUME_NONNULL_END 18 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_closeApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_closeApplet.m 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOP_closeApplet.h" 9 | #import 10 | 11 | @implementation MOP_closeApplet 12 | 13 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 14 | { 15 | if (!self.appletId || self.appletId.length < 1) { 16 | failure(@{@"errMsg": @"closeApplet:fail"}); 17 | return; 18 | } 19 | [[FATClient sharedClient] closeApplet:self.appletId animated:_animated completion:^{ 20 | success(@{}); 21 | }]; 22 | 23 | } 24 | 25 | @end 26 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_currentApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_currentApplet.h 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/16. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_currentApplet : MOPBaseApi 13 | 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_currentApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_currentApplet.m 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/16. 6 | // 7 | 8 | #import "MOP_currentApplet.h" 9 | 10 | #import 11 | 12 | @implementation MOP_currentApplet 13 | 14 | 15 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 16 | { 17 | FATAppletInfo *info = [[FATClient sharedClient] currentApplet]; 18 | if(info != nil) 19 | { 20 | NSMutableDictionary *dic = [NSMutableDictionary dictionary]; 21 | dic[@"appId"] = info.appId; 22 | dic[@"name"]= info.appTitle; 23 | dic[@"icon"]= info.appAvatar; 24 | dic[@"description"]=info.appDescription; 25 | dic[@"version"] = info.appVersion; 26 | dic[@"thumbnail"]=info.appThumbnail; 27 | dic[@"wechatLoginInfo"]=info.wechatLoginInfo; 28 | if (info.appletVersionType == FATAppletVersionTypeRelease) { 29 | dic[@"appletType"] = @"release"; 30 | } else if (info.appletVersionType == FATAppletVersionTypeTrial) { 31 | dic[@"appletType"] = @"trial"; 32 | } else if (info.appletVersionType == FATAppletVersionTypeTemporary) { 33 | dic[@"appletType"] = @"temporary"; 34 | } else if (info.appletVersionType == FATAppletVersionTypeReview) { 35 | dic[@"appletType"] = @"review"; 36 | } else { 37 | dic[@"appletType"] = @"development"; 38 | } 39 | success(dic); 40 | } else { 41 | success(@{}); 42 | } 43 | } 44 | 45 | + (void)load { 46 | 47 | } 48 | 49 | @end 50 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_finishRunningApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_finishRunningApplet.h 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_finishRunningApplet : MOPBaseApi 13 | @property (nonatomic, copy) NSString *appletId; 14 | @property (nonatomic, assign) BOOL animated; 15 | @end 16 | 17 | NS_ASSUME_NONNULL_END 18 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_finishRunningApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_finishRunningApplet.m 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOP_finishRunningApplet.h" 9 | 10 | @implementation MOP_finishRunningApplet 11 | 12 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 13 | { 14 | if (!self.appletId || self.appletId.length < 1) { 15 | failure(@{@"errMsg": @"finishRunningApplet:fail"}); 16 | return; 17 | } 18 | [[FATClient sharedClient] closeApplet:self.appletId animated:_animated completion:^{ 19 | [[FATClient sharedClient] clearMemeryApplet:self.appletId]; 20 | success(@{}); 21 | }]; 22 | 23 | } 24 | 25 | @end 26 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_initSDK.h: -------------------------------------------------------------------------------- 1 | // 2 | // Mop_initSDK.h 3 | // mop 4 | // 5 | // Created by 滔 on 2023/3/17. 6 | // 7 | 8 | #import 9 | #import "MOPBaseApi.h" 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOP_initSDK : MOPBaseApi 14 | @property (nonatomic, strong) NSDictionary *config; 15 | @property (nonatomic, strong) NSDictionary *uiConfig; 16 | @end 17 | 18 | NS_ASSUME_NONNULL_END 19 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_initialize.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_initialize.h 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import 9 | #import "MOPBaseApi.h" 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_initialize : MOPBaseApi 13 | 14 | @property (nonatomic, copy) NSString *appkey; 15 | @property (nonatomic, copy) NSString *secret; 16 | @property (nonatomic, copy) NSString *apiServer; 17 | @property (nonatomic, copy) NSString *apiPrefix; 18 | @property (nonatomic, copy) NSString *cryptType; 19 | @property (nonatomic, assign) BOOL encryptServerData; 20 | @property (nonatomic, copy) NSString *userId; 21 | @property (nonatomic, strong) NSArray *finStoreConfigs; 22 | @property (nonatomic, strong) NSDictionary *uiConfig; 23 | @property (nonatomic, copy) NSString *customWebViewUserAgent; 24 | @property (nonatomic, assign) BOOL disablePermission; 25 | @property (nonatomic, assign) NSInteger appletIntervalUpdateLimit; 26 | @property (nonatomic, assign) NSInteger maxRunningApplet; 27 | 28 | 29 | @end 30 | 31 | NS_ASSUME_NONNULL_END 32 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_initialize.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_initialize.m 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOP_initialize.h" 9 | #import 10 | #import 11 | #import "MOPTools.h" 12 | 13 | @implementation MOP_initialize 14 | 15 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 16 | { 17 | if (!self.appkey || !self.secret) { 18 | failure(@"sdkkey 或 secret不能为空"); 19 | return; 20 | } 21 | if (!self.apiServer || [self.apiServer isEqualToString:@""]) { 22 | self.apiServer = @"https://api.finclip.com"; 23 | } 24 | if (!self.apiPrefix|| [self.apiPrefix isEqualToString:@""]) { 25 | self.apiPrefix = @"/api/v1/mop"; 26 | } 27 | FATConfig *config; 28 | if (_finStoreConfigs && _finStoreConfigs.count > 0) { 29 | NSMutableArray *storeArrayM = [NSMutableArray array]; 30 | for (NSDictionary *dict in _finStoreConfigs) { 31 | FATStoreConfig *storeConfig = [[FATStoreConfig alloc] init]; 32 | storeConfig.sdkKey = dict[@"sdkKey"]; 33 | storeConfig.sdkSecret = dict[@"sdkSecret"]; 34 | storeConfig.apiServer = dict[@"apiServer"]; 35 | storeConfig.apmServer = dict[@"apmServer"]; 36 | storeConfig.fingerprint = dict[@"fingerprint"]; 37 | if ([@"SM" isEqualToString:dict[@"cryptType"]]) { 38 | storeConfig.cryptType = FATApiCryptTypeSM; 39 | } else { 40 | storeConfig.cryptType = FATApiCryptTypeMD5; 41 | } 42 | storeConfig.encryptServerData = [dict[@"encryptServerData"] boolValue]; 43 | [storeArrayM addObject:storeConfig]; 44 | } 45 | config = [FATConfig configWithStoreConfigs:storeArrayM]; 46 | } else { 47 | config = [FATConfig configWithAppSecret:self.secret appKey:self.appkey]; 48 | config.apiServer = [self.apiServer copy]; 49 | config.apiPrefix = [self.apiPrefix copy]; 50 | if([self.cryptType isEqualToString: @"SM"]) 51 | { 52 | config.cryptType = FATApiCryptTypeSM; 53 | } 54 | else 55 | { 56 | config.cryptType = FATApiCryptTypeMD5; 57 | } 58 | 59 | // encryptServerData 60 | NSLog(@"encryptServerData:%d",self.encryptServerData); 61 | config.encryptServerData = self.encryptServerData; 62 | } 63 | 64 | NSLog(@"disablePermission:%d",self.disablePermission); 65 | config.disableAuthorize = self.disablePermission; 66 | config.currentUserId = [self.userId copy]; 67 | config.appletIntervalUpdateLimit = self.appletIntervalUpdateLimit; 68 | 69 | // bool debug = false, 70 | // bool bindAppletWithMainProcess = false, 71 | // List? finStoreConfigs, 72 | // UIConfig? uiConfig, 73 | // String? customWebViewUserAgent, 74 | // int appletIntervalUpdateLimit = 0, 75 | // int maxRunningApplet = 5, 76 | 77 | NSError* error = nil; 78 | FATUIConfig *uiconfig = [[FATUIConfig alloc]init]; 79 | if (_uiConfig) { 80 | if (_uiConfig[@"navigationTitleTextAttributes"]) { 81 | uiconfig.navigationTitleTextAttributes = _uiConfig[@"navigationTitleTextAttributes"]; 82 | } 83 | if (_uiConfig[@"webViewProgressBarColor"]) { 84 | uiconfig.progressBarColor = [MOPTools colorWithRGBHex:[_uiConfig[@"webViewProgressBarColor"] intValue]]; 85 | } 86 | uiconfig.hideFeedbackMenu = [_uiConfig[@"isHideFeedbackAndComplaints"] boolValue]; 87 | uiconfig.hideForwardMenu = [_uiConfig[@"isHideForwardMenu"] boolValue]; 88 | uiconfig.autoAdaptDarkMode = [_uiConfig[@"autoAdaptDarkMode"] boolValue]; 89 | uiconfig.hideShareAppletMenu = [_uiConfig[@"isHideShareAppletMenu"] boolValue]; 90 | uiconfig.appletText = _uiConfig[@"appletText"]; 91 | uiconfig.hideTransitionCloseButton = [_uiConfig[@"hideTransitionCloseButton"] boolValue]; 92 | uiconfig.disableSlideCloseAppletGesture = [_uiConfig[@"disableSlideCloseAppletGesture"] boolValue]; 93 | if (_uiConfig[@"capsuleConfig"]) { 94 | NSDictionary *capsuleConfigDic = _uiConfig[@"capsuleConfig"]; 95 | FATCapsuleConfig *capsuleConfig = [[FATCapsuleConfig alloc]init]; 96 | capsuleConfig.capsuleWidth = [capsuleConfigDic[@"capsuleWidth"] floatValue]; 97 | capsuleConfig.capsuleHeight = [capsuleConfigDic[@"capsuleHeight"] floatValue]; 98 | capsuleConfig.capsuleRightMargin = [capsuleConfigDic[@"capsuleRightMargin"] floatValue]; 99 | capsuleConfig.capsuleCornerRadius = [capsuleConfigDic[@"capsuleCornerRadius"] floatValue]; 100 | capsuleConfig.capsuleBorderWidth = [capsuleConfigDic[@"capsuleBorderWidth"] floatValue]; 101 | capsuleConfig.moreBtnWidth = [capsuleConfigDic[@"moreBtnWidth"] floatValue]; 102 | capsuleConfig.moreBtnLeftMargin = [capsuleConfigDic[@"moreBtnLeftMargin"] floatValue]; 103 | capsuleConfig.closeBtnWidth = [capsuleConfigDic[@"closeBtnWidth"] floatValue]; 104 | capsuleConfig.closeBtnLeftMargin = [capsuleConfigDic[@"closeBtnLeftMargin"] floatValue]; 105 | 106 | 107 | capsuleConfig.capsuleBorderLightColor = [MOPTools colorWithRGBHex:[capsuleConfigDic[@"capsuleBorderLightColor"] intValue]]; 108 | capsuleConfig.capsuleBorderDarkColor = [MOPTools colorWithRGBHex:[capsuleConfigDic[@"capsuleBorderDarkColor"] intValue]]; 109 | capsuleConfig.capsuleBgLightColor = [MOPTools colorWithRGBHex:[capsuleConfigDic[@"capsuleBgLightColor"] intValue]]; 110 | capsuleConfig.capsuleBgDarkColor = [MOPTools colorWithRGBHex:[capsuleConfigDic[@"capsuleBgDarkColor"] intValue]]; 111 | capsuleConfig.capsuleDividerLightColor = [MOPTools colorWithRGBHex:[capsuleConfigDic[@"capsuleDividerLightColor"] intValue]]; 112 | capsuleConfig.capsuleDividerDarkColor = [MOPTools colorWithRGBHex:[capsuleConfigDic[@"capsuleDividerDarkColor"] intValue]]; 113 | uiconfig.capsuleConfig = capsuleConfig; 114 | 115 | } 116 | 117 | } 118 | uiconfig.appendingCustomUserAgent = self.customWebViewUserAgent; 119 | 120 | // uiconfig.moreMenuStyle = FATMoreViewStyleNormal; 121 | [[FATClient sharedClient] initWithConfig:config uiConfig:uiconfig error:&error]; 122 | if (error) { 123 | failure(@"初始化失败"); 124 | return; 125 | } 126 | // [[FATExtClient sharedClient] fat_prepareExtensionApis]; 127 | [[FATClient sharedClient].logManager initLogWithLogDir:nil logLevel:FATLogLevelVerbose consoleLog:YES]; 128 | 129 | success(@{}); 130 | 131 | 132 | } 133 | @end 134 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_openApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_openApplet.h 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_openApplet : MOPBaseApi 13 | 14 | @property(nonatomic,copy)NSString* appId; 15 | @property(nonatomic,copy)NSNumber* sequence; 16 | @property(nonatomic,copy)NSDictionary* params; 17 | 18 | @end 19 | 20 | NS_ASSUME_NONNULL_END 21 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_openApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_openApplet.m 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOP_openApplet.h" 9 | #import "MOPTools.h" 10 | #import 11 | 12 | @implementation MOP_openApplet 13 | 14 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 15 | { 16 | UIViewController *currentVC = [MOPTools topViewController]; 17 | 18 | // 打开小程序 19 | if (self.sequence == nil) { 20 | [[FATClient sharedClient] startRemoteApplet:self.appId startParams:self.params InParentViewController:currentVC completion:^(BOOL result, NSError *error) { 21 | NSLog(@"result:%d---error:%@", result, error); 22 | if (result){ 23 | success(@{}); 24 | }else { 25 | failure(error.description); 26 | } 27 | }]; 28 | }else{ 29 | [[FATClient sharedClient] startRemoteApplet:self.appId sequence:self.sequence startParams:self.params InParentViewController:currentVC transitionStyle:FATTranstionStyleUp animated:YES completion:^(BOOL result, NSError *error) { 30 | NSLog(@"result:%d---error:%@", result, error); 31 | if (result){ 32 | success(@{}); 33 | }else { 34 | failure(error.description); 35 | } 36 | }]; 37 | 38 | } 39 | } 40 | @end 41 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_parseAppletInfoFromWXQrCode.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_parseWXQrCode.h 3 | // mop 4 | // 5 | // Created by EDY on 2021/6/22. 6 | // 7 | 8 | #import 9 | #import "MOPBaseApi.h" 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOP_parseAppletInfoFromWXQrCode : MOPBaseApi 14 | @property(nonatomic,copy)NSString* qrCode; //二维码url 15 | @property(nonatomic,copy)NSString* apiServer; //服务器地址 16 | @end 17 | 18 | NS_ASSUME_NONNULL_END 19 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_parseAppletInfoFromWXQrCode.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_parseWXQrCode.m 3 | // mop 4 | // 5 | // Created by EDY on 2021/6/22. 6 | // 7 | 8 | #import "MOP_parseAppletInfoFromWXQrCode.h" 9 | #import "MOPTools.h" 10 | #import 11 | 12 | @implementation MOP_parseAppletInfoFromWXQrCode 13 | 14 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel { 15 | NSLog(@"MOP_parseWXQrCode:%@", self.qrCode); 16 | [[FATClient sharedClient] parseAppletInfoFromWXQrCode:self.qrCode apiServer:self.apiServer completion:^(FATAppletSimpleInfo *appInfo, FATError *aError) { 17 | if (aError) { 18 | failure(aError.description); 19 | }else{ 20 | NSMutableDictionary *dataDic = [[NSMutableDictionary alloc]init]; 21 | if (appInfo && appInfo.appId) { 22 | [dataDic setObject:appInfo.appId forKey:@"appId"]; 23 | } 24 | success(dataDic); 25 | } 26 | }]; 27 | } 28 | 29 | @end 30 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_qrcodeOpenApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_scanOpenApplet.h 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/6/7. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_qrcodeOpenApplet : MOPBaseApi 13 | 14 | @property (nonatomic,copy) NSString *qrcode; 15 | @property (nonatomic,copy) NSString *reLaunchMode; 16 | 17 | @end 18 | 19 | NS_ASSUME_NONNULL_END 20 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_qrcodeOpenApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_scanOpenApplet.m 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/6/7. 6 | // 7 | 8 | #import "MOP_qrcodeOpenApplet.h" 9 | #import "MOPTools.h" 10 | #import 11 | 12 | @implementation MOP_qrcodeOpenApplet 13 | 14 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel { 15 | NSLog(@"MOP_qrcodeOpenApplet:%@", self.qrcode); 16 | FATAppletQrCodeRequest *qrcodeRequest = [[FATAppletQrCodeRequest alloc] init]; 17 | qrcodeRequest.qrCode = self.qrcode; 18 | qrcodeRequest.reLaunchMode = [self.reLaunchMode intValue]; 19 | 20 | dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ 21 | UIViewController *currentVC = [MOPTools topViewController]; 22 | [[FATClient sharedClient] startAppletWithQrCodeRequest:qrcodeRequest inParentViewController:currentVC requestBlock:^(BOOL result, FATError *error) { 23 | NSLog(@"请求完成:%@", error); 24 | } completion:^(BOOL result, FATError *error) { 25 | NSLog(@"打开完成:%@", error); 26 | if (result){ 27 | success(@{}); 28 | } else { 29 | failure(error.localizedDescription); 30 | } 31 | } closeCompletion:^{ 32 | NSLog(@"关闭"); 33 | }]; 34 | }); 35 | 36 | } 37 | 38 | @end 39 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_registerAppletHandler.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_registerAppletHandler.h 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/20. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_registerAppletHandler : MOPBaseApi 13 | 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_registerAppletHandler.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_registerAppletHandler.m 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/20. 6 | // 7 | 8 | #import "MOP_registerAppletHandler.h" 9 | #import "MopPlugin.h" 10 | #import "MOPAppletDelegate.h" 11 | #import "MOPButtonOpenTypeDelegate.h" 12 | #import 13 | 14 | @implementation MOP_registerAppletHandler 15 | 16 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 17 | { 18 | NSLog(@"MOP_registerAppletHandler"); 19 | [FATClient sharedClient].delegate = [MOPAppletDelegate instance]; 20 | [FATClient sharedClient].buttonOpenTypeDelegate = [MOPButtonOpenTypeDelegate instance]; 21 | } 22 | 23 | @end 24 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_registerExtensionApi.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_registerExtensionApi.h 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/20. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_registerExtensionApi : MOPBaseApi 13 | 14 | @property(nonatomic, copy) NSString* name; 15 | 16 | @end 17 | 18 | NS_ASSUME_NONNULL_END 19 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_registerExtensionApi.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_registerExtensionApi.m 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/4/20. 6 | // 7 | 8 | #import "MOP_registerExtensionApi.h" 9 | #import "MopPlugin.h" 10 | #import 11 | 12 | @implementation MOP_registerExtensionApi 13 | 14 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 15 | { 16 | NSLog(@"MOP_registerExtensionApi"); 17 | FlutterMethodChannel *channel = [[MopPlugin instance] methodChannel]; 18 | NSString *name = self.name; 19 | [[FATClient sharedClient] registerExtensionApi:name handler:^(FATAppletInfo *appletInfo, id param, FATExtensionApiCallback callback) { 20 | NSLog(@"channel:%@---invoke ExtensionApi:%@, param:%@", channel, name, param); 21 | NSString *api = [@"extensionApi:" stringByAppendingString:name]; 22 | [channel invokeMethod:api arguments:param result:^(id _Nullable result) { 23 | NSLog(@"extensionApi [%@] reslut:%@", name, result); 24 | // 先判断是否flutter发生错误 25 | BOOL isValid = [result isKindOfClass:[NSDictionary class]]; 26 | if (!isValid) { 27 | NSLog(@"extensionApi reslut is not NSDictionary"); 28 | callback(FATExtensionCodeFailure,nil); 29 | return; 30 | } 31 | // 再判断回调是否为失败 32 | BOOL hasError = [[result allKeys] containsObject:@"errMsg"]; 33 | if (hasError) { 34 | NSString *errMsg = result[@"errMsg"]; 35 | NSString *errPrefix = [NSString stringWithFormat:@"%@:fail", name]; 36 | BOOL isFail = [errMsg hasPrefix:errPrefix]; 37 | if (isFail) { 38 | NSLog(@"extensionApi reslut:fail"); 39 | callback(FATExtensionCodeFailure,nil); 40 | return; 41 | } 42 | } 43 | // 其他的按成功处理 44 | NSLog(@"extensionApi callback:%@",result); 45 | callback(FATExtensionCodeSuccess,result); 46 | }]; 47 | }]; 48 | success(@{}); 49 | } 50 | 51 | @end 52 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_removeAllUsedApplets.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_removeAllUsedApplets.h 3 | // mop 4 | // 5 | // Created by 胡健辉 on 2022/5/20. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_removeAllUsedApplets : MOPBaseApi 13 | 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_removeAllUsedApplets.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_removeAllUsedApplets.m 3 | // mop 4 | // 5 | // Created by 胡健辉 on 2022/5/20. 6 | // 7 | 8 | #import "MOP_removeAllUsedApplets.h" 9 | #import 10 | 11 | @implementation MOP_removeAllUsedApplets 12 | 13 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel { 14 | NSLog(@"removeAllUsedApplets"); 15 | [[FATClient sharedClient] clearLocalApplets]; 16 | [[FATClient sharedClient] clearMemoryCache]; 17 | success(@{}); 18 | } 19 | @end 20 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_removeApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_removeApplet.h 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_removeApplet : MOPBaseApi 13 | @property (nonatomic, copy) NSString *appletId; 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_removeApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_removeApplet.m 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOP_removeApplet.h" 9 | 10 | @implementation MOP_removeApplet 11 | 12 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 13 | { 14 | if (!self.appletId || self.appletId.length < 1) { 15 | failure(@{@"errMsg": @"removeApplet:fail"}); 16 | return; 17 | } 18 | FATAppletInfo *appletInfo = [[FATClient sharedClient] currentApplet]; 19 | if (appletInfo && [appletInfo.appId isEqual:self.appletId]) { 20 | [[FATClient sharedClient] closeApplet:self.appletId animated:NO completion:^{ 21 | [[FATClient sharedClient] removeAppletFromLocalCache:self.appletId]; 22 | success(@{}); 23 | }]; 24 | } else { 25 | [[FATClient sharedClient] removeAppletFromLocalCache:self.appletId]; 26 | success(@{}); 27 | } 28 | 29 | 30 | 31 | } 32 | @end 33 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_removeUsedApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_removeUsedApplet.h 3 | // mop 4 | // 5 | // Created by EDY on 2021/9/3. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_removeUsedApplet : MOPBaseApi 13 | 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_removeUsedApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_removeUsedApplet.m 3 | // mop 4 | // 5 | // Created by EDY on 2021/9/3. 6 | // 7 | 8 | #import "MOP_removeUsedApplet.h" 9 | 10 | @implementation MOP_removeUsedApplet 11 | 12 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 13 | { 14 | NSLog(@"begin"); 15 | if (!self.param || !self.param[@"appId"]) { 16 | NSLog(@"removeUsedApplet失败打印"); 17 | failure(@{@"errMsg": @"removeUsedApplet:fail 2"}); 18 | return; 19 | } 20 | [[FATClient sharedClient] removeAppletFromLocalCache:self.param[@"appId"]]; 21 | NSLog(@"removeUsedApplet成功回调"); 22 | success(@{}); 23 | } 24 | @end 25 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_scanOpenApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_scanOpenApplet.h 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/6/7. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_scanOpenApplet : MOPBaseApi 13 | 14 | @property (nonatomic,copy) NSString *info; 15 | 16 | @end 17 | 18 | NS_ASSUME_NONNULL_END 19 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_scanOpenApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_scanOpenApplet.m 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/6/7. 6 | // 7 | 8 | #import "MOP_scanOpenApplet.h" 9 | #import "MOPTools.h" 10 | #import 11 | 12 | @implementation MOP_scanOpenApplet 13 | 14 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel { 15 | NSLog(@"MOP_scanOpenApplet:%@", self.info); 16 | FATAppletDecryptRequest *req = [[FATAppletDecryptRequest alloc] init]; 17 | req.info = self.info; 18 | dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ 19 | UIViewController *currentVC = [MOPTools topViewController]; 20 | [[FATClient sharedClient] startAppletWithDecryptRequest:req InParentViewController:currentVC completion:^(BOOL result, FATError *error) { 21 | NSLog(@"打开小程序:%@", error); 22 | } closeCompletion:^{ 23 | NSLog(@"关闭小程序"); 24 | }]; 25 | }); 26 | 27 | } 28 | 29 | @end 30 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_sdkVersion.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_sdkVersion.h 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/7/22. 6 | // 7 | 8 | #import 9 | #import "MOPBaseApi.h" 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOP_sdkVersion : MOPBaseApi 14 | 15 | @end 16 | 17 | NS_ASSUME_NONNULL_END 18 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_sdkVersion.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_sdkVersion.m 3 | // mop 4 | // 5 | // Created by 康旭耀 on 2020/7/22. 6 | // 7 | 8 | #import "MOP_sdkVersion.h" 9 | #import 10 | 11 | @implementation MOP_sdkVersion 12 | 13 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 14 | { 15 | NSLog(@"sdkVersion"); 16 | NSString *version = [[FATClient sharedClient] version]; 17 | success(version); 18 | } 19 | 20 | @end 21 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_sendCustomEvent.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_sendCustomEvent.h 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_sendCustomEvent : MOPBaseApi 13 | @property (nonatomic, copy)NSString *appId; 14 | @property (nonatomic, strong) NSDictionary *eventData; 15 | @end 16 | 17 | NS_ASSUME_NONNULL_END 18 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_sendCustomEvent.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_sendCustomEvent.m 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/21. 6 | // 7 | 8 | #import "MOP_sendCustomEvent.h" 9 | 10 | @implementation MOP_sendCustomEvent 11 | 12 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 13 | { 14 | if (!self.eventData ) { 15 | failure(@{@"errMsg": @"sendCustomEvent:fail"}); 16 | return; 17 | } 18 | if (!self.appId) { 19 | [[FATClient sharedClient].nativeViewManager sendCustomEventWithDetail:self.eventData completion:^(id result, NSError *error) { 20 | if (error) { 21 | failure(@{@"errMsg": @"sendCustomEvent:fail"}); 22 | } else { 23 | success(result); 24 | } 25 | }]; 26 | } else { 27 | [[FATClient sharedClient].nativeViewManager sendCustomEventWithDetail:self.eventData applet:self.appId completion:^(id result, NSError *error) { 28 | if (error) { 29 | failure(@{@"errMsg": @"sendCustomEvent:fail"}); 30 | } else { 31 | success(result); 32 | } 33 | }]; 34 | } 35 | 36 | 37 | } 38 | @end 39 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_setFinStoreConfigs.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_setFinStoreConfigs.h 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/20. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_setFinStoreConfigs : MOPBaseApi 13 | @property(nonatomic, strong) NSArray *storeConfigs; 14 | @end 15 | 16 | NS_ASSUME_NONNULL_END 17 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_setFinStoreConfigs.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_setFinStoreConfigs.m 3 | // mop 4 | // 5 | // Created by 王滔 on 2021/12/20. 6 | // 7 | 8 | #import "MOP_setFinStoreConfigs.h" 9 | 10 | @implementation MOP_setFinStoreConfigs 11 | 12 | @end 13 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_showBotomSheetModel.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_showBotomSheetModel.h 3 | // mop 4 | // 5 | // Created by 胡健辉 on 2020/12/11. 6 | // 7 | 8 | #import 9 | #import "MOPBaseApi.h" 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOP_showBotomSheetModel : MOPBaseApi 14 | @property(nonatomic, strong) NSString *appId; 15 | 16 | @end 17 | 18 | 19 | typedef void (^MOP_shareBottomViewTypeBlock)(NSInteger type); 20 | 21 | @interface MOP_shareBottomView : UIView 22 | @property(nonatomic, copy) MOP_shareBottomViewTypeBlock didSelcetTypeBlock; 23 | 24 | + (instancetype)view; 25 | - (void)show; 26 | - (void)dismiss; 27 | 28 | @end 29 | 30 | @interface MOP_shareBottomViewCell : UICollectionViewCell 31 | @property(nonatomic, assign) NSInteger type; 32 | @property(nonatomic, strong) UIImageView *imageView; 33 | @property(nonatomic, strong) UILabel *label; 34 | 35 | 36 | @end 37 | NS_ASSUME_NONNULL_END 38 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_smsign.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_smsign.h 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/4/21. 6 | // 7 | 8 | #import 9 | #import "MOPBaseApi.h" 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOP_smsign : MOPBaseApi 14 | 15 | @property (nonatomic, copy) NSString *plainText; 16 | 17 | @end 18 | 19 | NS_ASSUME_NONNULL_END 20 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_smsign.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_smsign.m 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/4/21. 6 | // 7 | 8 | #import "MOP_smsign.h" 9 | #import 10 | 11 | @implementation MOP_smsign 12 | 13 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 14 | { 15 | NSLog(@"smsign"); 16 | NSString *signature = [[FATClient sharedClient] getSM3String:self.plainText]; 17 | NSLog(@"signature = %@", signature); 18 | success(@{@"data": signature}); 19 | } 20 | 21 | @end 22 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_startApplet.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_openApplet.h 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOP_startApplet : MOPBaseApi 13 | 14 | @property (nonatomic, copy) NSString *appletId; 15 | @property (nonatomic, copy) NSString *apiServer; 16 | @property (nonatomic, copy) NSString *sequence; 17 | @property (nonatomic, copy) NSDictionary *startParams; 18 | @property (nonatomic, copy) NSString *offlineMiniprogramZipPath; 19 | @property (nonatomic, copy) NSString *offlineFrameworkZipPath; 20 | @property (nonatomic, copy) NSString *animated; 21 | @property (nonatomic, copy) NSString *transitionStyle; 22 | @property (nonatomic, copy) NSString *reLaunchMode; 23 | 24 | @end 25 | 26 | NS_ASSUME_NONNULL_END 27 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_startApplet.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_openApplet.m 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOP_startApplet.h" 9 | #import "MOPTools.h" 10 | #import 11 | 12 | @implementation MOP_startApplet 13 | 14 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel 15 | { 16 | UIViewController *currentVC = [MOPTools topViewController]; 17 | 18 | FATAppletRequest *request = [[FATAppletRequest alloc] init]; 19 | request.appletId = self.appletId; 20 | request.apiServer = self.apiServer; 21 | request.startParams = self.startParams; 22 | if (self.sequence){ 23 | request.sequence = @([self.sequence intValue]); 24 | } 25 | request.offlineMiniprogramZipPath = self.offlineMiniprogramZipPath; 26 | request.offlineFrameworkZipPath = self.offlineFrameworkZipPath; 27 | request.animated = [self.animated boolValue]; 28 | request.transitionStyle = [self.transitionStyle intValue]; 29 | request.reLaunchMode = [self.reLaunchMode intValue]; 30 | 31 | // 启动小程序 32 | [[FATClient sharedClient] startAppletWithRequest:request InParentViewController:currentVC completion:^(BOOL result, NSError *error) { 33 | if (result){ 34 | success(@{}); 35 | } else { 36 | failure(error.description); 37 | } 38 | } closeCompletion:^(void) { 39 | 40 | }]; 41 | } 42 | @end 43 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_webViewBounces.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_webViewBounces.h 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/11/16. 6 | // 7 | 8 | #import 9 | #import "MOPBaseApi.h" 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOP_webViewBounces : MOPBaseApi 14 | 15 | @property (nonatomic, assign) bool bounces; 16 | 17 | @end 18 | 19 | NS_ASSUME_NONNULL_END 20 | -------------------------------------------------------------------------------- /ios/Classes/Api/MOP_webViewBounces.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOP_webViewBounces.m 3 | // mop 4 | // 5 | // Created by beetle_92 on 2021/11/16. 6 | // 7 | 8 | #import "MOP_webViewBounces.h" 9 | #import "MOPTools.h" 10 | 11 | @implementation MOP_webViewBounces 12 | 13 | - (void)setupApiWithSuccess:(void (^)(NSDictionary * _Nonnull))success failure:(void (^)(id _Nullable))failure cancel:(void (^)(void))cancel { 14 | UIViewController *currentVC = [MOPTools topViewController]; 15 | WKWebView *webView = [self searchWKWebView:currentVC.view]; 16 | webView.scrollView.bounces = self.bounces; 17 | } 18 | 19 | - (WKWebView *)searchWKWebView:(UIView *)view { 20 | for (UIView *subview in view.subviews) { 21 | if ([subview isKindOfClass:[WKWebView class]]) { 22 | return (WKWebView *)subview; 23 | } 24 | WKWebView *webView = [self searchWKWebView:subview]; 25 | if (webView) { 26 | return webView; 27 | } 28 | } 29 | return nil; 30 | } 31 | 32 | @end 33 | -------------------------------------------------------------------------------- /ios/Classes/Model/MopCustomMenuModel.h: -------------------------------------------------------------------------------- 1 | // 2 | // MopCustomMenuModel.h 3 | // mop 4 | // 5 | // Created by Lin on 2021/2/26. 6 | // 7 | 8 | #import 9 | #import 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MopCustomMenuModel : NSObject 14 | 15 | /** 16 | 菜单id 17 | */ 18 | @property (nonatomic, copy) NSString *menuId; 19 | 20 | /** 21 | 菜单的icon图标 22 | 我们固定菜单的大小:3倍图:90*90 23 | 图标中间小logo与图标宽度比是 5:8。 24 | 注意:菜单图标显示优先级:后台配置icon > APP注入icon 25 | */ 26 | @property (nonatomic, strong) UIImage *menuIconImage; 27 | 28 | /** 29 | 菜单的icon图标网络链接地址 30 | 我们固定菜单的大小:3倍图:90*90 31 | 图标中间小logo与图标宽度比是 5:8,供参考 32 | 注意:菜单图标显示优先级:后台配置的icon path > App注入的icon 33 | */ 34 | @property (nonatomic, copy) NSString *menuIconUrl; 35 | 36 | /** 37 | 菜单在黑暗模式下的icon图标 38 | 我们固定菜单的大小:3倍图:90*90 39 | 图标中间小logo与图标宽度比是 5:8。 40 | 注意:菜单图标显示优先级:后台配置icon > APP注入icon 41 | */ 42 | @property (nonatomic, strong) UIImage *menuIconDarkImage; 43 | 44 | /** 45 | 菜单的暗黑模式icon图标网络链接地址 46 | 我们固定菜单的大小:3倍图:90*90 47 | 图标中间小logo与图标宽度比是 5:8,供参考 48 | 注意:菜单图标显示优先级:后台配置的darkIcon path > App注入的icon 49 | */ 50 | @property (nonatomic, copy) NSString *menuDarkIconUrl; 51 | 52 | /** 53 | 菜单的标题 54 | 注意:菜单标题显示优先级:后台配置标题 > APP注入标题 55 | */ 56 | @property (nonatomic, copy) NSString *menuTitle; 57 | 58 | /** 59 | 菜单的类型 60 | FATAppletMenuStyleCommon:通用的按钮,不需要小程序提供额外信息就可以调用的,比如收藏; 61 | FATAppletMenuStyleOnMiniProgram:需要小程序配合实现的按钮,也就是说需要小程序提供额外调用参数的按钮,比如分享到微信 62 | */ 63 | @property (nonatomic, assign) FATAppletMenuStyle menuType; 64 | 65 | @end 66 | 67 | NS_ASSUME_NONNULL_END 68 | -------------------------------------------------------------------------------- /ios/Classes/Model/MopCustomMenuModel.m: -------------------------------------------------------------------------------- 1 | // 2 | // MopCustomMenuModel.m 3 | // mop 4 | // 5 | // Created by Lin on 2021/2/26. 6 | // 7 | 8 | #import "MopCustomMenuModel.h" 9 | 10 | @implementation MopCustomMenuModel 11 | 12 | - (id)copyWithZone:(NSZone *)zone 13 | { 14 | MopCustomMenuModel *model = [[MopCustomMenuModel allocWithZone:zone] init]; 15 | model.menuId = self.menuId; 16 | model.menuIconImage = self.menuIconImage; 17 | model.menuIconDarkImage = self.menuIconDarkImage; 18 | model.menuTitle = self.menuTitle; 19 | model.menuType = self.menuType; 20 | model.menuIconUrl = self.menuIconUrl; 21 | model.menuDarkIconUrl = self.menuDarkIconUrl; 22 | return model; 23 | } 24 | 25 | @end 26 | -------------------------------------------------------------------------------- /ios/Classes/MopPlugin.h: -------------------------------------------------------------------------------- 1 | #import 2 | 3 | @interface MopEventStream : NSObject 4 | - (void)send:(NSString *)channel event:(NSString *)event body:(id)body; 5 | @end 6 | 7 | @interface MopPlugin : NSObject 8 | @property MopEventStream *mopEventStreamHandler; 9 | @property FlutterMethodChannel *methodChannel; 10 | @property FlutterMethodChannel *shareMethodChannel; 11 | @property FlutterMethodChannel *shareAppletMethodChannel; 12 | @property FlutterMethodChannel *appletMethodChannel; 13 | 14 | + (instancetype) instance; 15 | @end 16 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MOPApiConverter.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOPApiConverter.h 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import 9 | #import "MOPApiRequest.h" 10 | #import "MOPBaseApi.h" 11 | 12 | NS_ASSUME_NONNULL_BEGIN 13 | 14 | @interface MOPApiConverter : NSObject 15 | + (MOPBaseApi*)apiWithRequest:(MOPApiRequest*)request; 16 | 17 | @end 18 | 19 | NS_ASSUME_NONNULL_END 20 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MOPApiConverter.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOPApiConverter.m 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOPApiConverter.h" 9 | #import 10 | 11 | @implementation MOPApiConverter 12 | + (MOPBaseApi*)apiWithRequest:(MOPApiRequest*)request 13 | { 14 | 15 | NSString* command = request.command; 16 | NSDictionary* param = request.param; 17 | 18 | //自动生成类名 19 | NSString *apiMethod = [NSString stringWithFormat:@"MOP_%@",command]; 20 | Class ApiClass = NSClassFromString(apiMethod); 21 | 22 | if (!ApiClass) { 23 | NSLog(@"MOPybridExtensionConverter Error %@",apiMethod); 24 | return nil; 25 | } 26 | 27 | MOPBaseApi *api = [[ApiClass alloc] init]; 28 | [api setValue:command forKey:@"command"]; 29 | [api setValue:param forKey:@"param"]; 30 | 31 | NSDictionary *propertyMap = @{}; 32 | NSArray *mapToKeys = propertyMap.allValues; 33 | for (NSString *datakey in param.allKeys) { 34 | @autoreleasepool { 35 | __block NSString *propertyKey = datakey; 36 | if (propertyMap && [mapToKeys containsObject:datakey]) { 37 | [propertyMap enumerateKeysAndObjectsUsingBlock:^(NSString * _Nonnull key, NSString * _Nonnull obj, BOOL * _Nonnull stop) { 38 | if (key.length && [obj isEqualToString:datakey]) { 39 | propertyKey = key; 40 | *stop = YES; 41 | } 42 | }]; 43 | } 44 | 45 | objc_property_t property = class_getProperty([api class], [propertyKey UTF8String]); 46 | if (!property) { 47 | // NSlog(@"找不到对应的属性,需要留意..."); 48 | continue; 49 | } 50 | 51 | id value = [param objectForKey:datakey]; 52 | id safetyValue = [self parseFromKeyValue:value]; 53 | if (safetyValue) { 54 | [api setValue:safetyValue forKey:propertyKey]; 55 | } 56 | } 57 | } 58 | return api; 59 | } 60 | 61 | #pragma mark - moved from WDDataSecurityManager 62 | 63 | // 作空值过滤处理-任意对象 64 | + (id)parseFromKeyValue:(id)value { 65 | //值无效 66 | if ([value isKindOfClass:[NSNull class]]) { 67 | return nil; 68 | } 69 | 70 | if ([value isKindOfClass:[NSNumber class]]) { //统一处理为字符串 71 | value = [NSString stringWithFormat:@"%@",value]; 72 | } else if ([value isKindOfClass:[NSArray class]]) { //数组 73 | value = [self parseFromArray:value]; 74 | } else if ([value isKindOfClass:[NSDictionary class]]) { //字典 75 | value = [self parseFromDictionary:value]; 76 | } 77 | 78 | return value; 79 | } 80 | 81 | 82 | // 作空值过滤处理-字典对象 83 | + (NSDictionary *)parseFromDictionary:(NSDictionary *)container { 84 | if ([container isKindOfClass:[NSDictionary class]]) { 85 | NSMutableDictionary *result = [NSMutableDictionary new]; 86 | for (id key in container.allKeys) { 87 | @autoreleasepool { 88 | id value = container[key]; 89 | 90 | id safetyValue = [self parseFromKeyValue:value]; 91 | if (!safetyValue) //如果safetyValue是字典或者数组类型,为nil值时设置成空字符串会产生崩溃 92 | { 93 | // safetyValue = @""; 94 | continue; 95 | } 96 | [result setObject:safetyValue forKey:key]; 97 | } 98 | } 99 | return result; 100 | } 101 | return container; 102 | } 103 | 104 | 105 | // 作空值过滤处理-数组对象 106 | + (NSArray *)parseFromArray:(NSArray *)container { 107 | if ([container isKindOfClass:[NSArray class]]) { 108 | NSMutableArray *result = [NSMutableArray new]; 109 | for (int i = 0; i < container.count; i++) { 110 | @autoreleasepool { 111 | id value = container[i]; 112 | 113 | id safetyValue = [self parseFromKeyValue:value]; 114 | if (!safetyValue) { 115 | safetyValue = @""; 116 | } 117 | 118 | [result addObject:safetyValue]; 119 | } 120 | } 121 | 122 | return result; 123 | } 124 | 125 | return container; 126 | } 127 | @end 128 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MOPApiRequest.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOPApiRequest.h 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOPApiRequest : NSObject 13 | 14 | /** 15 | api方法 16 | */ 17 | @property (nonatomic, copy) NSString *command; 18 | 19 | /** 20 | 请求参数 21 | */ 22 | @property (nonatomic, strong) NSDictionary *param; 23 | 24 | @end 25 | 26 | NS_ASSUME_NONNULL_END 27 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MOPApiRequest.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOPApiRequest.m 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOPApiRequest.h" 9 | 10 | @implementation MOPApiRequest 11 | 12 | @end 13 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MOPBaseApi.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOPBaseApi.h 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import 9 | #import 10 | 11 | NS_ASSUME_NONNULL_BEGIN 12 | 13 | @interface MOPBaseApi : NSObject 14 | 15 | /** 16 | api名称 17 | */ 18 | @property (nonatomic, readonly, copy) NSString * _Null_unspecified command; 19 | 20 | /** 21 | 原始参数 22 | */ 23 | @property (nonatomic, readonly, copy) NSDictionary * _Nullable param; 24 | 25 | 26 | /** 27 | 设置API, 子类重写 28 | 29 | @param success 成功回调 30 | @param failure 失败回调 31 | @param cancel 取消回调 32 | */ 33 | - (void)setupApiWithSuccess:(void(^_Null_unspecified)(NSDictionary * _Nonnull))success 34 | failure:(void(^_Null_unspecified)(id _Nullable))failure 35 | cancel:(void(^_Null_unspecified)(void))cancel; 36 | @end 37 | 38 | NS_ASSUME_NONNULL_END 39 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MOPBaseApi.m: -------------------------------------------------------------------------------- 1 | // 2 | // MOPBaseApi.m 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import "MOPBaseApi.h" 9 | 10 | @implementation MOPBaseApi 11 | 12 | - (void)setupWithCompletion:(void(^_Null_unspecified)(NSDictionary * _Nonnull))completion 13 | { 14 | //默认实现,子类重写!!! 15 | if (completion) { 16 | completion(@{}); 17 | } 18 | } 19 | 20 | - (void)setupApiWithSuccess:(void(^_Null_unspecified)(NSDictionary * _Nonnull))success 21 | failure:(void(^_Null_unspecified)(id _Nullable))failure 22 | cancel:(void(^_Null_unspecified)(void))cancel 23 | { 24 | //默认实现,子类重写!!! 25 | if (cancel) { 26 | cancel(); 27 | } 28 | 29 | if (success) { 30 | success(@{}); 31 | } 32 | 33 | if (failure) { 34 | failure(nil); 35 | } 36 | } 37 | @end 38 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MOPTools.h: -------------------------------------------------------------------------------- 1 | // 2 | // MOPTools.h 3 | // mop 4 | // 5 | // Created by 杨涛 on 2020/2/27. 6 | // 7 | 8 | #import 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | @interface MOPTools : NSObject 13 | + (UIViewController *)topViewController; 14 | + (UIViewController *)topViewController:(UIViewController *)rootViewController; 15 | 16 | + (UIColor *)colorWithRGBHex:(UInt32)hex; 17 | 18 | + (UIColor *)fat_colorWithHexString:(NSString *)hexColor; 19 | 20 | + (BOOL)fat_currentLanguageIsEn; 21 | 22 | /// 设置颜色( + 暗黑模式):UIDynamicProviderColor(会随着暗黑模式/明亮模式切换自动变化颜色) 23 | /// @param lightHexString (明亮模式 的颜色值) 24 | /// @param darkHexString (暗黑模式 的颜色值) 25 | + (UIColor *)fat_dynamicColorWithLightHexString:(NSString *)lightHexString darkHexString:(NSString *)darkHexString; 26 | 27 | /// 生成image对象 28 | /// @param view 指定的view 29 | + (UIImage *)snapshotWithView:(UIView *)view; 30 | 31 | /// 根据链接生成二维码图片 32 | /// @param string 二维码的内容 33 | + (UIImage *)makeQRCodeForString:(NSString *)string; 34 | 35 | + (UIImage *)getCurrentPageImage; 36 | 37 | @end 38 | 39 | NS_ASSUME_NONNULL_END 40 | -------------------------------------------------------------------------------- /ios/Classes/Utils/MopShareView.h: -------------------------------------------------------------------------------- 1 | // 2 | // MopShareView.h 3 | // mop 4 | // 5 | // Created by 王兆耀 on 2023/1/2. 6 | // 7 | 8 | #import 9 | 10 | NS_ASSUME_NONNULL_BEGIN 11 | 12 | typedef void (^MOPshareBottomViewTypeBlock)(NSString *type); 13 | 14 | @interface MopShareView : UIView 15 | @property (nonatomic, copy) MOPshareBottomViewTypeBlock didSelcetTypeBlock; 16 | @property (nonatomic, strong) UIImage *image; 17 | @property (nonatomic, strong) NSDictionary *dataDic; 18 | + (instancetype)viewWithData:(NSDictionary *)data; 19 | - (void)show; 20 | - (void)dismiss; 21 | @end 22 | 23 | 24 | @class MOPshareBottomViewCell; 25 | 26 | @protocol MOPCellClickDelegate 27 | - (void)iconBtnDidClick:(MOPshareBottomViewCell *)cell; 28 | @end 29 | 30 | @interface MOPshareBottomViewCell : UICollectionViewCell 31 | @property (nonatomic, strong) NSString *type; 32 | @property (nonatomic, strong) UIButton *imageButton; 33 | @property (nonatomic, strong) UILabel *label; 34 | @property (nonatomic, weak) id delegate; 35 | 36 | 37 | @end 38 | 39 | NS_ASSUME_NONNULL_END 40 | -------------------------------------------------------------------------------- /ios/mop.podspec: -------------------------------------------------------------------------------- 1 | # 2 | # To learn more about a Podspec see http://guides.cocoapods.org/syntax/podspec.html 3 | # 4 | Pod::Spec.new do |s| 5 | s.name = 'mop' 6 | s.version = '0.1.1' 7 | s.summary = 'finclip miniprogram flutter sdk' 8 | s.description = <<-DESC 9 | A finclip miniprogram flutter sdk. 10 | DESC 11 | s.homepage = 'https://www.finclip.com' 12 | s.license = { :file => '../LICENSE' } 13 | s.author = { 'finogeeks' => 'contact@finogeeks.com' } 14 | s.source = { :path => '.' } 15 | s.source_files = 'Classes/**/*' 16 | s.public_header_files = 'Classes/**/*.h' 17 | s.dependency 'Flutter' 18 | s.ios.deployment_target = '9.0' 19 | 20 | s.dependency 'FinApplet' , '2.48.7' 21 | s.dependency 'FinAppletExt' , '2.48.7' 22 | end 23 | 24 | -------------------------------------------------------------------------------- /ios/mop.podspec.tpl: -------------------------------------------------------------------------------- 1 | # 2 | # To learn more about a Podspec see http://guides.cocoapods.org/syntax/podspec.html 3 | # 4 | Pod::Spec.new do |s| 5 | s.name = 'mop' 6 | s.version = '0.1.1' 7 | s.summary = 'finclip miniprogram flutter sdk' 8 | s.description = <<-DESC 9 | A finclip miniprogram flutter sdk. 10 | DESC 11 | s.homepage = 'https://www.finclip.com' 12 | s.license = { :file => '../LICENSE' } 13 | s.author = { 'finogeeks' => 'contact@finogeeks.com' } 14 | s.source = { :path => '.' } 15 | s.source_files = 'Classes/**/*' 16 | s.public_header_files = 'Classes/**/*.h' 17 | s.dependency 'Flutter' 18 | s.ios.deployment_target = '9.0' 19 | 20 | s.dependency 'FinApplet' , '__finapplet_version__' 21 | s.dependency 'FinAppletExt' , '__finapplet_version__' 22 | end 23 | 24 | -------------------------------------------------------------------------------- /lib/api.dart: -------------------------------------------------------------------------------- 1 | class CustomMenu { 2 | String menuId; 3 | String image; 4 | String? darkImage; 5 | String title; 6 | String type; 7 | 8 | CustomMenu(this.menuId, this.image, this.title, this.type); 9 | 10 | Map toJson() => 11 | {'menuId': menuId, 'image': image, 'darkImage': darkImage, 'title': title, 'type': type}; 12 | } 13 | 14 | abstract class AppletHandler { 15 | /// 16 | /// 转发小程序 17 | /// 18 | /// 19 | /// 20 | void forwardApplet(Map appletInfo); 21 | 22 | /// 23 | ///获取用户信息 24 | /// "userId" 25 | /// "nickName" 26 | /// "avatarUrl" 27 | /// "jwt" 28 | /// "accessToken" 29 | /// 30 | Future> getUserInfo(); 31 | 32 | /// 是否自定义胶囊里更多按钮的点击事件(该代理方法只对iOS端生效) 33 | bool customCapsuleMoreButtonClick(String appId); 34 | 35 | /// 获取自定义菜单 36 | Future> getCustomMenus(String appId); 37 | 38 | ///自定义菜单点击处理 39 | Future onCustomMenuClick( 40 | String appId, String path, String menuId, String appInfo); 41 | 42 | ///打开小程序 43 | Future appletDidOpen(String appId); 44 | 45 | ///getMobileNumber 46 | Future getMobileNumber(Function(dynamic params) param0); 47 | } 48 | -------------------------------------------------------------------------------- /publish.sh: -------------------------------------------------------------------------------- 1 | 2 | flutter packages pub publish --dry-run --server=https://pub.dartlang.org 3 | 4 | flutter packages pub publish --server=https://pub.dartlang.org --force -------------------------------------------------------------------------------- /pubspec.lock: -------------------------------------------------------------------------------- 1 | # Generated by pub 2 | # See https://dart.dev/tools/pub/glossary#lockfile 3 | packages: 4 | async: 5 | dependency: transitive 6 | description: 7 | name: async 8 | sha256: "947bfcf187f74dbc5e146c9eb9c0f10c9f8b30743e341481c1e2ed3ecc18c20c" 9 | url: "https://pub.dev" 10 | source: hosted 11 | version: "2.11.0" 12 | boolean_selector: 13 | dependency: transitive 14 | description: 15 | name: boolean_selector 16 | sha256: "6cfb5af12253eaf2b368f07bacc5a80d1301a071c73360d746b7f2e32d762c66" 17 | url: "https://pub.dev" 18 | source: hosted 19 | version: "2.1.1" 20 | characters: 21 | dependency: transitive 22 | description: 23 | name: characters 24 | sha256: "04a925763edad70e8443c99234dc3328f442e811f1d8fd1a72f1c8ad0f69a605" 25 | url: "https://pub.dev" 26 | source: hosted 27 | version: "1.3.0" 28 | clock: 29 | dependency: transitive 30 | description: 31 | name: clock 32 | sha256: cb6d7f03e1de671e34607e909a7213e31d7752be4fb66a86d29fe1eb14bfb5cf 33 | url: "https://pub.dev" 34 | source: hosted 35 | version: "1.1.1" 36 | collection: 37 | dependency: transitive 38 | description: 39 | name: collection 40 | sha256: a1ace0a119f20aabc852d165077c036cd864315bd99b7eaa10a60100341941bf 41 | url: "https://pub.dev" 42 | source: hosted 43 | version: "1.19.0" 44 | fake_async: 45 | dependency: transitive 46 | description: 47 | name: fake_async 48 | sha256: "511392330127add0b769b75a987850d136345d9227c6b94c96a04cf4a391bf78" 49 | url: "https://pub.dev" 50 | source: hosted 51 | version: "1.3.1" 52 | flutter: 53 | dependency: "direct main" 54 | description: flutter 55 | source: sdk 56 | version: "0.0.0" 57 | flutter_lints: 58 | dependency: "direct dev" 59 | description: 60 | name: flutter_lints 61 | sha256: b543301ad291598523947dc534aaddc5aaad597b709d2426d3a0e0d44c5cb493 62 | url: "https://pub.dev" 63 | source: hosted 64 | version: "1.0.4" 65 | flutter_plugin_android_lifecycle: 66 | dependency: "direct main" 67 | description: 68 | name: flutter_plugin_android_lifecycle 69 | sha256: "615a505aef59b151b46bbeef55b36ce2b6ed299d160c51d84281946f0aa0ce0e" 70 | url: "https://pub.dev" 71 | source: hosted 72 | version: "2.0.24" 73 | flutter_test: 74 | dependency: "direct dev" 75 | description: flutter 76 | source: sdk 77 | version: "0.0.0" 78 | leak_tracker: 79 | dependency: transitive 80 | description: 81 | name: leak_tracker 82 | sha256: "7bb2830ebd849694d1ec25bf1f44582d6ac531a57a365a803a6034ff751d2d06" 83 | url: "https://pub.dev" 84 | source: hosted 85 | version: "10.0.7" 86 | leak_tracker_flutter_testing: 87 | dependency: transitive 88 | description: 89 | name: leak_tracker_flutter_testing 90 | sha256: "9491a714cca3667b60b5c420da8217e6de0d1ba7a5ec322fab01758f6998f379" 91 | url: "https://pub.dev" 92 | source: hosted 93 | version: "3.0.8" 94 | leak_tracker_testing: 95 | dependency: transitive 96 | description: 97 | name: leak_tracker_testing 98 | sha256: "6ba465d5d76e67ddf503e1161d1f4a6bc42306f9d66ca1e8f079a47290fb06d3" 99 | url: "https://pub.dev" 100 | source: hosted 101 | version: "3.0.1" 102 | lints: 103 | dependency: transitive 104 | description: 105 | name: lints 106 | sha256: a2c3d198cb5ea2e179926622d433331d8b58374ab8f29cdda6e863bd62fd369c 107 | url: "https://pub.dev" 108 | source: hosted 109 | version: "1.0.1" 110 | matcher: 111 | dependency: transitive 112 | description: 113 | name: matcher 114 | sha256: d2323aa2060500f906aa31a895b4030b6da3ebdcc5619d14ce1aada65cd161cb 115 | url: "https://pub.dev" 116 | source: hosted 117 | version: "0.12.16+1" 118 | material_color_utilities: 119 | dependency: transitive 120 | description: 121 | name: material_color_utilities 122 | sha256: f7142bb1154231d7ea5f96bc7bde4bda2a0945d2806bb11670e30b850d56bdec 123 | url: "https://pub.dev" 124 | source: hosted 125 | version: "0.11.1" 126 | meta: 127 | dependency: transitive 128 | description: 129 | name: meta 130 | sha256: bdb68674043280c3428e9ec998512fb681678676b3c54e773629ffe74419f8c7 131 | url: "https://pub.dev" 132 | source: hosted 133 | version: "1.15.0" 134 | path: 135 | dependency: transitive 136 | description: 137 | name: path 138 | sha256: "087ce49c3f0dc39180befefc60fdb4acd8f8620e5682fe2476afd0b3688bb4af" 139 | url: "https://pub.dev" 140 | source: hosted 141 | version: "1.9.0" 142 | sky_engine: 143 | dependency: transitive 144 | description: flutter 145 | source: sdk 146 | version: "0.0.0" 147 | source_span: 148 | dependency: transitive 149 | description: 150 | name: source_span 151 | sha256: "53e943d4206a5e30df338fd4c6e7a077e02254531b138a15aec3bd143c1a8b3c" 152 | url: "https://pub.dev" 153 | source: hosted 154 | version: "1.10.0" 155 | stack_trace: 156 | dependency: transitive 157 | description: 158 | name: stack_trace 159 | sha256: "9f47fd3630d76be3ab26f0ee06d213679aa425996925ff3feffdec504931c377" 160 | url: "https://pub.dev" 161 | source: hosted 162 | version: "1.12.0" 163 | stream_channel: 164 | dependency: transitive 165 | description: 166 | name: stream_channel 167 | sha256: ba2aa5d8cc609d96bbb2899c28934f9e1af5cddbd60a827822ea467161eb54e7 168 | url: "https://pub.dev" 169 | source: hosted 170 | version: "2.1.2" 171 | string_scanner: 172 | dependency: transitive 173 | description: 174 | name: string_scanner 175 | sha256: "688af5ed3402a4bde5b3a6c15fd768dbf2621a614950b17f04626c431ab3c4c3" 176 | url: "https://pub.dev" 177 | source: hosted 178 | version: "1.3.0" 179 | term_glyph: 180 | dependency: transitive 181 | description: 182 | name: term_glyph 183 | sha256: a29248a84fbb7c79282b40b8c72a1209db169a2e0542bce341da992fe1bc7e84 184 | url: "https://pub.dev" 185 | source: hosted 186 | version: "1.2.1" 187 | test_api: 188 | dependency: transitive 189 | description: 190 | name: test_api 191 | sha256: "664d3a9a64782fcdeb83ce9c6b39e78fd2971d4e37827b9b06c3aa1edc5e760c" 192 | url: "https://pub.dev" 193 | source: hosted 194 | version: "0.7.3" 195 | vector_math: 196 | dependency: transitive 197 | description: 198 | name: vector_math 199 | sha256: "80b3257d1492ce4d091729e3a67a60407d227c27241d6927be0130c98e741803" 200 | url: "https://pub.dev" 201 | source: hosted 202 | version: "2.1.4" 203 | vm_service: 204 | dependency: transitive 205 | description: 206 | name: vm_service 207 | sha256: f6be3ed8bd01289b34d679c2b62226f63c0e69f9fd2e50a6b3c1c729a961041b 208 | url: "https://pub.dev" 209 | source: hosted 210 | version: "14.3.0" 211 | sdks: 212 | dart: ">=3.5.0 <4.0.0" 213 | flutter: ">=3.24.0" 214 | -------------------------------------------------------------------------------- /pubspec.tpl.yaml: -------------------------------------------------------------------------------- 1 | name: mop 2 | description: A Finogeeks MiniProgram Flutter SDK. 3 | version: '__mop_flutter_sdk_version__' 4 | homepage: https://github.com/finogeeks/mop-flutter-sdk 5 | 6 | environment: 7 | sdk: '>=2.12.0 <4.0.0' 8 | flutter: '>=2.2.3' 9 | 10 | dependencies: 11 | flutter: 12 | sdk: flutter 13 | flutter_plugin_android_lifecycle: ^2.0.3 14 | 15 | dev_dependencies: 16 | flutter_test: 17 | sdk: flutter 18 | flutter_lints: ^1.0.0 19 | 20 | flutter: 21 | plugin: 22 | platforms: 23 | android: 24 | package: com.finogeeks.mop 25 | pluginClass: MopPlugin 26 | ios: 27 | pluginClass: MopPlugin 28 | -------------------------------------------------------------------------------- /pubspec.yaml: -------------------------------------------------------------------------------- 1 | name: mop 2 | description: A Finogeeks MiniProgram Flutter SDK. 3 | version: '2.48.7' 4 | homepage: https://github.com/finogeeks/mop-flutter-sdk 5 | 6 | environment: 7 | sdk: '>=2.12.0 <4.0.0' 8 | flutter: '>=2.2.3' 9 | 10 | dependencies: 11 | flutter: 12 | sdk: flutter 13 | flutter_plugin_android_lifecycle: ^2.0.3 14 | 15 | dev_dependencies: 16 | flutter_test: 17 | sdk: flutter 18 | flutter_lints: ^1.0.0 19 | 20 | flutter: 21 | plugin: 22 | platforms: 23 | android: 24 | package: com.finogeeks.mop 25 | pluginClass: MopPlugin 26 | ios: 27 | pluginClass: MopPlugin 28 | -------------------------------------------------------------------------------- /tag.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | git tag |xargs git tag -d 4 | git pull --tags 5 | git tag -d $1 6 | git push origin --delete tag $1 7 | git add -u && git commit -m "add tag $1" 8 | git tag -m "$message" $1 9 | git push --follow-tags 10 | -------------------------------------------------------------------------------- /test/mop_test.dart: -------------------------------------------------------------------------------- 1 | import 'package:flutter/services.dart'; 2 | import 'package:flutter_test/flutter_test.dart'; 3 | import 'package:mop/mop.dart'; 4 | 5 | void main() { 6 | const MethodChannel channel = MethodChannel('mop'); 7 | 8 | TestWidgetsFlutterBinding.ensureInitialized(); 9 | 10 | setUp(() { 11 | channel.setMockMethodCallHandler((MethodCall methodCall) async { 12 | return '42'; 13 | }); 14 | }); 15 | 16 | tearDown(() { 17 | channel.setMockMethodCallHandler(null); 18 | }); 19 | 20 | test('getPlatformVersion', () async { 21 | expect(await Mop.instance.platformVersion, '42'); 22 | }); 23 | } 24 | -------------------------------------------------------------------------------- /trigger.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | set -e 3 | 4 | curl --location --request POST 'https://jenkins.finogeeks.club/gogs-webhook/?job=mop-flutter-sdk' \ 5 | --header 'Content-Type: application/json' \ 6 | --header 'X-Gogs-Delivery: 27ea7f4d-2778-4a01-bb69-406d063eb16b' \ 7 | --header 'X-Gogs-Event: push' \ 8 | --header 'X-Gogs-Signature: 35174c0a630bc2de140e8fbb9ce6fb60b39385fd1b72efaba304fe6609bdf9bf' \ 9 | --header 'Cookie: JSESSIONID.26488c4e=node01jpx6whum04n91ted4v0x1pf976.node0' \ 10 | --data-raw '{ 11 | "ref": "refs/heads/master", 12 | "before": "20e38c1c89da87a454a1f41ccce2e4a4c409a8b8", 13 | "after": "20e38c1c89da87a454a1f41ccce2e4a4c409a8b8", 14 | "compare_url": "", 15 | "commits": [ 16 | { 17 | "id": "20e38c1c89da87a454a1f41ccce2e4a4c409a8b8", 18 | "message": "fix\n", 19 | "url": "https://git.finogeeks.club/mop-mobile/mop-flutter-sdk/commit/20e38c1c89da87a454a1f41ccce2e4a4c409a8b8", 20 | "author": { 21 | "name": "developer", 22 | "email": "developer@finogeeks.com", 23 | "username": "" 24 | }, 25 | "committer": { 26 | "name": "developer", 27 | "email": "developer@finogeeks.com", 28 | "username": "" 29 | }, 30 | "added": null, 31 | "removed": null, 32 | "modified": [ 33 | "CHANGELOG.md", 34 | "example/.flutter-plugins-dependencies", 35 | "example/pubspec.lock", 36 | "pubspec.yaml" 37 | ], 38 | "timestamp": "0001-01-01T00:00:00Z" 39 | } 40 | ], 41 | "repository": { 42 | "id": 2487, 43 | "owner": { 44 | "id": 294, 45 | "username": "mop-mobile", 46 | "login": "mop-mobile", 47 | "full_name": "", 48 | "email": "", 49 | "avatar_url": "https://git.finogeeks.club/avatars/294" 50 | }, 51 | "name": "mop-flutter-sdk", 52 | "full_name": "mop-mobile/mop-flutter-sdk", 53 | "description": "", 54 | "private": true, 55 | "fork": false, 56 | "parent": null, 57 | "empty": false, 58 | "mirror": false, 59 | "size": 4198400, 60 | "html_url": "https://git.finogeeks.club/mop-mobile/mop-flutter-sdk", 61 | "ssh_url": "git@git.finogeeks.club:mop-mobile/mop-flutter-sdk.git", 62 | "clone_url": "https://git.finogeeks.club/mop-mobile/mop-flutter-sdk.git", 63 | "website": "", 64 | "stars_count": 0, 65 | "forks_count": 0, 66 | "watchers_count": 4, 67 | "open_issues_count": 0, 68 | "default_branch": "master", 69 | "created_at": "2020-04-13T10:51:01+08:00", 70 | "updated_at": "2021-01-19T22:37:20+08:00" 71 | }, 72 | "pusher": { 73 | "id": 2, 74 | "username": "yangtao", 75 | "login": "yangtao", 76 | "full_name": "yangtao", 77 | "email": "yangtao@finogeeks.com", 78 | "avatar_url": "https://git.finogeeks.club/avatars/2" 79 | }, 80 | "sender": { 81 | "id": 2, 82 | "username": "yangtao", 83 | "login": "yangtao", 84 | "full_name": "yangtao", 85 | "email": "yangtao@finogeeks.com", 86 | "avatar_url": "https://git.finogeeks.club/avatars/2" 87 | } 88 | }' 89 | echo "trigger success." -------------------------------------------------------------------------------- /update_version.sh: -------------------------------------------------------------------------------- 1 | export LANG=en_US.UTF-8 2 | export FASTLANE_DISABLE_COLORS=1 3 | 4 | 5 | # 接收参数并去除可能的引号 6 | version=$1 7 | iosVersion=$2 8 | androidVersion=$3 9 | 10 | #version=`git describe --abbrev=0 --tags | tr -d '\\n' | tr -d '\\t'` 11 | 12 | echo "当前版本号:${version}" 13 | echo "依赖的iOS:${iosVersion}" 14 | echo "依赖的Android:${androidVersion}" 15 | 16 | git reset --hard 17 | #git checkout ${version} 18 | 19 | # 更新 pubspec.yaml 20 | cp -r pubspec.tpl.yaml pubspec.yaml 21 | sed -i "" "s/__mop_flutter_sdk_version__/${version}/g" pubspec.yaml 22 | 23 | # 更新iOS podspec 24 | if [[ -n "$iosVersion" && "$iosVersion" != "none" ]]; then 25 | echo "更新mop.podspec====>" 26 | cp -r ios/mop.podspec.tpl ios/mop.podspec 27 | sed -i "" "s/__finapplet_version__/${iosVersion}/g" ios/mop.podspec 28 | else 29 | echo "跳过 iOS podspec 更新(未设置版本号)" 30 | fi 31 | 32 | # 更新android gradle 33 | if [[ -n "$androidVersion" && "$androidVersion" != "none" ]]; then 34 | echo "更新build.gradle====>" 35 | cp -r android/build.gradle.tpl android/build.gradle 36 | sed -i "" "s/__finapplet_version__/${androidVersion}/g" android/build.gradle 37 | else 38 | echo "跳过 Android gradle 更新(未设置版本号)" 39 | fi 40 | 41 | git remote add ssh-origin ssh://git@gitlab.finogeeks.club:2233/finclipsdk/finclip-flutter-sdk.git 42 | 43 | git add . 44 | git commit -m "update version:$version" 45 | git push ssh-origin 46 | --------------------------------------------------------------------------------