Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
DCloud
test-cross
提交
a832048f
T
test-cross
项目概览
DCloud
/
test-cross
通知
41
Star
1
Fork
1
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
T
test-cross
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
提交
a832048f
编写于
12月 21, 2023
作者:
H
hdx
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
add test_flutter_message_channel
上级
f8101d5d
变更
28
隐藏空白更改
内联
并排
Showing
28 changed file
with
1039 addition
and
0 deletion
+1039
-0
test_flutter_message_channel/.gitignore
test_flutter_message_channel/.gitignore
+43
-0
test_flutter_message_channel/.metadata
test_flutter_message_channel/.metadata
+30
-0
test_flutter_message_channel/README.md
test_flutter_message_channel/README.md
+19
-0
test_flutter_message_channel/analysis_options.yaml
test_flutter_message_channel/analysis_options.yaml
+28
-0
test_flutter_message_channel/android/.gitignore
test_flutter_message_channel/android/.gitignore
+13
-0
test_flutter_message_channel/android/app/build.gradle
test_flutter_message_channel/android/app/build.gradle
+73
-0
test_flutter_message_channel/android/app/src/debug/AndroidManifest.xml
...message_channel/android/app/src/debug/AndroidManifest.xml
+7
-0
test_flutter_message_channel/android/app/src/main/AndroidManifest.xml
..._message_channel/android/app/src/main/AndroidManifest.xml
+33
-0
test_flutter_message_channel/android/app/src/main/kotlin/com/example/test_flutter_message_channel/MainActivity.kt
.../com/example/test_flutter_message_channel/MainActivity.kt
+81
-0
test_flutter_message_channel/android/app/src/main/res/drawable-v21/launch_background.xml
...droid/app/src/main/res/drawable-v21/launch_background.xml
+12
-0
test_flutter_message_channel/android/app/src/main/res/drawable/launch_background.xml
...l/android/app/src/main/res/drawable/launch_background.xml
+12
-0
test_flutter_message_channel/android/app/src/main/res/mipmap-hdpi/ic_launcher.png
...nnel/android/app/src/main/res/mipmap-hdpi/ic_launcher.png
+0
-0
test_flutter_message_channel/android/app/src/main/res/mipmap-mdpi/ic_launcher.png
...nnel/android/app/src/main/res/mipmap-mdpi/ic_launcher.png
+0
-0
test_flutter_message_channel/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png
...nel/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png
+0
-0
test_flutter_message_channel/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
...el/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
+0
-0
test_flutter_message_channel/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
...l/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
+0
-0
test_flutter_message_channel/android/app/src/main/res/values-night/styles.xml
..._channel/android/app/src/main/res/values-night/styles.xml
+18
-0
test_flutter_message_channel/android/app/src/main/res/values/styles.xml
...essage_channel/android/app/src/main/res/values/styles.xml
+18
-0
test_flutter_message_channel/android/app/src/profile/AndroidManifest.xml
...ssage_channel/android/app/src/profile/AndroidManifest.xml
+7
-0
test_flutter_message_channel/android/build.gradle
test_flutter_message_channel/android/build.gradle
+30
-0
test_flutter_message_channel/android/gradle.properties
test_flutter_message_channel/android/gradle.properties
+3
-0
test_flutter_message_channel/android/gradle/wrapper/gradle-wrapper.properties
..._channel/android/gradle/wrapper/gradle-wrapper.properties
+5
-0
test_flutter_message_channel/android/settings.gradle
test_flutter_message_channel/android/settings.gradle
+29
-0
test_flutter_message_channel/lib/main.dart
test_flutter_message_channel/lib/main.dart
+270
-0
test_flutter_message_channel/pubspec.lock
test_flutter_message_channel/pubspec.lock
+188
-0
test_flutter_message_channel/pubspec.yaml
test_flutter_message_channel/pubspec.yaml
+90
-0
test_flutter_message_channel/test/widget_test.dart
test_flutter_message_channel/test/widget_test.dart
+30
-0
test_flutter_message_channel/test_flutter_message_channel.arm64.apk
...er_message_channel/test_flutter_message_channel.arm64.apk
+0
-0
未找到文件。
test_flutter_message_channel/.gitignore
0 → 100644
浏览文件 @
a832048f
# Miscellaneous
*.class
*.log
*.pyc
*.swp
.DS_Store
.atom/
.buildlog/
.history
.svn/
migrate_working_dir/
# IntelliJ related
*.iml
*.ipr
*.iws
.idea/
# The .vscode folder contains launch configuration and tasks you configure in
# VS Code which you may wish to be included in version control, so this line
# is commented out by default.
#.vscode/
# Flutter/Dart/Pub related
**/doc/api/
**/ios/Flutter/.last_build_id
.dart_tool/
.flutter-plugins
.flutter-plugins-dependencies
.pub-cache/
.pub/
/build/
# Symbolication related
app.*.symbols
# Obfuscation related
app.*.map.json
# Android Studio will place build artifacts here
/android/app/debug
/android/app/profile
/android/app/release
test_flutter_message_channel/.metadata
0 → 100644
浏览文件 @
a832048f
# This file tracks properties of this Flutter project.
# Used by Flutter tool to assess capabilities and perform upgrades etc.
#
# This file should be version controlled and should not be manually edited.
version:
revision: "7f20e5d18ce4cb80c621533090a7c5113f5bdc52"
channel: "stable"
project_type: app
# Tracks metadata for the flutter migrate command
migration:
platforms:
- platform: root
create_revision: 7f20e5d18ce4cb80c621533090a7c5113f5bdc52
base_revision: 7f20e5d18ce4cb80c621533090a7c5113f5bdc52
- platform: android
create_revision: 7f20e5d18ce4cb80c621533090a7c5113f5bdc52
base_revision: 7f20e5d18ce4cb80c621533090a7c5113f5bdc52
# User provided section
# List of Local paths (relative to this file) that should be
# ignored by the migrate tool.
#
# Files that are not part of the templates will be ignored by default.
unmanaged_files:
- 'lib/main.dart'
- 'ios/Runner.xcodeproj/project.pbxproj'
test_flutter_message_channel/README.md
0 → 100644
浏览文件 @
a832048f
# test_flutter_message_channel
## 测试 Flutter 读写原生对象时间消耗
-
读取测试
1.
在 原生 层创建一个联系人列表,每项有2个字段,类型为 string
2.
从 flutter 层发送消息到原生层,原生层将数据列表序列化为字符串,然后返回
3.
在 flutter 层将字符串还原为 dart 数据结构
4.
循环操作 1000 次并记录总耗时
-
读取并写回原生层
1.
在 原生 层创建一个联系人列表,每项有2个字段,类型为 string
2.
从 flutter 层发送消息到原生层,原生层将数据列表序列化为字符串,然后返回
3.
在 flutter 层将字符串还原为 dart 数据结构, 然后在序列化为字符串发送到原生层
4.
在 原生 层将字符串还原为对应的数据结构
5.
循环操作 1000 次并记录总耗时
test_flutter_message_channel/analysis_options.yaml
0 → 100644
浏览文件 @
a832048f
# This file configures the analyzer, which statically analyzes Dart code to
# check for errors, warnings, and lints.
#
# The issues identified by the analyzer are surfaced in the UI of Dart-enabled
# IDEs (https://dart.dev/tools#ides-and-editors). The analyzer can also be
# invoked from the command line by running `flutter analyze`.
# The following line activates a set of recommended lints for Flutter apps,
# packages, and plugins designed to encourage good coding practices.
include
:
package:flutter_lints/flutter.yaml
linter
:
# The lint rules applied to this project can be customized in the
# section below to disable rules from the `package:flutter_lints/flutter.yaml`
# included above or to enable additional rules. A list of all available lints
# and their documentation is published at https://dart.dev/lints.
#
# Instead of disabling a lint rule for the entire project in the
# section below, it can also be suppressed for a single line of code
# or a specific dart file by using the `// ignore: name_of_lint` and
# `// ignore_for_file: name_of_lint` syntax on the line or in the file
# producing the lint.
rules
:
# avoid_print: false # Uncomment to disable the `avoid_print` rule
# prefer_single_quotes: true # Uncomment to enable the `prefer_single_quotes` rule
# Additional information about this file can be found at
# https://dart.dev/guides/language/analysis-options
test_flutter_message_channel/android/.gitignore
0 → 100644
浏览文件 @
a832048f
gradle-wrapper.jar
/.gradle
/captures/
/gradlew
/gradlew.bat
/local.properties
GeneratedPluginRegistrant.java
# Remember to never publicly share your keystore.
# See https://flutter.dev/docs/deployment/android#reference-the-keystore-from-the-app
key.properties
**/*.keystore
**/*.jks
test_flutter_message_channel/android/app/build.gradle
0 → 100644
浏览文件 @
a832048f
plugins
{
id
"com.android.application"
id
"kotlin-android"
id
"dev.flutter.flutter-gradle-plugin"
}
def
localProperties
=
new
Properties
()
def
localPropertiesFile
=
rootProject
.
file
(
'local.properties'
)
if
(
localPropertiesFile
.
exists
())
{
localPropertiesFile
.
withReader
(
'UTF-8'
)
{
reader
->
localProperties
.
load
(
reader
)
}
}
def
flutterVersionCode
=
localProperties
.
getProperty
(
'flutter.versionCode'
)
if
(
flutterVersionCode
==
null
)
{
flutterVersionCode
=
'1'
}
def
flutterVersionName
=
localProperties
.
getProperty
(
'flutter.versionName'
)
if
(
flutterVersionName
==
null
)
{
flutterVersionName
=
'1.0'
}
android
{
namespace
"com.example.test_flutter_message_channel"
compileSdkVersion
flutter
.
compileSdkVersion
ndkVersion
flutter
.
ndkVersion
compileOptions
{
sourceCompatibility
JavaVersion
.
VERSION_1_8
targetCompatibility
JavaVersion
.
VERSION_1_8
}
kotlinOptions
{
jvmTarget
=
'1.8'
}
sourceSets
{
main
.
java
.
srcDirs
+=
'src/main/kotlin'
}
defaultConfig
{
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
applicationId
"com.example.test_flutter_message_channel"
// You can update the following values to match your application needs.
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-gradle-build-configuration.
minSdkVersion
flutter
.
minSdkVersion
targetSdkVersion
flutter
.
targetSdkVersion
versionCode
flutterVersionCode
.
toInteger
()
versionName
flutterVersionName
ndk
{
abiFilters
'arm64-v8a'
}
}
buildTypes
{
release
{
// TODO: Add your own signing config for the release build.
// Signing with the debug keys for now, so `flutter run --release` works.
signingConfig
signingConfigs
.
debug
}
}
}
flutter
{
source
'../..'
}
dependencies
{
implementation
'com.google.code.gson:gson:2.8.9'
}
test_flutter_message_channel/android/app/src/debug/AndroidManifest.xml
0 → 100644
浏览文件 @
a832048f
<manifest
xmlns:android=
"http://schemas.android.com/apk/res/android"
>
<!-- The INTERNET permission is required for development. Specifically,
the Flutter tool needs it to communicate with the running application
to allow setting breakpoints, to provide hot reload, etc.
-->
<uses-permission
android:name=
"android.permission.INTERNET"
/>
</manifest>
test_flutter_message_channel/android/app/src/main/AndroidManifest.xml
0 → 100644
浏览文件 @
a832048f
<manifest
xmlns:android=
"http://schemas.android.com/apk/res/android"
>
<application
android:label=
"test_flutter_message_channel"
android:name=
"${applicationName}"
android:icon=
"@mipmap/ic_launcher"
>
<activity
android:name=
".MainActivity"
android:exported=
"true"
android:launchMode=
"singleTop"
android:theme=
"@style/LaunchTheme"
android:configChanges=
"orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
android:hardwareAccelerated=
"true"
android:windowSoftInputMode=
"adjustResize"
>
<!-- Specifies an Android theme to apply to this Activity as soon as
the Android process has started. This theme is visible to the user
while the Flutter UI initializes. After that, this theme continues
to determine the Window background behind the Flutter UI. -->
<meta-data
android:name=
"io.flutter.embedding.android.NormalTheme"
android:resource=
"@style/NormalTheme"
/>
<intent-filter>
<action
android:name=
"android.intent.action.MAIN"
/>
<category
android:name=
"android.intent.category.LAUNCHER"
/>
</intent-filter>
</activity>
<!-- Don't delete the meta-data below.
This is used by the Flutter tool to generate GeneratedPluginRegistrant.java -->
<meta-data
android:name=
"flutterEmbedding"
android:value=
"2"
/>
</application>
</manifest>
test_flutter_message_channel/android/app/src/main/kotlin/com/example/test_flutter_message_channel/MainActivity.kt
0 → 100644
浏览文件 @
a832048f
package
com.example.test_flutter_message_channel
import
android.content.Context
import
android.hardware.Sensor
import
android.hardware.SensorManager
import
com.google.gson.Gson
import
com.google.gson.reflect.TypeToken
import
com.google.gson.annotations.SerializedName
import
io.flutter.embedding.android.FlutterActivity
import
io.flutter.embedding.engine.FlutterEngine
import
io.flutter.plugin.common.*
import
java.io.InputStream
import
java.nio.ByteBuffer
import
kotlin.math.log
class
MainActivity
:
FlutterActivity
()
{
override
fun
configureFlutterEngine
(
flutterEngine
:
FlutterEngine
)
{
// 0.1k
var
contactModel100
=
ContactModel
()
// 1k
var
contactModel1000
=
ContactModel
()
for
(
i
in
1
..
3
)
{
contactModel100
.
add
(
ContactDetails
(
"name"
,
"phone"
));
}
for
(
i
in
1
..
32
)
{
contactModel1000
.
add
(
ContactDetails
(
"name"
,
"phone"
));
}
MethodChannel
(
flutterEngine
.
dartExecutor
,
"methodChannelDemo"
)
.
setMethodCallHandler
{
call
,
result
->
when
(
call
.
method
)
{
"setContacts100"
->
{
val
contacts
:
String
?
=
call
.
argument
<
String
>(
"contacts"
);
// println(contacts!!.length.toString());
contactModel100
.
fromJson
(
contacts
!!
);
result
.
success
(
1
);
}
"setContacts1000"
->
{
val
contacts
:
String
?
=
call
.
argument
<
String
>(
"contacts"
);
// println(contacts.length); // 1025
contactModel1000
.
fromJson
(
contacts
!!
);
result
.
success
(
1
);
}
else
->
result
.
notImplemented
()
}
}
BasicMessageChannel
(
flutterEngine
.
dartExecutor
,
"jsonMessageCodecDemo"
,
JSONMessageCodec
.
INSTANCE
)
.
setMessageHandler
{
message
,
reply
->
if
(
message
==
"getContact100"
)
{
reply
.
reply
(
contactModel100
.
toJson
())
}
else
if
(
message
==
"getContact1000"
)
{
reply
.
reply
(
contactModel1000
.
toJson
())
}
else
{
reply
.
reply
(
null
)
}
}
}
}
open
class
ContactDetails
(
@SerializedName
(
"name"
)
open
var
name
:
String
,
@SerializedName
(
"phone"
)
open
var
phone
:
String
)
{}
open
class
ContactModel
{
open
var
contacts
:
MutableCollection
<
ContactDetails
>
=
mutableListOf
();
private
val
gson
=
Gson
();
open
fun
add
(
contact
:
ContactDetails
)
{
contacts
.
add
(
contact
);
}
fun
fromJson
(
jsonString
:
String
)
{
contacts
=
gson
.
fromJson
(
jsonString
,
object
:
TypeToken
<
MutableCollection
<
ContactDetails
>>()
{}.
type
);
}
fun
toJson
()
:
String
{
return
gson
.
toJson
(
mapOf
(
"contacts"
to
contacts
));
}
}
test_flutter_message_channel/android/app/src/main/res/drawable-v21/launch_background.xml
0 → 100644
浏览文件 @
a832048f
<?xml version="1.0" encoding="utf-8"?>
<!-- Modify this file to customize your launch splash screen -->
<layer-list
xmlns:android=
"http://schemas.android.com/apk/res/android"
>
<item
android:drawable=
"?android:colorBackground"
/>
<!-- You can insert your own image assets here -->
<!-- <item>
<bitmap
android:gravity="center"
android:src="@mipmap/launch_image" />
</item> -->
</layer-list>
test_flutter_message_channel/android/app/src/main/res/drawable/launch_background.xml
0 → 100644
浏览文件 @
a832048f
<?xml version="1.0" encoding="utf-8"?>
<!-- Modify this file to customize your launch splash screen -->
<layer-list
xmlns:android=
"http://schemas.android.com/apk/res/android"
>
<item
android:drawable=
"@android:color/white"
/>
<!-- You can insert your own image assets here -->
<!-- <item>
<bitmap
android:gravity="center"
android:src="@mipmap/launch_image" />
</item> -->
</layer-list>
test_flutter_message_channel/android/app/src/main/res/mipmap-hdpi/ic_launcher.png
0 → 100644
浏览文件 @
a832048f
544 字节
test_flutter_message_channel/android/app/src/main/res/mipmap-mdpi/ic_launcher.png
0 → 100644
浏览文件 @
a832048f
442 字节
test_flutter_message_channel/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png
0 → 100644
浏览文件 @
a832048f
721 字节
test_flutter_message_channel/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
0 → 100644
浏览文件 @
a832048f
1.0 KB
test_flutter_message_channel/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
0 → 100644
浏览文件 @
a832048f
1.4 KB
test_flutter_message_channel/android/app/src/main/res/values-night/styles.xml
0 → 100644
浏览文件 @
a832048f
<?xml version="1.0" encoding="utf-8"?>
<resources>
<!-- Theme applied to the Android Window while the process is starting when the OS's Dark Mode setting is on -->
<style
name=
"LaunchTheme"
parent=
"@android:style/Theme.Black.NoTitleBar"
>
<!-- Show a splash screen on the activity. Automatically removed when
the Flutter engine draws its first frame -->
<item
name=
"android:windowBackground"
>
@drawable/launch_background
</item>
</style>
<!-- Theme applied to the Android Window as soon as the process has started.
This theme determines the color of the Android Window while your
Flutter UI initializes, as well as behind your Flutter UI while its
running.
This Theme is only used starting with V2 of Flutter's Android embedding. -->
<style
name=
"NormalTheme"
parent=
"@android:style/Theme.Black.NoTitleBar"
>
<item
name=
"android:windowBackground"
>
?android:colorBackground
</item>
</style>
</resources>
test_flutter_message_channel/android/app/src/main/res/values/styles.xml
0 → 100644
浏览文件 @
a832048f
<?xml version="1.0" encoding="utf-8"?>
<resources>
<!-- Theme applied to the Android Window while the process is starting when the OS's Dark Mode setting is off -->
<style
name=
"LaunchTheme"
parent=
"@android:style/Theme.Light.NoTitleBar"
>
<!-- Show a splash screen on the activity. Automatically removed when
the Flutter engine draws its first frame -->
<item
name=
"android:windowBackground"
>
@drawable/launch_background
</item>
</style>
<!-- Theme applied to the Android Window as soon as the process has started.
This theme determines the color of the Android Window while your
Flutter UI initializes, as well as behind your Flutter UI while its
running.
This Theme is only used starting with V2 of Flutter's Android embedding. -->
<style
name=
"NormalTheme"
parent=
"@android:style/Theme.Light.NoTitleBar"
>
<item
name=
"android:windowBackground"
>
?android:colorBackground
</item>
</style>
</resources>
test_flutter_message_channel/android/app/src/profile/AndroidManifest.xml
0 → 100644
浏览文件 @
a832048f
<manifest
xmlns:android=
"http://schemas.android.com/apk/res/android"
>
<!-- The INTERNET permission is required for development. Specifically,
the Flutter tool needs it to communicate with the running application
to allow setting breakpoints, to provide hot reload, etc.
-->
<uses-permission
android:name=
"android.permission.INTERNET"
/>
</manifest>
test_flutter_message_channel/android/build.gradle
0 → 100644
浏览文件 @
a832048f
buildscript
{
ext
.
kotlin_version
=
'1.7.10'
repositories
{
google
()
mavenCentral
()
}
dependencies
{
classpath
"org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
}
}
allprojects
{
repositories
{
google
()
mavenCentral
()
}
}
rootProject
.
buildDir
=
'../build'
subprojects
{
project
.
buildDir
=
"${rootProject.buildDir}/${project.name}"
}
subprojects
{
project
.
evaluationDependsOn
(
':app'
)
}
tasks
.
register
(
"clean"
,
Delete
)
{
delete
rootProject
.
buildDir
}
test_flutter_message_channel/android/gradle.properties
0 → 100644
浏览文件 @
a832048f
org.gradle.jvmargs
=
-Xmx4G
android.useAndroidX
=
true
android.enableJetifier
=
true
test_flutter_message_channel/android/gradle/wrapper/gradle-wrapper.properties
0 → 100644
浏览文件 @
a832048f
distributionBase
=
GRADLE_USER_HOME
distributionPath
=
wrapper/dists
zipStoreBase
=
GRADLE_USER_HOME
zipStorePath
=
wrapper/dists
distributionUrl
=
https
\:
//services.gradle.org/distributions/gradle-7.5-all.zip
test_flutter_message_channel/android/settings.gradle
0 → 100644
浏览文件 @
a832048f
pluginManagement
{
def
flutterSdkPath
=
{
def
properties
=
new
Properties
()
file
(
"local.properties"
).
withInputStream
{
properties
.
load
(
it
)
}
def
flutterSdkPath
=
properties
.
getProperty
(
"flutter.sdk"
)
assert
flutterSdkPath
!=
null
,
"flutter.sdk not set in local.properties"
return
flutterSdkPath
}
settings
.
ext
.
flutterSdkPath
=
flutterSdkPath
()
includeBuild
(
"${settings.ext.flutterSdkPath}/packages/flutter_tools/gradle"
)
repositories
{
google
()
mavenCentral
()
gradlePluginPortal
()
}
plugins
{
id
"dev.flutter.flutter-gradle-plugin"
version
"1.0.0"
apply
false
}
}
plugins
{
id
"dev.flutter.flutter-plugin-loader"
version
"1.0.0"
id
"com.android.application"
version
"7.3.0"
apply
false
}
include
":app"
test_flutter_message_channel/lib/main.dart
0 → 100644
浏览文件 @
a832048f
import
'dart:convert'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/services.dart'
;
void
main
(
)
{
runApp
(
const
MyApp
());
}
class
MyApp
extends
StatelessWidget
{
const
MyApp
({
super
.
key
});
@override
Widget
build
(
BuildContext
context
)
{
return
MaterialApp
(
title:
'test flutter message channel'
,
theme:
ThemeData
(
colorScheme:
ColorScheme
.
fromSeed
(
seedColor:
Colors
.
deepPurple
),
useMaterial3:
true
,
),
home:
const
ContactPage
(),
);
}
}
class
ContactDetails
{
ContactDetails
({
required
this
.
name
,
required
this
.
phone
,
});
final
String
name
;
final
String
phone
;
factory
ContactDetails
.
fromMap
(
Map
<
String
,
dynamic
>
map
)
=>
ContactDetails
(
name:
map
[
'name'
]
as
String
,
phone:
map
[
'phone'
]
as
String
,
);
Map
<
String
,
String
>
toJson
()
=>
<
String
,
String
>{
'name'
:
name
,
'phone'
:
phone
,
};
}
class
ContactListModel
{
ContactListModel
({
required
this
.
contactList
,
});
final
List
<
ContactDetails
>
contactList
;
factory
ContactListModel
.
fromJson
(
String
jsonString
)
{
final
jsonData
=
json
.
decode
(
jsonString
)
as
Map
<
String
,
dynamic
>;
return
ContactListModel
(
contactList:
List
.
from
((
jsonData
[
'contacts'
]
as
List
).
map
<
ContactDetails
>(
(
dynamic
contactDetailsMap
)
=>
ContactDetails
.
fromMap
(
contactDetailsMap
as
Map
<
String
,
dynamic
>,
),
)),
);
}
String
toJson
()
{
String
json
=
jsonEncode
(
contactList
.
map
((
i
)
=>
i
.
toJson
()).
toList
()).
toString
();
return
json
;
}
}
class
ContactsMessageChannel
{
static
const
MethodChannel
_methodChannel
=
MethodChannel
(
'methodChannelDemo'
);
static
const
_jsonMessageCodecChannel
=
BasicMessageChannel
<
dynamic
>(
'jsonMessageCodecDemo'
,
JSONMessageCodec
());
static
void
addContactDetails
(
ContactDetails
contactDetails
)
{
_jsonMessageCodecChannel
.
send
(
contactDetails
.
toJson
());
}
static
Future
<
ContactListModel
>
getContacts
(
String
type
)
async
{
final
reply
=
await
_jsonMessageCodecChannel
.
send
(
'getContact
$type
'
);
if
(
reply
==
null
)
{
throw
PlatformException
(
code:
'INVALID'
,
message:
'Failed to get contact'
,
details:
null
,
);
}
else
{
return
ContactListModel
.
fromJson
(
reply
);
}
}
static
Future
<
int
>
setContacts
(
json
,
String
type
)
async
{
final
result
=
await
_methodChannel
.
invokeMethod
<
int
>(
'setContacts
$type
'
,
{
'contacts'
:
json
});
return
result
!;
}
}
class
ContactPage
extends
StatefulWidget
{
const
ContactPage
({
super
.
key
});
@override
State
<
ContactPage
>
createState
()
=>
_ContactPageState
();
}
class
_ContactPageState
extends
State
<
ContactPage
>
{
static
const
int
invokeCount
=
1000
;
ContactListModel
contactListModel
=
ContactListModel
(
contactList:
[]);
String
dataType
=
'1000'
;
String
dataTypeText
=
'1'
;
int
getCount
=
0
;
int
getSetCount
=
0
;
final
List
<
String
>
timeList
=
[];
_setDataType
()
async
{
setState
(()
{
if
(
dataType
==
'1000'
)
{
dataType
=
'100'
;
dataTypeText
=
'0.1'
;
}
else
{
dataType
=
'1000'
;
dataTypeText
=
'1'
;
}
//dataTypeText = (dataType / 1000).toString();
});
}
Future
<
void
>
_getContactData
()
async
{
// 记录开始时间
var
startDateTime
=
DateTime
.
now
();
// 循环调用 1000 次
for
(
int
i
=
0
;
i
<
invokeCount
;
i
++)
{
contactListModel
=
await
ContactsMessageChannel
.
getContacts
(
dataType
);
}
// 记录结束时间
var
endDateTime
=
DateTime
.
now
();
// 计算消耗的毫秒数
var
totalMilliseconds
=
endDateTime
.
difference
(
startDateTime
)
.
inMilliseconds
;
getCount
++;
timeList
.
add
(
"第
$getCount
次读取总耗时=
$totalMilliseconds
毫秒"
);
// 更新界面
setState
(()
{});
}
Future
<
void
>
_getSetContactData
()
async
{
// 记录开始时间
var
startDateTime
=
DateTime
.
now
();
// 先从Java层读取 1KB 联系人,然后序列为JSON后在Java层还原
for
(
int
i
=
0
;
i
<
invokeCount
;
i
++)
{
contactListModel
=
await
ContactsMessageChannel
.
getContacts
(
dataType
);
await
ContactsMessageChannel
.
setContacts
(
contactListModel
.
toJson
(),
dataType
);
}
// 记录结束时间
var
endDateTime
=
DateTime
.
now
();
// 计算消耗的毫秒数
var
totalMilliseconds
=
endDateTime
.
difference
(
startDateTime
)
.
inMilliseconds
;
getSetCount
++;
timeList
.
add
(
"第
$getSetCount
次读取+写入总耗时=
$totalMilliseconds
毫秒"
);
setState
(()
{});
}
@override
Widget
build
(
BuildContext
context
)
{
return
Scaffold
(
appBar:
AppBar
(
backgroundColor:
Theme
.
of
(
context
)
.
colorScheme
.
inversePrimary
,
title:
const
Text
(
'test flutter message channel'
),
),
body:
Flex
(
direction:
Axis
.
horizontal
,
crossAxisAlignment:
CrossAxisAlignment
.
start
,
mainAxisAlignment:
MainAxisAlignment
.
spaceBetween
,
children:
<
Widget
>[
Flexible
(
flex:
1
,
child:
BuildTimeListWidget
(
timeList
),
),
Flexible
(
flex:
1
,
child:
contactListModel
.
contactList
.
isEmpty
?
const
Center
(
child:
Text
(
'no data'
))
:
BuildContactListWidget
(
contactListModel
.
contactList
),
),
Flexible
(
flex:
1
,
child:
ListView
(
children:
<
Widget
>[
Container
(
height:
10
),
GestureDetector
(
behavior:
HitTestBehavior
.
opaque
,
child:
Text
(
'数据长度约
$dataTypeText
KB'
),
onTap:
()
{
_setDataType
();
},
),
Container
(
height:
10
),
const
Text
(
'循环执行 1000 次'
),
Container
(
height:
15
),
ElevatedButton
(
onPressed:
_getContactData
,
child:
const
Text
(
'读取原生对象数据'
),
),
ElevatedButton
(
onPressed:
_getSetContactData
,
child:
const
Text
(
'读取并写回原生对象'
),
),
],
),
),
],
),
// This trailing comma makes auto-formatting nicer for build methods.
);
}
}
class
BuildContactListWidget
extends
StatelessWidget
{
final
List
<
ContactDetails
>
contactList
;
const
BuildContactListWidget
(
this
.
contactList
,
{
super
.
key
});
@override
Widget
build
(
BuildContext
context
)
{
return
ListView
.
builder
(
padding:
const
EdgeInsets
.
all
(
1
),
itemCount:
contactList
.
length
,
itemBuilder:
(
context
,
index
)
{
return
ListTile
(
title:
Text
(
contactList
[
index
].
name
,
style:
const
TextStyle
(
fontSize:
12
),),
subtitle:
Text
(
contactList
[
index
].
phone
,
style:
const
TextStyle
(
fontSize:
12
),),
);
},
);
}
}
class
BuildTimeListWidget
extends
StatelessWidget
{
final
List
<
String
>
timeList
;
const
BuildTimeListWidget
(
this
.
timeList
,
{
super
.
key
});
@override
Widget
build
(
BuildContext
context
)
{
return
ListView
.
builder
(
padding:
const
EdgeInsets
.
all
(
2
),
itemCount:
timeList
.
length
,
itemBuilder:
(
context
,
index
)
{
return
ListTile
(
title:
Text
(
style:
const
TextStyle
(
fontSize:
12
),
timeList
[
index
])
);
},
);
}
}
test_flutter_message_channel/pubspec.lock
0 → 100644
浏览文件 @
a832048f
# Generated by pub
# See https://dart.dev/tools/pub/glossary#lockfile
packages:
async:
dependency: transitive
description:
name: async
sha256: "947bfcf187f74dbc5e146c9eb9c0f10c9f8b30743e341481c1e2ed3ecc18c20c"
url: "https://pub.flutter-io.cn"
source: hosted
version: "2.11.0"
boolean_selector:
dependency: transitive
description:
name: boolean_selector
sha256: "6cfb5af12253eaf2b368f07bacc5a80d1301a071c73360d746b7f2e32d762c66"
url: "https://pub.flutter-io.cn"
source: hosted
version: "2.1.1"
characters:
dependency: transitive
description:
name: characters
sha256: "04a925763edad70e8443c99234dc3328f442e811f1d8fd1a72f1c8ad0f69a605"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.3.0"
clock:
dependency: transitive
description:
name: clock
sha256: cb6d7f03e1de671e34607e909a7213e31d7752be4fb66a86d29fe1eb14bfb5cf
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.1.1"
collection:
dependency: transitive
description:
name: collection
sha256: ee67cb0715911d28db6bf4af1026078bd6f0128b07a5f66fb2ed94ec6783c09a
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.18.0"
cupertino_icons:
dependency: "direct main"
description:
name: cupertino_icons
sha256: d57953e10f9f8327ce64a508a355f0b1ec902193f66288e8cb5070e7c47eeb2d
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.0.6"
fake_async:
dependency: transitive
description:
name: fake_async
sha256: "511392330127add0b769b75a987850d136345d9227c6b94c96a04cf4a391bf78"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.3.1"
flutter:
dependency: "direct main"
description: flutter
source: sdk
version: "0.0.0"
flutter_lints:
dependency: "direct dev"
description:
name: flutter_lints
sha256: a25a15ebbdfc33ab1cd26c63a6ee519df92338a9c10f122adda92938253bef04
url: "https://pub.flutter-io.cn"
source: hosted
version: "2.0.3"
flutter_test:
dependency: "direct dev"
description: flutter
source: sdk
version: "0.0.0"
lints:
dependency: transitive
description:
name: lints
sha256: "0a217c6c989d21039f1498c3ed9f3ed71b354e69873f13a8dfc3c9fe76f1b452"
url: "https://pub.flutter-io.cn"
source: hosted
version: "2.1.1"
matcher:
dependency: transitive
description:
name: matcher
sha256: "1803e76e6653768d64ed8ff2e1e67bea3ad4b923eb5c56a295c3e634bad5960e"
url: "https://pub.flutter-io.cn"
source: hosted
version: "0.12.16"
material_color_utilities:
dependency: transitive
description:
name: material_color_utilities
sha256: "9528f2f296073ff54cb9fee677df673ace1218163c3bc7628093e7eed5203d41"
url: "https://pub.flutter-io.cn"
source: hosted
version: "0.5.0"
meta:
dependency: transitive
description:
name: meta
sha256: a6e590c838b18133bb482a2745ad77c5bb7715fb0451209e1a7567d416678b8e
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.10.0"
path:
dependency: transitive
description:
name: path
sha256: "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.8.3"
sky_engine:
dependency: transitive
description: flutter
source: sdk
version: "0.0.99"
source_span:
dependency: transitive
description:
name: source_span
sha256: "53e943d4206a5e30df338fd4c6e7a077e02254531b138a15aec3bd143c1a8b3c"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.10.0"
stack_trace:
dependency: transitive
description:
name: stack_trace
sha256: "73713990125a6d93122541237550ee3352a2d84baad52d375a4cad2eb9b7ce0b"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.11.1"
stream_channel:
dependency: transitive
description:
name: stream_channel
sha256: ba2aa5d8cc609d96bbb2899c28934f9e1af5cddbd60a827822ea467161eb54e7
url: "https://pub.flutter-io.cn"
source: hosted
version: "2.1.2"
string_scanner:
dependency: transitive
description:
name: string_scanner
sha256: "556692adab6cfa87322a115640c11f13cb77b3f076ddcc5d6ae3c20242bedcde"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.2.0"
term_glyph:
dependency: transitive
description:
name: term_glyph
sha256: a29248a84fbb7c79282b40b8c72a1209db169a2e0542bce341da992fe1bc7e84
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.2.1"
test_api:
dependency: transitive
description:
name: test_api
sha256: "5c2f730018264d276c20e4f1503fd1308dfbbae39ec8ee63c5236311ac06954b"
url: "https://pub.flutter-io.cn"
source: hosted
version: "0.6.1"
vector_math:
dependency: transitive
description:
name: vector_math
sha256: "80b3257d1492ce4d091729e3a67a60407d227c27241d6927be0130c98e741803"
url: "https://pub.flutter-io.cn"
source: hosted
version: "2.1.4"
web:
dependency: transitive
description:
name: web
sha256: afe077240a270dcfd2aafe77602b4113645af95d0ad31128cc02bce5ac5d5152
url: "https://pub.flutter-io.cn"
source: hosted
version: "0.3.0"
sdks:
dart: ">=3.2.1 <4.0.0"
test_flutter_message_channel/pubspec.yaml
0 → 100644
浏览文件 @
a832048f
name
:
test_flutter_message_channel
description
:
"
A
new
Flutter
project."
# The following line prevents the package from being accidentally published to
# pub.dev using `flutter pub publish`. This is preferred for private packages.
publish_to
:
'
none'
# Remove this line if you wish to publish to pub.dev
# The following defines the version and build number for your application.
# A version number is three numbers separated by dots, like 1.2.43
# followed by an optional build number separated by a +.
# Both the version and the builder number may be overridden in flutter
# build by specifying --build-name and --build-number, respectively.
# In Android, build-name is used as versionName while build-number used as versionCode.
# Read more about Android versioning at https://developer.android.com/studio/publish/versioning
# In iOS, build-name is used as CFBundleShortVersionString while build-number is used as CFBundleVersion.
# Read more about iOS versioning at
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
# In Windows, build-name is used as the major, minor, and patch parts
# of the product and file versions while build-number is used as the build suffix.
version
:
1.0.0+1
environment
:
sdk
:
'
>=3.2.1
<4.0.0'
# Dependencies specify other packages that your package needs in order to work.
# To automatically upgrade your package dependencies to the latest versions
# consider running `flutter pub upgrade --major-versions`. Alternatively,
# dependencies can be manually updated by changing the version numbers below to
# the latest version available on pub.dev. To see which dependencies have newer
# versions available, run `flutter pub outdated`.
dependencies
:
flutter
:
sdk
:
flutter
# The following adds the Cupertino Icons font to your application.
# Use with the CupertinoIcons class for iOS style icons.
cupertino_icons
:
^1.0.2
dev_dependencies
:
flutter_test
:
sdk
:
flutter
# The "flutter_lints" package below contains a set of recommended lints to
# encourage good coding practices. The lint set provided by the package is
# activated in the `analysis_options.yaml` file located at the root of your
# package. See that file for information about deactivating specific lint
# rules and activating additional ones.
flutter_lints
:
^2.0.0
# For information on the generic Dart part of this file, see the
# following page: https://dart.dev/tools/pub/pubspec
# The following section is specific to Flutter packages.
flutter
:
# The following line ensures that the Material Icons font is
# included with your application, so that you can use the icons in
# the material Icons class.
uses-material-design
:
true
# To add assets to your application, add an assets section, like this:
# assets:
# - images/a_dot_burr.jpeg
# - images/a_dot_ham.jpeg
# An image asset can refer to one or more resolution-specific "variants", see
# https://flutter.dev/assets-and-images/#resolution-aware
# For details regarding adding assets from package dependencies, see
# https://flutter.dev/assets-and-images/#from-packages
# To add custom fonts to your application, add a fonts section here,
# in this "flutter" section. Each entry in this list should have a
# "family" key with the font family name, and a "fonts" key with a
# list giving the asset and other descriptors for the font. For
# example:
# fonts:
# - family: Schyler
# fonts:
# - asset: fonts/Schyler-Regular.ttf
# - asset: fonts/Schyler-Italic.ttf
# style: italic
# - family: Trajan Pro
# fonts:
# - asset: fonts/TrajanPro.ttf
# - asset: fonts/TrajanPro_Bold.ttf
# weight: 700
#
# For details regarding fonts from package dependencies,
# see https://flutter.dev/custom-fonts/#from-packages
test_flutter_message_channel/test/widget_test.dart
0 → 100644
浏览文件 @
a832048f
// This is a basic Flutter widget test.
//
// To perform an interaction with a widget in your test, use the WidgetTester
// utility in the flutter_test package. For example, you can send tap and scroll
// gestures. You can also use WidgetTester to find child widgets in the widget
// tree, read text, and verify that the values of widget properties are correct.
import
'package:flutter/material.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:test_flutter_message_channel/main.dart'
;
void
main
(
)
{
testWidgets
(
'Counter increments smoke test'
,
(
WidgetTester
tester
)
async
{
// Build our app and trigger a frame.
await
tester
.
pumpWidget
(
const
MyApp
());
// Verify that our counter starts at 0.
expect
(
find
.
text
(
'0'
),
findsOneWidget
);
expect
(
find
.
text
(
'1'
),
findsNothing
);
// Tap the '+' icon and trigger a frame.
await
tester
.
tap
(
find
.
byIcon
(
Icons
.
add
));
await
tester
.
pump
();
// Verify that our counter has incremented.
expect
(
find
.
text
(
'0'
),
findsNothing
);
expect
(
find
.
text
(
'1'
),
findsOneWidget
);
});
}
test_flutter_message_channel/test_flutter_message_channel.arm64.apk
0 → 100644
浏览文件 @
a832048f
文件已添加
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录