commit c052a6781644f872c634d999dde76c1cf312dbac Author: akoo Date: Mon Mar 16 10:37:46 2026 +0800 Initial commit diff --git a/.hbuilderx/launch.json b/.hbuilderx/launch.json new file mode 100644 index 0000000..14b6ecf --- /dev/null +++ b/.hbuilderx/launch.json @@ -0,0 +1,11 @@ +{ + "version" : "1.0", + "configurations" : [ + { + "customPlaygroundType" : "local", + "packageName" : "airunner.mzhfkj.com", + "playground" : "standard", + "type" : "uni-app:app-android" + } + ] +} diff --git a/.tmp b/.tmp new file mode 100644 index 0000000..e69de29 diff --git a/.tmpdir/placeholder b/.tmpdir/placeholder new file mode 100644 index 0000000..e69de29 diff --git a/.todo b/.todo new file mode 100644 index 0000000..3602361 --- /dev/null +++ b/.todo @@ -0,0 +1 @@ +temp \ No newline at end of file diff --git a/AndroidManifest.xml b/AndroidManifest.xml new file mode 100644 index 0000000..109d5ee --- /dev/null +++ b/AndroidManifest.xml @@ -0,0 +1,44 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/App.uvue b/App.uvue new file mode 100644 index 0000000..2c021b8 --- /dev/null +++ b/App.uvue @@ -0,0 +1,53 @@ + + + \ No newline at end of file diff --git a/ak/PermissionManager.uts b/ak/PermissionManager.uts new file mode 100644 index 0000000..a0f389c --- /dev/null +++ b/ak/PermissionManager.uts @@ -0,0 +1,366 @@ +/** + * PermissionManager.uts + * + * Utility class for managing Android permissions throughout the app + * Handles requesting permissions, checking status, and directing users to settings + */ + +/** + * Common permission types that can be requested + */ +export enum PermissionType { + BLUETOOTH = 'bluetooth', + LOCATION = 'location', + STORAGE = 'storage', + CAMERA = 'camera', + MICROPHONE = 'microphone', + NOTIFICATIONS = 'notifications', + CALENDAR = 'calendar', + CONTACTS = 'contacts', + SENSORS = 'sensors' +} + +/** + * Result of a permission request + */ +type PermissionResult = { + granted: boolean; + grantedPermissions: string[]; + deniedPermissions: string[]; +} + +/** + * Manages permission requests and checks throughout the app + */ +export class PermissionManager { + /** + * Maps permission types to the actual Android permission strings + */ + private static getPermissionsForType(type: PermissionType): string[] { + switch (type) { + case PermissionType.BLUETOOTH: + return [ + 'android.permission.BLUETOOTH_SCAN', + 'android.permission.BLUETOOTH_CONNECT', + 'android.permission.BLUETOOTH_ADVERTISE' + ]; + case PermissionType.LOCATION: + return [ + 'android.permission.ACCESS_FINE_LOCATION', + 'android.permission.ACCESS_COARSE_LOCATION' + ]; + case PermissionType.STORAGE: + return [ + 'android.permission.READ_EXTERNAL_STORAGE', + 'android.permission.WRITE_EXTERNAL_STORAGE' + ]; + case PermissionType.CAMERA: + return ['android.permission.CAMERA']; + case PermissionType.MICROPHONE: + return ['android.permission.RECORD_AUDIO']; + case PermissionType.NOTIFICATIONS: + return ['android.permission.POST_NOTIFICATIONS']; + case PermissionType.CALENDAR: + return [ + 'android.permission.READ_CALENDAR', + 'android.permission.WRITE_CALENDAR' + ]; + case PermissionType.CONTACTS: + return [ + 'android.permission.READ_CONTACTS', + 'android.permission.WRITE_CONTACTS' + ]; + case PermissionType.SENSORS: + return ['android.permission.BODY_SENSORS']; + default: + return []; + } + } + + /** + * Get appropriate display name for a permission type + */ + private static getPermissionDisplayName(type: PermissionType): string { + switch (type) { + case PermissionType.BLUETOOTH: + return '蓝牙'; + case PermissionType.LOCATION: + return '位置'; + case PermissionType.STORAGE: + return '存储'; + case PermissionType.CAMERA: + return '相机'; + case PermissionType.MICROPHONE: + return '麦克风'; + case PermissionType.NOTIFICATIONS: + return '通知'; + case PermissionType.CALENDAR: + return '日历'; + case PermissionType.CONTACTS: + return '联系人'; + case PermissionType.SENSORS: + return '身体传感器'; + default: + return '未知权限'; + } + } + + /** + * Check if a permission is granted + * @param type The permission type to check + * @returns True if the permission is granted, false otherwise + */ + static isPermissionGranted(type: PermissionType): boolean { + // #ifdef APP-ANDROID + try { + const permissions = this.getPermissionsForType(type); + const activity = UTSAndroid.getUniActivity(); + + if (activity == null || permissions.length === 0) { + return false; + } + + // Check each permission in the group + for (const permission of permissions) { + if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) { + return false; + } + } + + return true; + } catch (e) { + console.error(`Error checking ${type} permission:`, e); + return false; + } + // #endif + + // #ifndef APP-ANDROID + return true; // Non-Android platforms don't need explicit permission checks + // #endif + } + + /** + * Request a permission from the user + * @param type The permission type to request + * @param callback Function to call with the result of the permission request + * @param showRationale Whether to show a rationale dialog if permission was previously denied + */ + static requestPermission( + type: PermissionType, + callback: (result: PermissionResult) => void, + showRationale: boolean = true + ): void { + // #ifdef APP-ANDROID + try { + const permissions = this.getPermissionsForType(type); + const activity = UTSAndroid.getUniActivity(); + + if (activity == null || permissions.length === 0) { + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: permissions + }); + return; + } + + // Check if already granted + let allGranted = true; + for (const permission of permissions) { + if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) { + allGranted = false; + break; + } + } + + if (allGranted) { + callback({ + granted: true, + grantedPermissions: permissions, + deniedPermissions: [] + }); + return; + } + + // Request the permissions + UTSAndroid.requestSystemPermission( + activity, + permissions, + (granted: boolean, grantedPermissions: string[]) => { + if (granted) { + callback({ + granted: true, + grantedPermissions: grantedPermissions, + deniedPermissions: [] + }); + } else if (showRationale) { + // Show rationale dialog + this.showPermissionRationale(type, callback); + } else { + // Just report the denial + callback({ + granted: false, + grantedPermissions: grantedPermissions, + deniedPermissions: this.getDeniedPermissions(permissions, grantedPermissions) + }); + } + }, + (denied: boolean, deniedPermissions: string[]) => { + callback({ + granted: false, + grantedPermissions: this.getGrantedPermissions(permissions, deniedPermissions), + deniedPermissions: deniedPermissions + }); + } + ); + } catch (e) { + console.error(`Error requesting ${type} permission:`, e); + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + }); + } + // #endif + + // #ifndef APP-ANDROID + // Non-Android platforms don't need explicit permissions + callback({ + granted: true, + grantedPermissions: this.getPermissionsForType(type), + deniedPermissions: [] + }); + // #endif + } + + /** + * Show a rationale dialog explaining why the permission is needed + */ + private static showPermissionRationale( + type: PermissionType, + callback: (result: PermissionResult) => void + ): void { + const permissionName = this.getPermissionDisplayName(type); + + uni.showModal({ + title: '权限申请', + content: `需要${permissionName}权限才能使用相关功能`, + confirmText: '去设置', + cancelText: '取消', + success: (result) => { + if (result.confirm) { + this.openAppSettings(); + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + }); + } else { + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + }); + } + } + }); + } + + /** + * Open the app settings page + */ + static openAppSettings(): void { + // #ifdef APP-ANDROID + try { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const intent = new android.content.Intent(); + intent.setAction("android.settings.APPLICATION_DETAILS_SETTINGS"); + const uri = android.net.Uri.fromParts("package", context.getPackageName(), null); + intent.setData(uri); + intent.addFlags(android.content.Intent.FLAG_ACTIVITY_NEW_TASK); + context.startActivity(intent); + } + } catch (e) { + console.error('Failed to open app settings', e); + uni.showToast({ + title: '请手动前往系统设置修改应用权限', + icon: 'none', + duration: 3000 + }); + } + // #endif + + // #ifndef APP-ANDROID + uni.showToast({ + title: '请在系统设置中管理应用权限', + icon: 'none', + duration: 2000 + }); + // #endif + } + + /** + * Helper to get the list of granted permissions + */ + private static getGrantedPermissions(allPermissions: string[], deniedPermissions: string[]): string[] { + return allPermissions.filter(p => !deniedPermissions.includes(p)); + } + + /** + * Helper to get the list of denied permissions + */ + private static getDeniedPermissions(allPermissions: string[], grantedPermissions: string[]): string[] { + return allPermissions.filter(p => !grantedPermissions.includes(p)); + } + + /** + * Request multiple permission types at once + * @param types Array of permission types to request + * @param callback Function to call when all permissions have been processed + */ + static requestMultiplePermissions( + types: PermissionType[], + callback: (results: Map) => void + ): void { + if (types.length === 0) { + callback(new Map()); + return; + } + + const results = new Map(); + let remaining = types.length; + + for (const type of types) { + this.requestPermission( + type, + (result) => { + results.set(type, result); + remaining--; + + if (remaining === 0) { + callback(results); + } + }, + true + ); + } + } + + /** + * Convenience method to request Bluetooth permissions + * @param callback Function to call after the permission request + */ + static requestBluetoothPermissions(callback: (granted: boolean) => void): void { + this.requestPermission(PermissionType.BLUETOOTH, (result) => { + // For Bluetooth, we also need location permissions on Android + if (result.granted) { + this.requestPermission(PermissionType.LOCATION, (locationResult) => { + callback(locationResult.granted); + }); + } else { + callback(false); + } + }); + } +} \ No newline at end of file diff --git a/ak/sqlite.uts b/ak/sqlite.uts new file mode 100644 index 0000000..4f3ca3f --- /dev/null +++ b/ak/sqlite.uts @@ -0,0 +1,81 @@ +import { createSQLiteContext } from '../uni_modules/ak-sqlite/utssdk/app-android/index.uts' +import { createSQLiteContextOptions } from '../uni_modules/ak-sqlite/utssdk/interface.uts' +//创建查询的上下文 +export const sqliteContext = createSQLiteContext({ + name: 'ble.db', +} as createSQLiteContextOptions); + +// 初始化所有表 +export function initTables() { + const sql = ` + + CREATE TABLE IF NOT EXISTS ble_event_log ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + device_id TEXT, + event_type TEXT, + detail TEXT, + timestamp INTEGER + ); + CREATE TABLE IF NOT EXISTS ble_data_log ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + device_id TEXT, + service_id TEXT, + char_id TEXT, + direction TEXT, + data TEXT, + timestamp INTEGER + ); + `; + console.log(sql); // 打印建表语句,便于调试 + sqliteContext.executeSql({ + sql: sql, + success: function(res) { console.log('SQLite表已创建', res); }, + fail: function(err) { console.error('SQLite表创建失败', err); } + }); +} + +// 测试插入一条 ble_data_log 日志 +export function testInsertDataLog() { + sqliteContext.executeSql({ + sql: ` + INSERT INTO ble_data_log (device_id, service_id, char_id, direction, data, timestamp) + VALUES ('test_device', 'test_service', 'test_char', 'send', 'test_data', ${Date.now()}) + `, + success: (res) => { console.log('插入 ble_data_log 成功', res); }, + fail: (err) => { console.error('插入 ble_data_log 失败', err); } + }); +} + +// 测试查询所有 ble_data_log 日志 +export function testQueryDataLog() { + sqliteContext.selectSql({ + sql: `SELECT * FROM ble_data_log ORDER BY timestamp DESC`, + success: (res) => { console.log('查询 ble_data_log 成功', res); }, + fail: (err) => { console.error('查询 ble_data_log 失败', err); } + }); +} + +// 测试更新 ble_data_log(将 data 字段改为 'updated_data',只更新最新一条) +export function testUpdateDataLog() { + sqliteContext.executeSql({ + sql: ` + UPDATE ble_data_log + SET data = 'updated_data' + WHERE id = (SELECT id FROM ble_data_log ORDER BY timestamp DESC LIMIT 1) + `, + success: (res) => { console.log('更新 ble_data_log 成功', res); }, + fail: (err) => { console.error('更新 ble_data_log 失败', err); } + }); +} + +// 测试删除 ble_data_log(删除最新一条) +export function testDeleteDataLog() { + sqliteContext.executeSql({ + sql: ` + DELETE FROM ble_data_log + WHERE id = (SELECT id FROM ble_data_log ORDER BY timestamp DESC LIMIT 1) + `, + success: (res) => { console.log('删除 ble_data_log 成功', res); }, + fail: (err) => { console.error('删除 ble_data_log 失败', err); } + }); +} diff --git a/components/blecommu.uvue.bak b/components/blecommu.uvue.bak new file mode 100644 index 0000000..cffc238 --- /dev/null +++ b/components/blecommu.uvue.bak @@ -0,0 +1,81 @@ + + + + + \ No newline at end of file diff --git a/components/ringcard.uvue b/components/ringcard.uvue new file mode 100644 index 0000000..573bbda --- /dev/null +++ b/components/ringcard.uvue @@ -0,0 +1,439 @@ + + + + + \ No newline at end of file diff --git a/ed.md b/ed.md new file mode 100644 index 0000000..ffaddb9 --- /dev/null +++ b/ed.md @@ -0,0 +1,73 @@ +直接帮我修改一个多个蓝牙设备的连接管理插件,支持以下功能: +1. 扫描设备 +2. 连接设备 +3. 断开连接 +4. 发送数据 +5. 接收数据 +6. 处理连接状态变化 +7. 处理数据接收 +8. 处理数据发送 +9. 处理错误 +10. 处理设备连接状态变化 +11. 处理数据发送状态变化 +12. 处理数据接收状态变化 + +这个连接服务需要对接多个蓝牙设备,支持多种蓝牙协议(如SLE,BLE、BR/EDR等),并且需要支持多种数据格式(如JSON、XML等)。 +这个服务在Uni_modules中按插件方式实现,需要支持多种平台(如Android、iOS、H5等)。可以先只实现h5平台的功能,后续再实现其他平台的功能。H5平台需要使用web bluetooth API实现,其他平台可以使用原生蓝牙API实现。 +这个插件命名ak-sbsrv.使用最严格的 UTS/uni-app-x规范进行开发。参考https://doc.dcloud.net.cn/uni-app-x/uts/ +上层操控使用interface.uts的插件规范来处理(https://doc.dcloud.net.cn/uni-app-x/plugin/uts-plugin.html)。使用强类型的ts进行开发,使用uni-app-x的ts规范进行开发(https://doc.dcloud.net.cn/uni-app-x/uts/)。特别需要注意的是,uni-app-x的ts规范和typescript的ts规范有很大的区别,特别是在类型定义方面。需要使用uni-app-x的ts规范进行开发。 +uni-app-x插件的区分平台是在 /utssdk/下。 +h5为 /utssdk/web下。 +android为 /utssdk/app-android下。 +ios为 /utssdk/app-ios下。 +尽量少用interface,用type 来代替 + +从ak-sbsrv的android的代码看,我需要达到的几个目的都没有达到 +1.希望通过interface.uts管理整个蓝牙服务. +2.这个蓝牙服务可以管理多个蓝牙连接,维持状态。 +3.通过回调函数来获取蓝牙状态及蓝牙的notification +4.通过不同的protocol-handler来连接不同协议的设备。 + + +bluetoothService增加一个自动连接的函数,根据deviceid ,从connect开始就自动连接,连接成功后获取service,然后从data-processor中获取私有service id模板,然后执行获取charater, 最后注册可写协议char和notification.后续的业务就围绕可写char和notification展开 + +在血氧检测中,**红色PPG、红外PPG、XYZ加速度**各自有重要的生理和信号学意义: + +--- + +### 1. 红色PPG(Red PPG)与红外PPG(IR PPG) + +- **PPG(光电容积描记)**信号是通过光照射皮肤,检测血液流动引起的光吸收变化,反映脉搏波动。 +- **红色PPG**(一般波长660nm)和**红外PPG**(一般波长940nm)分别对血红蛋白和氧合血红蛋白有不同吸收特性。 +- **血氧饱和度(SpO₂)**的计算,正是基于红光和红外光的吸收比值。 + - 红光/红外光的比值变化 → 反映血液中氧合/还原血红蛋白比例 → 计算出血氧。 +- **异常波形**(如幅度异常、形态畸变、无脉搏波)可能提示: + - 血流灌注差(如休克、低温、外周循环障碍) + - 心律失常(如心跳不齐、心搏骤停) + - 佩戴不良或运动伪影 + +--- + +### 2. XYZ加速度 + +- **XYZ加速度**反映手指/手腕/设备的三维运动状态。 +- 主要作用: + - **运动伪影识别**:运动时PPG信号易受干扰,通过加速度信号可辅助算法识别并滤除运动伪影,提高血氧和心率测量准确性。 + - **佩戴状态判断**:静止时加速度变化小,剧烈运动或脱落时加速度变化大。 + - **辅助健康分析**:可用于分析活动量、睡眠、跌倒等。 + +--- + +### 3. 能否发现身体状况? + +- **血氧异常**:持续低血氧(如SpO₂<90%)提示呼吸系统、心血管系统疾病风险,如慢阻肺、睡眠呼吸暂停、心衰等。 +- **脉搏波异常**:PPG波形异常可提示心律失常、外周循环障碍等。 +- **运动/静止状态**:加速度结合PPG可区分真实生理异常和运动伪影,辅助医生或AI判断异常原因。 +- **AI分析**:结合大量PPG和加速度数据,AI可进一步识别心律失常、血管硬化、微循环障碍等风险。 + +--- + +**总结:** +- 红色PPG和红外PPG用于计算血氧和心率,是血氧仪的核心信号。 +- XYZ加速度用于识别运动伪影、判断佩戴状态、辅助健康分析。 +- 这些指标结合,可更准确地反映身体状况,发现异常信号时建议进一步医学检查。 diff --git a/index.html b/index.html new file mode 100644 index 0000000..8ac465c --- /dev/null +++ b/index.html @@ -0,0 +1,20 @@ + + + + + + + + + + +
+ + + \ No newline at end of file diff --git a/main.uts b/main.uts new file mode 100644 index 0000000..8bdcc86 --- /dev/null +++ b/main.uts @@ -0,0 +1,9 @@ +import App from './App.uvue' + +import { createSSRApp } from 'vue' +export function createApp() { + const app = createSSRApp(App) + return { + app + } +} \ No newline at end of file diff --git a/manifest.json b/manifest.json new file mode 100644 index 0000000..861640e --- /dev/null +++ b/manifest.json @@ -0,0 +1,71 @@ +{ + "name": "akbleserver", + "appid": "__UNI__95B2570", + "description": "", + "versionName": "1.0.1", + "versionCode": "101", + "uni-app-x": {}, + /* 快应用特有相关 */ + "quickapp": {}, + /* 小程序特有相关 */ + "mp-weixin": { + "appid": "", + "setting": { + "urlCheck": false + }, + "usingComponents": true + }, + "mp-alipay": { + "usingComponents": true + }, + "mp-baidu": { + "usingComponents": true + }, + "mp-toutiao": { + "usingComponents": true + }, + "uniStatistics": { + "enable": false + }, + "vueVersion": "3", + "app": { + "distribute": { + "icons": { + "android": { + "hdpi": "unpackage/res/icons/72x72.png", + "xhdpi": "unpackage/res/icons/96x96.png", + "xxhdpi": "unpackage/res/icons/144x144.png", + "xxxhdpi": "unpackage/res/icons/192x192.png" + }, + "ios": { + "appstore": "unpackage/res/icons/1024x1024.png" + } + } + } + }, + "app-android": { + "distribute": { + "modules": { + "FileSystem": {} + }, + "icons": { + "hdpi": "unpackage/res/icons/72x72.png", + "xhdpi": "unpackage/res/icons/96x96.png", + "xxhdpi": "unpackage/res/icons/144x144.png", + "xxxhdpi": "unpackage/res/icons/192x192.png" + }, + "splashScreens": { + "default": {} + } + } + }, + "app-ios": { + "distribute": { + "modules": {}, + "icons": { + "appstore": "unpackage/res/icons/1024x1024.png" + }, + "splashScreens": {} + } + } +} \ No newline at end of file diff --git a/pages.json b/pages.json new file mode 100644 index 0000000..6b4d590 --- /dev/null +++ b/pages.json @@ -0,0 +1,36 @@ +{ + "pages": [ + // { + // "path": "pages/alldevices", + // "style": { + // "navigationBarTitleText": "全体都有" + // } + // } + // , + // { + // "path": "components/blecommu", + // "style": { + // "navigationBarTitleText": "蓝牙通信" + // } + // }, + { + "path": "pages/akbletest", + "style": { + "navigationBarTitleText": "akble" + } + } + // { + // "path": "pages/control", + // "style": { + // "navigationBarTitleText": "uni-app x" + // } + // } + ], + "globalStyle": { + "navigationBarTextStyle": "black", + "navigationBarTitleText": "体测训练", + "navigationBarBackgroundColor": "#F8F8F8", + "backgroundColor": "#F8F8F8" + }, + "uniIdRouter": {} +} \ No newline at end of file diff --git a/pages/akbletest.uvue b/pages/akbletest.uvue new file mode 100644 index 0000000..c1dd5bb --- /dev/null +++ b/pages/akbletest.uvue @@ -0,0 +1,728 @@ + + + + + \ No newline at end of file diff --git a/pages/alldevices.uvue b/pages/alldevices.uvue new file mode 100644 index 0000000..9089d29 --- /dev/null +++ b/pages/alldevices.uvue @@ -0,0 +1,218 @@ + + + + + \ No newline at end of file diff --git a/pages/control.uvue b/pages/control.uvue new file mode 100644 index 0000000..2afca49 --- /dev/null +++ b/pages/control.uvue @@ -0,0 +1,963 @@ + + + + + diff --git a/platformConfig.json b/platformConfig.json new file mode 100644 index 0000000..896f669 --- /dev/null +++ b/platformConfig.json @@ -0,0 +1,7 @@ + +// 参考链接 https://doc.dcloud.net.cn/uni-app-x/tutorial/ls-plugin.html#setting +{ + "targets": [ + "APP-ANDROID" + ] +} \ No newline at end of file diff --git a/static/OmFw2509140009.zip b/static/OmFw2509140009.zip new file mode 100644 index 0000000..5b7b661 Binary files /dev/null and b/static/OmFw2509140009.zip differ diff --git a/static/OmFw2510150943.zip b/static/OmFw2510150943.zip new file mode 100644 index 0000000..dacb75e Binary files /dev/null and b/static/OmFw2510150943.zip differ diff --git a/static/logo.png b/static/logo.png new file mode 100644 index 0000000..b5771e2 Binary files /dev/null and b/static/logo.png differ diff --git a/uni.scss b/uni.scss new file mode 100644 index 0000000..b9249e9 --- /dev/null +++ b/uni.scss @@ -0,0 +1,76 @@ +/** + * 这里是uni-app内置的常用样式变量 + * + * uni-app 官方扩展插件及插件市场(https://ext.dcloud.net.cn)上很多三方插件均使用了这些样式变量 + * 如果你是插件开发者,建议你使用scss预处理,并在插件代码中直接使用这些变量(无需 import 这个文件),方便用户通过搭积木的方式开发整体风格一致的App + * + */ + +/** + * 如果你是App开发者(插件使用者),你可以通过修改这些变量来定制自己的插件主题,实现自定义主题功能 + * + * 如果你的项目同样使用了scss预处理,你也可以直接在你的 scss 代码中使用如下变量,同时无需 import 这个文件 + */ + +/* 颜色变量 */ + +/* 行为相关颜色 */ +$uni-color-primary: #007aff; +$uni-color-success: #4cd964; +$uni-color-warning: #f0ad4e; +$uni-color-error: #dd524d; + +/* 文字基本颜色 */ +$uni-text-color:#333;//基本色 +$uni-text-color-inverse:#fff;//反色 +$uni-text-color-grey:#999;//辅助灰色,如加载更多的提示信息 +$uni-text-color-placeholder: #808080; +$uni-text-color-disable:#c0c0c0; + +/* 背景颜色 */ +$uni-bg-color:#ffffff; +$uni-bg-color-grey:#f8f8f8; +$uni-bg-color-hover:#f1f1f1;//点击状态颜色 +$uni-bg-color-mask:rgba(0, 0, 0, 0.4);//遮罩颜色 + +/* 边框颜色 */ +$uni-border-color:#c8c7cc; + +/* 尺寸变量 */ + +/* 文字尺寸 */ +$uni-font-size-sm:12px; +$uni-font-size-base:14px; +$uni-font-size-lg:16px; + +/* 图片尺寸 */ +$uni-img-size-sm:20px; +$uni-img-size-base:26px; +$uni-img-size-lg:40px; + +/* Border Radius */ +$uni-border-radius-sm: 2px; +$uni-border-radius-base: 3px; +$uni-border-radius-lg: 6px; +$uni-border-radius-circle: 50%; + +/* 水平间距 */ +$uni-spacing-row-sm: 5px; +$uni-spacing-row-base: 10px; +$uni-spacing-row-lg: 15px; + +/* 垂直间距 */ +$uni-spacing-col-sm: 4px; +$uni-spacing-col-base: 8px; +$uni-spacing-col-lg: 12px; + +/* 透明度 */ +$uni-opacity-disabled: 0.3; // 组件禁用态的透明度 + +/* 文章场景相关 */ +$uni-color-title: #2C405A; // 文章标题颜色 +$uni-font-size-title:20px; +$uni-color-subtitle: #555555; // 二级标题颜色 +$uni-font-size-subtitle:26px; +$uni-color-paragraph: #3F536E; // 文章段落颜色 +$uni-font-size-paragraph:15px; diff --git a/uni_modules/ak-charts/README.md b/uni_modules/ak-charts/README.md new file mode 100644 index 0000000..2fb7f5e --- /dev/null +++ b/uni_modules/ak-charts/README.md @@ -0,0 +1,28 @@ +# ak-charts + +一个简单的 uni_modules 图表插件,支持基础柱状图和折线图,UTS 插件规范。 + +## 使用方法 + +1. 在页面中引用组件: + ````vue + + ```` + +2. 通过 AkCharts.render(option, canvasId) 进行全局渲染调用。 + +option 示例: +```js +{ + type: 'bar', // 或 'line' + data: [10, 20, 30], + labels: ['A', 'B', 'C'], + color: '#2196f3' +} +``` + +## 目录结构 +- index.uts 插件主入口 +- components/ak-charts/ak-charts.vue 图表组件 +- package.json 插件描述 +- README.md 插件说明 \ No newline at end of file diff --git a/uni_modules/ak-charts/components/ak-charts.uvue b/uni_modules/ak-charts/components/ak-charts.uvue new file mode 100644 index 0000000..dac03f9 --- /dev/null +++ b/uni_modules/ak-charts/components/ak-charts.uvue @@ -0,0 +1,803 @@ + + + + + diff --git a/uni_modules/ak-charts/interface.uts b/uni_modules/ak-charts/interface.uts new file mode 100644 index 0000000..ccb4ce3 --- /dev/null +++ b/uni_modules/ak-charts/interface.uts @@ -0,0 +1,45 @@ +/** + * ak-charts UTS 插件主入口 + * 提供注册和渲染图表的基础接口 + */ + +export type ChartType = 'bar' | 'line' | 'pie' | 'doughnut' | 'radar'; + +export type ChartSeries = { + name: string; + data: number[]; + color?: string; +}; + +export type ChartOption = { + type: ChartType; + data?: number[]; + series?: ChartSeries[]; // 新增 + labels?: string[]; + color?: string | string[]; + centerX?: number; + centerY?: number; + radius?: number; + innerRadius?: number; // 环形图内圆半径 +} + export type Margin { + top: number; + right: number; + bottom: number; + left: number; + } +export class AkCharts { + // 注册图表(可扩展) + static register(type: ChartType, render: Function): void { + // 这里可以实现自定义图表类型注册 + } + + // 渲染图表(实际渲染由组件完成) + static render(option: ChartOption, canvasId: string): void { + // 这里只做参数校验和分发,实际渲染由 ak-charts.vue 组件实现 + // 可通过 uni.$emit/uni.$on 或全局事件通信 + uni.$emit('ak-charts-render', { option, canvasId }); + } +} + +export default AkCharts; diff --git a/uni_modules/ak-charts/package.json b/uni_modules/ak-charts/package.json new file mode 100644 index 0000000..eb8c226 --- /dev/null +++ b/uni_modules/ak-charts/package.json @@ -0,0 +1,12 @@ +{ + "name": "ak-charts", + "version": "0.1.0", + "description": "一个简单的uni_modules图表插件,支持基础柱状图和折线图,UTS插件规范。", + "uni_modules": { + "uni_modules": true, + "platforms": ["app", "h5", "mp-weixin"], + "uts": true + }, + "main": "index.uts", + "keywords": ["charts", "canvas", "uni_modules", "uts"] +} diff --git a/uni_modules/ak-sbsrv/package.json b/uni_modules/ak-sbsrv/package.json new file mode 100644 index 0000000..42cfd90 --- /dev/null +++ b/uni_modules/ak-sbsrv/package.json @@ -0,0 +1,101 @@ +{ + "id": "ak-sbsrv", + "displayName": "多蓝牙设备连接管理插件", + "version": "1.0.0", + "description": "支持多蓝牙设备连接管理的插件,可扫描、连接、发送数据等", + "keywords": [ + "蓝牙", + "设备管理", + "BLE", + "多设备", + "连接管理" + ], + "repository": "", + "engines": { + "HBuilderX": "^4.0.0", + "uni-app": "^3.1.0", + "uni-app-x": "^3.1.0" + }, + "dcloudext": { + "type": "uts-plugin", + "sale": { + "regular": { + "price": "0.00" + }, + "sourcecode": { + "price": "0.00" + } + }, + "contact": { + "qq": "" + }, + "declaration": { + "ads": "无", + "data": "无", + "permissions": "设备蓝牙" + }, + "npmurl": "", + "darkmode": "-", + "i18n": "-", + "widescreen": "-" + }, + "uni_modules": { + "dependencies": [ + ], + "encrypt": [], + "platforms": { + "cloud": { + "tcb": "√", + "aliyun": "√" + }, + "client": { + "uni-app": { + "vue": { + "vue2": "-", + "vue3": "-" + }, + "web": { + "safari": "-", + "chrome": "-" + }, + "app": { + "vue": "-", + "nvue": "-", + "android": "-", + "ios": "-", + "harmony": "-" + }, + "mp": { + "weixin": "-", + "alipay": "-", + "toutiao": "-", + "baidu": "-", + "kuaishou": "-", + "jd": "-", + "harmony": "-", + "qq": "-", + "lark": "-" + }, + "quickapp": { + "huawei": "-", + "union": "-" + } + }, + "uni-app-x": { + "web": { + "safari": "-", + "chrome": "-" + }, + "app": { + "android": "-", + "ios": "-", + "harmony": "-" + }, + "mp": { + "weixin": "-" + } + } + } + } + } +} \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/readme.md b/uni_modules/ak-sbsrv/readme.md new file mode 100644 index 0000000..4987eef --- /dev/null +++ b/uni_modules/ak-sbsrv/readme.md @@ -0,0 +1,115 @@ +# ak-sbsrv + +## 介绍 + +ak-sbsrv 是一个多蓝牙设备连接管理插件,基于 uni-app-x UTS 开发,支持同时连接和管理多个蓝牙设备。 +主要特点: +- 支持多蓝牙设备的扫描、连接和通信 +- 支持多种蓝牙协议(BLE、SLE、BR/EDR等) +- 支持多种数据格式(JSON、XML、RAW等) +- 统一接口,多平台支持(目前已支持H5平台) + +## 平台支持 + +- H5 (Chrome、Edge、Safari等支持Web Bluetooth API的现代浏览器) +- Android (开发中) +- iOS (开发中) + +> 注:H5端需要在支持Web Bluetooth API的浏览器及安全上下文(HTTPS或localhost)中使用 + +## 安装使用 + +1. 在插件市场下载或通过HBuilderX导入本插件 +2. 导入到项目中 + +## API列表 + +### 基础功能 + +#### 扫描设备 +```js +import { bluetoothService } from '@/uni_modules/ak-sbsrv/utssdk/web/index.uts'; + +// 扫描设备 +const result = await bluetoothService.scanDevices(); +console.log('扫描到设备:', result.devices); +``` + +#### 连接设备 +```js +// 连接设备 +await bluetoothService.connectDevice(deviceId); +``` + +#### 断开连接 +```js +// 断开连接 +await bluetoothService.disconnectDevice(deviceId); +``` + +#### 发送数据 +```js +// 发送数据 +await bluetoothService.sendData({ + deviceId: '设备ID', + serviceId: '服务UUID', + characteristicId: '特征值UUID', + data: '要发送的数据', + format: 2 // 2代表RAW格式 +}); +``` + +### 事件监听 + +#### 监听连接状态变化 +```js +// 监听连接状态变化 +bluetoothService.onConnectionStateChange((deviceId, state) => { + console.log(`设备 ${deviceId} 连接状态变为: ${state}`); + // state: 0-断开,1-连接中,2-已连接,3-断开中 +}); +``` + +#### 监听数据接收 +```js +// 监听数据接收 +bluetoothService.onDataReceived((payload) => { + console.log('收到数据:', payload); +}); +``` + +#### 监听错误 +```js +// 监听错误 +bluetoothService.onError((error) => { + console.error('蓝牙错误:', error); +}); +``` + +### 其他API + +- `getConnectedDevices()` - 获取已连接设备列表 +- `getConnectionState(deviceId)` - 获取指定设备的连接状态 +- `listenCharacteristicNotify(deviceId, serviceId, characteristicId)` - 监听特征值通知 + +## 示例项目 + +参见仓库中的 [control.uvue](pages/control.uvue) 页面了解完整的使用示例。 + +## 常见问题 + +1. **H5中无法扫描到设备?** + 请确保浏览器支持Web Bluetooth API,且页面在HTTPS或localhost环境下运行。 + +2. **扫描后无法连接设备?** + 请确保设备在可连接范围内,且蓝牙服务已打开。 + +3. **发送数据失败?** + 请检查serviceId和characteristicId是否正确,以及特征值是否支持写入。 + +## 更新日志 + +### 1.0.0 (2025-04-24) +- 支持Web平台的蓝牙设备扫描、连接和数据收发 +- 支持多设备同时连接管理 +- 实现事件监听机制 \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts b/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts new file mode 100644 index 0000000..1d6dffe --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts @@ -0,0 +1,279 @@ +import type { + BleDevice, + BleConnectionState, + BleEvent, + BleEventCallback, + BleEventPayload, + BleScanResult, + BleConnectOptionsExt, + AutoBleInterfaces, + BleDataPayload, + SendDataPayload, + BleOptions, + MultiProtocolDevice, + ScanHandler, + BleProtocolType, + ScanDevicesOptions +} from '../interface.uts'; +import { ProtocolHandler } from '../protocol_handler.uts'; +import { BluetoothService } from '../interface.uts'; +import { DeviceManager } from './device_manager.uts'; + +// Shape used when callers register plain objects as handlers. Using a named +// type keeps member access explicit so the code generator emits valid Kotlin +// member references instead of trying to access properties on Any. +type RawProtocolHandler = { + protocol?: BleProtocolType; + scanDevices?: (options?: ScanDevicesOptions) => Promise; + connect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; + disconnect?: (device: BleDevice) => Promise; + sendData?: (device: BleDevice, payload?: SendDataPayload, options?: BleOptions) => Promise; + autoConnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; +} + +// 设备上下文 +class DeviceContext { + device : BleDevice; + protocol : BleProtocolType; + state : BleConnectionState; + handler : ProtocolHandler; + constructor(device : BleDevice, protocol : BleProtocolType, handler : ProtocolHandler) { + this.device = device; + this.protocol = protocol; + this.state = 0; // DISCONNECTED + this.handler = handler; + } +} + +const deviceMap = new Map(); // key: deviceId|protocol +// Single active protocol handler (no multi-protocol registration) +let activeProtocol: BleProtocolType = 'standard'; +let activeHandler: ProtocolHandler | null = null; +// 事件监听注册表 +const eventListeners = new Map>(); + +function emit(event : BleEvent, payload : BleEventPayload) { + if (event === 'connectionStateChanged') { + console.log('[AKBLE][LOG] bluetooth_manager.uts emit connectionStateChanged', payload) + } + const listeners = eventListeners.get(event); + if (listeners != null) { + listeners.forEach(cb => { + try { cb(payload); } catch (e) { } + }); + } +} +class ProtocolHandlerWrapper extends ProtocolHandler { + private _raw: RawProtocolHandler | null; + constructor(raw?: RawProtocolHandler) { + // pass a lightweight BluetoothService instance to satisfy generators + super(new BluetoothService()); + this._raw = (raw != null) ? raw : null; + } + override async scanDevices(options?: ScanDevicesOptions): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.scanDevices === 'function') { + await rawTyped.scanDevices(options); + } + return; + } + override async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.connect === 'function') { + await rawTyped.connect(device, options); + } + return; + } + override async disconnect(device: BleDevice): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.disconnect === 'function') { + await rawTyped.disconnect(device); + } + return; + } + override async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.sendData === 'function') { + await rawTyped.sendData(device, payload, options); + } + return; + } + override async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.autoConnect === 'function') { + return await rawTyped.autoConnect(device, options); + } + return { serviceId: '', writeCharId: '', notifyCharId: '' }; + } +} + +// Strong runtime detector for plain object handlers (no Type Predicate) +// Note: the UTS bundler doesn't support TypeScript type predicates (x is T), +// and it doesn't accept the 'unknown' type. This returns a boolean and +// callers must cast the value to RawProtocolHandler after the function +// returns true. +function isRawProtocolHandler(x: any): boolean { + if (x == null || typeof x !== 'object') return false; + const r = x as Record; + if (typeof r['scanDevices'] === 'function') return true; + if (typeof r['connect'] === 'function') return true; + if (typeof r['disconnect'] === 'function') return true; + if (typeof r['sendData'] === 'function') return true; + if (typeof r['autoConnect'] === 'function') return true; + if (typeof r['protocol'] === 'string') return true; + return false; +} + +export const registerProtocolHandler = (handler : any) => { + if (handler == null) return; + // Determine protocol value defensively. Default to 'standard' when unknown. + let proto: BleProtocolType = 'standard'; + if (handler instanceof ProtocolHandler) { + try { proto = (handler as ProtocolHandler).protocol as BleProtocolType; } catch (e) { } + activeHandler = handler as ProtocolHandler; + } else if (isRawProtocolHandler(handler)) { + try { proto = (handler as RawProtocolHandler).protocol as BleProtocolType; } catch (e) { } + activeHandler = new ProtocolHandlerWrapper(handler as RawProtocolHandler); + (activeHandler as ProtocolHandler).protocol = proto; + } else { + console.warn('[AKBLE] registerProtocolHandler: unsupported handler type, ignoring', handler); + return; + } + activeProtocol = proto; +} + + +export const scanDevices = async (options ?: ScanDevicesOptions) : Promise => { + console.log('[AKBLE] start scan', options) + // Determine which protocols to run: either user-specified or all registered + // Single active handler flow + if (activeHandler == null) { + console.log('[AKBLE] no active scan handler registered') + return + } + const handler = activeHandler as ProtocolHandler; + const scanOptions : ScanDevicesOptions = { + onDeviceFound: (device : BleDevice) => emit('deviceFound', { event: 'deviceFound', device }), + onScanFinished: () => emit('scanFinished', { event: 'scanFinished' }) + } + try { + await handler.scanDevices(scanOptions) + } catch (e) { + console.warn('[AKBLE] scanDevices handler error', e) + } +} + + +export const connectDevice = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => { + const handler = activeHandler; + if (handler == null) throw new Error('No protocol handler'); + const device : BleDevice = { deviceId, name: '', rssi: 0 }; // 可扩展 + await handler.connect(device, options); + const ctx = new DeviceContext(device, protocol, handler); + ctx.state = 2; // CONNECTED + deviceMap.set(getDeviceKey(deviceId, protocol), ctx); + console.log(deviceMap) + emit('connectionStateChanged', { event: 'connectionStateChanged', device, protocol, state: 2 }); +} + +export const disconnectDevice = async (deviceId : string, protocol : BleProtocolType) : Promise => { + const ctx = deviceMap.get(getDeviceKey(deviceId, protocol)); + if (ctx == null || ctx.handler == null) return; + await ctx.handler.disconnect(ctx.device); + ctx.state = 0; + emit('connectionStateChanged', { event: 'connectionStateChanged', device: ctx.device, protocol, state: 0 }); + deviceMap.delete(getDeviceKey(deviceId, protocol)); +} +export const sendData = async (payload : SendDataPayload, options ?: BleOptions) : Promise => { + const ctx = deviceMap.get(getDeviceKey(payload.deviceId, payload.protocol)); + if (ctx == null) throw new Error('Device not connected'); + // copy to local non-null variable so generator can smart-cast across awaits + const deviceCtx = ctx as DeviceContext; + if (deviceCtx.handler == null) throw new Error('sendData not supported for this protocol'); + await deviceCtx.handler.sendData(deviceCtx.device, payload, options); + emit('dataSent', { event: 'dataSent', device: deviceCtx.device, protocol: payload.protocol, data: payload.data }); +} + +export const getConnectedDevices = () : MultiProtocolDevice[] => { + const result : MultiProtocolDevice[] = []; + deviceMap.forEach((ctx : DeviceContext) => { + const dev : MultiProtocolDevice = { + deviceId: ctx.device.deviceId, + name: ctx.device.name, + rssi: ctx.device.rssi, + protocol: ctx.protocol + }; + result.push(dev); + }); + return result; +} + +export const getConnectionState = (deviceId : string, protocol : BleProtocolType) : BleConnectionState => { + const ctx = deviceMap.get(getDeviceKey(deviceId, protocol)); + if (ctx == null) return 0; + return ctx.state; +} + +export const on = (event : BleEvent, callback : BleEventCallback) => { + if (!eventListeners.has(event)) eventListeners.set(event, new Set()); + eventListeners.get(event)!.add(callback); +} + +export const off = (event : BleEvent, callback ?: BleEventCallback) => { + if (callback == null) { + eventListeners.delete(event); + } else { + eventListeners.get(event)?.delete(callback as BleEventCallback); + } +} + +function getDeviceKey(deviceId : string, protocol : BleProtocolType) : string { + return `${deviceId}|${protocol}`; +} + +export const autoConnect = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => { + const handler = activeHandler; + if (handler == null) throw new Error('autoConnect not supported for this protocol'); + const device : BleDevice = { deviceId, name: '', rssi: 0 }; + // safe call - handler.autoConnect exists on ProtocolHandler + return await handler.autoConnect(device, options) as AutoBleInterfaces; +} + +// Ensure there is at least one handler registered so callers can scan/connect +// without needing to import a registry module. This creates a minimal default +// ProtocolHandler backed by a BluetoothService instance. +try { + if (activeHandler == null) { + // Create a DeviceManager-backed raw handler that delegates to native code + const _dm = DeviceManager.getInstance(); + const _raw: RawProtocolHandler = { + protocol: 'standard', + scanDevices: (options?: ScanDevicesOptions) => { + try { + const scanOptions = options != null ? options : {} as ScanDevicesOptions; + _dm.startScan(scanOptions); + } catch (e) { + console.warn('[AKBLE] DeviceManager.startScan failed', e); + } + return Promise.resolve(); + }, + connect: (device, options?: BleConnectOptionsExt) => { + return _dm.connectDevice(device.deviceId, options); + }, + disconnect: (device) => { + return _dm.disconnectDevice(device.deviceId); + }, + autoConnect: (device, options?: any) => { + // DeviceManager does not provide an autoConnect helper; return default + const result: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' }; + return Promise.resolve(result); + } + }; + const _wrapper = new ProtocolHandlerWrapper(_raw); + activeHandler = _wrapper; + activeProtocol = _raw.protocol as BleProtocolType; + console.log('[AKBLE] default protocol handler (BluetoothService-backed) registered', activeProtocol); + } +} catch (e) { + console.warn('[AKBLE] failed to register default protocol handler', e); +} \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/utssdk/app-android/config.json b/uni_modules/ak-sbsrv/utssdk/app-android/config.json new file mode 100644 index 0000000..c08ec42 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/app-android/config.json @@ -0,0 +1,5 @@ +{ + "dependencies": [ + + ] +} diff --git a/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts b/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts new file mode 100644 index 0000000..4bab39e --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts @@ -0,0 +1,311 @@ +import type { BleDevice, BleOptions, BleConnectionState, BleConnectionStateChangeCallback } from '../interface.uts' +import type { BleConnectOptionsExt } from '../interface.uts' +import type { ScanDevicesOptions } from '../interface.uts'; +import Context from "android.content.Context"; +import BluetoothAdapter from "android.bluetooth.BluetoothAdapter"; +import BluetoothManager from "android.bluetooth.BluetoothManager"; +import BluetoothDevice from "android.bluetooth.BluetoothDevice"; +import BluetoothGatt from "android.bluetooth.BluetoothGatt"; +import BluetoothGattCallback from "android.bluetooth.BluetoothGattCallback"; +import ScanCallback from "android.bluetooth.le.ScanCallback"; +import ScanResult from "android.bluetooth.le.ScanResult"; +import ScanSettings from "android.bluetooth.le.ScanSettings"; +import Handler from "android.os.Handler"; +import Looper from "android.os.Looper"; +import ContextCompat from "androidx.core.content.ContextCompat"; +import PackageManager from "android.content.pm.PackageManager"; +// 定义 PendingConnect 类型和实现类 +interface PendingConnect { + resolve: () => void; + reject: (err?: any) => void; // Changed to make err optional + timer?: number; +} + +class PendingConnectImpl implements PendingConnect { + resolve: () => void; + reject: (err?: any) => void; // Changed to make err optional + timer?: number; + + constructor(resolve: () => void, reject: (err?: any) => void, timer?: number) { + this.resolve = resolve; + this.reject = reject; + this.timer = timer; + } +} +// 引入全局回调管理 +import { gattCallback } from './service_manager.uts' +const pendingConnects = new Map(); + +const STATE_DISCONNECTED = 0; +const STATE_CONNECTING = 1; +const STATE_CONNECTED = 2; +const STATE_DISCONNECTING = 3; + +export class DeviceManager { + private static instance: DeviceManager | null = null; + private devices = new Map(); + private connectionStates = new Map(); + private connectionStateChangeListeners: BleConnectionStateChangeCallback[] = [] + private gattMap = new Map(); + private scanCallback: ScanCallback | null = null + private isScanning: boolean = false + private constructor() {} + static getInstance(): DeviceManager { + if (DeviceManager.instance == null) { + DeviceManager.instance = new DeviceManager(); + } + return DeviceManager.instance!; + } + startScan(options: ScanDevicesOptions): void { + console.log('ak startscan now') + const adapter = this.getBluetoothAdapter(); + if (adapter == null) { + throw new Error('未找到蓝牙适配器'); + } + if (!adapter.isEnabled) { + // 尝试请求用户开启蓝牙 + try { + adapter.enable(); // 直接调用,无需可选链和括号 + } catch (e) { + // 某些设备可能不支持 enable + } + setTimeout(() => { + if (!adapter.isEnabled) { + throw new Error('蓝牙未开启'); + } + }, 1500); + throw new Error('正在开启蓝牙,请重试'); + } + const foundDevices = this.devices; // 直接用全局 devices + + class MyScanCallback extends ScanCallback { + private foundDevices: Map; + private onDeviceFound: (device: BleDevice) => void; + constructor(foundDevices: Map, onDeviceFound: (device: BleDevice) => void) { + super(); + this.foundDevices = foundDevices; + this.onDeviceFound = onDeviceFound; + } + override onScanResult(callbackType: Int, result: ScanResult): void { + const device = result.getDevice(); + if (device != null) { + const deviceId = device.getAddress(); + let bleDevice = foundDevices.get(deviceId); + if (bleDevice == null) { + bleDevice = { + deviceId, + name: device.getName() ?? 'Unknown', + rssi: result.getRssi(), + lastSeen: Date.now() + }; + foundDevices.set(deviceId, bleDevice); + this.onDeviceFound(bleDevice); + } else { + // 更新属性(已确保 bleDevice 非空) + bleDevice.rssi = result.getRssi(); + bleDevice.name = device.getName() ?? bleDevice.name; + bleDevice.lastSeen = Date.now(); + } + } + } + + + override onScanFailed(errorCode: Int): void { + console.log('ak scan fail') + } + } + this.scanCallback = new MyScanCallback(foundDevices, options.onDeviceFound ?? (() => {})); + const scanner = adapter.getBluetoothLeScanner(); + if (scanner == null) { + throw new Error('无法获取扫描器'); + } + const scanSettings = new ScanSettings.Builder() + .setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY) + .build(); + scanner.startScan(null, scanSettings, this.scanCallback); + this.isScanning = true; + // 默认10秒后停止扫描 + new Handler(Looper.getMainLooper()).postDelayed(() => { + if (this.isScanning && this.scanCallback != null) { + scanner.stopScan(this.scanCallback); + this.isScanning = false; + // this.devices = foundDevices; + if (options.onScanFinished != null) options.onScanFinished?.invoke(); + } + }, 40000); + } + + async connectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise { + console.log('[AKBLE] connectDevice called, deviceId:', deviceId, 'options:', options, 'connectionStates:') + const adapter = this.getBluetoothAdapter(); + if (adapter == null) { + console.error('[AKBLE] connectDevice failed: 蓝牙适配器不可用') + throw new Error('蓝牙适配器不可用'); + } + const device = adapter.getRemoteDevice(deviceId); + if (device == null) { + console.error('[AKBLE] connectDevice failed: 未找到设备', deviceId) + throw new Error('未找到设备'); + } + this.connectionStates.set(deviceId, STATE_CONNECTING); + console.log('[AKBLE] connectDevice set STATE_CONNECTING, deviceId:', deviceId, 'connectionStates:') + this.emitConnectionStateChange(deviceId, STATE_CONNECTING); + const activity = UTSAndroid.getUniActivity(); + const timeout = options?.timeout ?? 15000; + const key = `${deviceId}|connect`; + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + console.error('[AKBLE] connectDevice 超时:', deviceId) + pendingConnects.delete(key); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + this.gattMap.set(deviceId, null); + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + reject(new Error('连接超时')); + }, timeout); + + // 创建一个适配器函数来匹配类型签名 + const resolveAdapter = () => { + console.log('[AKBLE] connectDevice resolveAdapter:', deviceId) + resolve(); + }; + const rejectAdapter = (err?: any) => { + console.error('[AKBLE] connectDevice rejectAdapter:', deviceId, err) + reject(err); + }; + + pendingConnects.set(key, new PendingConnectImpl(resolveAdapter, rejectAdapter, timer)); + try { + console.log('[AKBLE] connectGatt 调用前:', deviceId) + const gatt = device.connectGatt(activity, false, gattCallback); + this.gattMap.set(deviceId, gatt); + console.log('[AKBLE] connectGatt 调用后:', deviceId, gatt) + } catch (e) { + console.error('[AKBLE] connectGatt 异常:', deviceId, e) + clearTimeout(timer); + pendingConnects.delete(key); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + this.gattMap.set(deviceId, null); + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + reject(e); + } + }); + } + + // 统一分发连接回调(应在 gattCallback.onConnectionStateChange 内调用) + static handleConnectionStateChange(deviceId: string, newState: number, error?: any) { + console.log('[AKBLE] handleConnectionStateChange:', deviceId, 'newState:', newState, 'error:', error, 'pendingConnects:') + const key = `${deviceId}|connect`; + const cb = pendingConnects.get(key); + if (cb != null) { + // 修复 timer 的空安全问题,使用临时变量 + const timerValue = cb.timer; + if (timerValue != null) { + clearTimeout(timerValue); + } + + // 修复 error 处理 + if (newState === STATE_CONNECTED) { + console.log('[AKBLE] handleConnectionStateChange: 连接成功', deviceId) + cb.resolve(); + } else { + // 正确处理可空值 + const errorToUse = error != null ? error : new Error('连接断开'); + console.error('[AKBLE] handleConnectionStateChange: 连接失败', deviceId, errorToUse) + cb.reject(errorToUse); + } + pendingConnects.delete(key); + } else { + console.warn('[AKBLE] handleConnectionStateChange: 未找到 pendingConnects', deviceId, newState) + } + } + + async disconnectDevice(deviceId: string, isActive: boolean = true): Promise { + console.log('[AKBLE] disconnectDevice called, deviceId:', deviceId, 'isActive:', isActive) + let gatt = this.gattMap.get(deviceId); + if (gatt != null) { + gatt.disconnect(); + gatt.close(); + // gatt=null; + this.gattMap.set(deviceId, null); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + console.log('[AKBLE] disconnectDevice set STATE_DISCONNECTED, deviceId:', deviceId, 'connectionStates:') + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + return; + } else { + console.log('[AKBLE] disconnectDevice: gatt is null, deviceId:', deviceId) + return; + } + } + + async reconnectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise { + let attempts = 0; + const maxAttempts = options?.maxAttempts ?? 3; + const interval = options?.interval ?? 3000; + while (attempts < maxAttempts) { + try { + await this.disconnectDevice(deviceId, false); + await this.connectDevice(deviceId, options); + return; + } catch (e) { + attempts++; + if (attempts >= maxAttempts) throw new Error('重连失败'); + // 修复 setTimeout 问题,使用旧式 Promise + setTimeout 解决 + await new Promise((resolve) => { + setTimeout(() => { + resolve(); + }, interval); + }); + } + } + } + + getConnectedDevices(): BleDevice[] { + // 创建一个空数组来存储结果 + const result: BleDevice[] = []; + + // 遍历 devices Map 并检查连接状态 + this.devices.forEach((device, deviceId) => { + if (this.connectionStates.get(deviceId) === STATE_CONNECTED) { + result.push(device); + } + }); + + return result; + } + + onConnectionStateChange(listener: BleConnectionStateChangeCallback) { + console.log('[AKBLE][LOG] onConnectionStateChange 注册, 当前监听数:', this.connectionStateChangeListeners.length + 1, listener) + this.connectionStateChangeListeners.push(listener) + } + + protected emitConnectionStateChange(deviceId: string, state: BleConnectionState) { + console.log('[AKBLE][LOG] emitConnectionStateChange', deviceId, state, 'listeners:', this.connectionStateChangeListeners.length, 'connectionStates:', this.connectionStates) + for (const listener of this.connectionStateChangeListeners) { + try { + console.log('[AKBLE][LOG] emitConnectionStateChange 调用 listener', listener) + listener(deviceId, state) + } catch (e) { + console.error('[AKBLE][LOG] emitConnectionStateChange listener error', e) + } + } + } + + getGattInstance(deviceId: string): BluetoothGatt | null { + return this.gattMap.get(deviceId) ?? null; + } + + private getBluetoothAdapter(): BluetoothAdapter | null { + const context = UTSAndroid.getAppContext(); + if (context == null) return null; + const manager = context?.getSystemService(Context.BLUETOOTH_SERVICE) as BluetoothManager; + return manager.getAdapter(); + } + + /** + * 获取指定ID的设备(如果存在) + */ + public getDevice(deviceId: string): BleDevice | null { + console.log(deviceId,this.devices) + return this.devices.get(deviceId) ?? null; + } +} diff --git a/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts b/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts new file mode 100644 index 0000000..8ae6bc3 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts @@ -0,0 +1,734 @@ +import { BleService } from '../interface.uts' +import type { WriteCharacteristicOptions, DfuOptions, ControlParserResult } from '../interface.uts' +import { DeviceManager } from './device_manager.uts' +import { ServiceManager } from './service_manager.uts' +import BluetoothGatt from 'android.bluetooth.BluetoothGatt' +import BluetoothGattCharacteristic from 'android.bluetooth.BluetoothGattCharacteristic' +import BluetoothGattDescriptor from 'android.bluetooth.BluetoothGattDescriptor' +import UUID from 'java.util.UUID' + +// 通用 Nordic DFU UUIDs (常见设备可能使用这些;如厂商自定义请替换) +const DFU_SERVICE_UUID = '0000fe59-0000-1000-8000-00805f9b34fb' +const DFU_CONTROL_POINT_UUID = '8ec90001-f315-4f60-9fb8-838830daea50' +const DFU_PACKET_UUID = '8ec90002-f315-4f60-9fb8-838830daea50' + +type DfuSession = { + resolve : () => void; + reject : (err ?: any) => void; + onProgress ?: (p : number) => void; + onLog ?: (s : string) => void; + controlParser ?: (data : Uint8Array) => ControlParserResult | null; + // Nordic 专用字段 + bytesSent ?: number; + totalBytes ?: number; + useNordic ?: boolean; + // PRN (packet receipt notification) support + prn ?: number; + packetsSincePrn ?: number; + prnResolve ?: () => void; + prnReject ?: (err ?: any) => void; +} + + + +export class DfuManager { + // 会话表,用于把 control-point 通知路由到当前 DFU 流程 + private sessions : Map = new Map(); + + // 简化:只实现最基本的 GATT-based DFU 上传逻辑,需按设备协议调整 control point 的命令/解析 + + // Emit a DFU lifecycle event for a session. name should follow Nordic listener names + private _emitDfuEvent(deviceId : string, name : string, payload ?: any) { + console.log('[DFU][Event]', name, deviceId, payload ?? ''); + const s = this.sessions.get(deviceId); + if (s == null) return; + if (typeof s.onLog == 'function') { + try { + const logFn = s.onLog as (msg : string) => void; + logFn(`[${name}] ${payload != null ? JSON.stringify(payload) : ''}`); + } catch (e) { } + } + if (name == 'onProgress' && typeof s.onProgress == 'function' && typeof payload == 'number') { + try { s.onProgress(payload); } catch (e) { } + } + } + + async startDfu(deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) : Promise { + console.log('startDfu 0') + const deviceManager = DeviceManager.getInstance(); + const serviceManager = ServiceManager.getInstance(); + console.log('startDfu 1') + const gatt : BluetoothGatt | null = deviceManager.getGattInstance(deviceId); + console.log('startDfu 2') + if (gatt == null) throw new Error('Device not connected'); + console.log('[DFU] startDfu start deviceId=', deviceId, 'firmwareBytes=', firmwareBytes != null ? firmwareBytes.length : 0, 'options=', options); + try { + console.log('[DFU] requesting high connection priority for', deviceId); + gatt.requestConnectionPriority(BluetoothGatt.CONNECTION_PRIORITY_HIGH); + } catch (e) { + console.warn('[DFU] requestConnectionPriority failed', e); + } + + // 发现服务并特征 + // ensure services discovered before accessing GATT; serviceManager exposes Promise-based API + await serviceManager.getServices(deviceId, null); + console.log('[DFU] services ensured for', deviceId); + const dfuService = gatt.getService(UUID.fromString(DFU_SERVICE_UUID)); + if (dfuService == null) throw new Error('DFU service not found'); + const controlChar = dfuService.getCharacteristic(UUID.fromString(DFU_CONTROL_POINT_UUID)); + const packetChar = dfuService.getCharacteristic(UUID.fromString(DFU_PACKET_UUID)); + console.log('[DFU] dfuService=', dfuService != null ? dfuService.getUuid().toString() : null, 'controlChar=', controlChar != null ? controlChar.getUuid().toString() : null, 'packetChar=', packetChar != null ? packetChar.getUuid().toString() : null); + if (controlChar == null || packetChar == null) throw new Error('DFU characteristics missing'); + const packetProps = packetChar.getProperties(); + const supportsWriteWithResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE) != 0; + const supportsWriteNoResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) != 0; + console.log('[DFU] packet characteristic props mask=', packetProps, 'supportsWithResponse=', supportsWriteWithResponse, 'supportsNoResponse=', supportsWriteNoResponse); + + // Allow caller to request a desired MTU via options for higher throughput + const desiredMtu = (options != null && typeof options.mtu == 'number') ? options.mtu : 247; + try { + console.log('[DFU] requesting MTU=', desiredMtu, 'for', deviceId); + await this._requestMtu(gatt, desiredMtu, 8000); + console.log('[DFU] requestMtu completed for', deviceId); + } catch (e) { + console.warn('[DFU] requestMtu failed or timed out, continue with default.', e); + } + const mtu = desiredMtu; // 假定成功或使用期望值 + const chunkSize = Math.max(20, mtu - 3); + + // small helper to convert a byte (possibly signed) to a two-digit hex string + const byteToHex = (b : number) => { + const v = (b < 0) ? (b + 256) : b; + let s = v.toString(16); + if (s.length < 2) s = '0' + s; + return s; + }; + + // Parameterize PRN window and timeout via options early so they are available + // for session logging. Defaults: prn = 12 packets, prnTimeoutMs = 10000 ms + let prnWindow = 0; + if (options != null && typeof options.prn == 'number') { + prnWindow = Math.max(0, Math.floor(options.prn)); + } + const prnTimeoutMs = (options != null && typeof options.prnTimeoutMs == 'number') ? Math.max(1000, Math.floor(options.prnTimeoutMs)) : 8000; + const disablePrnOnTimeout = !(options != null && options.disablePrnOnTimeout == false); + + // 订阅 control point 通知并将通知路由到会话处理器 + const controlHandler = (data : Uint8Array) => { + // 交给会话处理器解析并触发事件 + try { + const hexParts: string[] = []; + for (let i = 0; i < data.length; i++) { + const v = data[i] as number; + hexParts.push(byteToHex(v)); + } + const hex = hexParts.join(' '); + console.log('[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data), 'hex=', hex); + } catch (e) { + console.log('[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data)); + } + this._handleControlNotification(deviceId, data); + }; + console.log('[DFU] subscribing control point for', deviceId); + await serviceManager.subscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, controlHandler); + console.log('[DFU] subscribeCharacteristic returned for', deviceId); + + // 保存会话回调(用于 waitForControlEvent); 支持 Nordic 模式追踪已发送字节 + this.sessions.set(deviceId, { + resolve: () => { }, + reject: (err ?: any) => {console.log(err) }, + onProgress: null, + onLog: null, + controlParser: (data : Uint8Array) => this._defaultControlParser(data), + bytesSent: 0, + totalBytes: firmwareBytes.length, + useNordic: options != null && options.useNordic == true, + prn: null, + packetsSincePrn: 0, + prnResolve: null, + prnReject: null + }); + console.log('[DFU] session created for', deviceId, 'totalBytes=', firmwareBytes.length); + console.log('[DFU] DFU session details:', { deviceId: deviceId, totalBytes: firmwareBytes.length, chunkSize: chunkSize, prnWindow: prnWindow, prnTimeoutMs: prnTimeoutMs }); + + // wire options callbacks into the session (if provided) + const sessRef = this.sessions.get(deviceId); + if (sessRef != null) { + sessRef.onProgress = (options != null && typeof options.onProgress == 'function') ? options.onProgress : null; + sessRef.onLog = (options != null && typeof options.onLog == 'function') ? options.onLog : null; + } + + // emit initial lifecycle events (Nordic-like) + this._emitDfuEvent(deviceId, 'onDeviceConnecting', null); + + // 写入固件数据(非常保守的实现:逐包写入并等待短延迟) + // --- PRN setup (optional, Nordic-style flow) --- + // Parameterize PRN window and timeout via options: options.prn, options.prnTimeoutMs + // Defaults were set earlier; build PRN payload using arithmetic to avoid + // bitwise operators which don't map cleanly to generated Kotlin. + if (prnWindow > 0) { + try { + // send Set PRN to device (format: [OP_CODE_SET_PRN, prn LSB, prn MSB]) + // WARNING: Ensure your device uses the same opcode/format; change if needed. + const prnLsb = prnWindow % 256; + const prnMsb = Math.floor(prnWindow / 256) % 256; + const prnPayload = new Uint8Array([0x02, prnLsb, prnMsb]); + await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, prnPayload, null); + const sess0 = this.sessions.get(deviceId); + if (sess0 != null) { + sess0.useNordic = true; + sess0.prn = prnWindow; + sess0.packetsSincePrn = 0; + sess0.controlParser = (data : Uint8Array) => this._nordicControlParser(data); + } + console.log('[DFU] Set PRN sent (prn=', prnWindow, ') for', deviceId); + } catch (e) { + console.warn('[DFU] Set PRN failed (continuing without PRN):', e); + const sessFallback = this.sessions.get(deviceId); + if (sessFallback != null) sessFallback.prn = 0; + } + } else { + console.log('[DFU] PRN disabled (prnWindow=', prnWindow, ') for', deviceId); + } + + // 写入固件数据(逐包写入并根据 options.waitForResponse 选择是否等待响应) + let offset = 0; + const total = firmwareBytes.length; + this._emitDfuEvent(deviceId, 'onDfuProcessStarted', null); + this._emitDfuEvent(deviceId, 'onUploadingStarted', null); + // Track outstanding write operations when using fire-and-forget mode so we can + // log and throttle if the Android stack becomes overwhelmed. + let outstandingWrites = 0; + // read tuning parameters from options in a safe, generator-friendly way + let configuredMaxOutstanding = 2; + let writeSleepMs = 0; + let writeRetryDelay = 100; + let writeMaxAttempts = 12; + let writeGiveupTimeout = 60000; + let drainOutstandingTimeout = 3000; + let failureBackoffMs = 0; + + // throughput measurement + let throughputWindowBytes = 0; + let lastThroughputTime = Date.now(); + function _logThroughputIfNeeded(force ?: boolean) { + try { + const now = Date.now(); + const elapsed = now - lastThroughputTime; + if (force == true || elapsed >= 1000) { + const bytes = throughputWindowBytes; + const bps = Math.floor((bytes * 1000) / Math.max(1, elapsed)); + // reset window + throughputWindowBytes = 0; + lastThroughputTime = now; + const human = `${bps} B/s`; + console.log('[DFU] throughput:', human, 'elapsedMs=', elapsed); + const s = this.sessions.get(deviceId); + if (s != null && typeof s.onLog == 'function') { + try { s.onLog?.invoke('[DFU] throughput: ' + human); } catch (e) { } + } + } + } catch (e) { } + } + + function _safeErr(e ?: any) { + try { + if (e == null) return ''; + if (typeof e == 'string') return e; + try { return JSON.stringify(e); } catch (e2) { } + try { return (e as any).toString(); } catch (e3) { } + return ''; + } catch (e4) { return ''; } + } + try { + if (options != null) { + try { + if (options.maxOutstanding != null) { + const parsed = Math.floor(options.maxOutstanding as number); + if (!isNaN(parsed) && parsed > 0) configuredMaxOutstanding = parsed; + } + } catch (e) { } + try { + if (options.writeSleepMs != null) { + const parsedWs = Math.floor(options.writeSleepMs as number); + if (!isNaN(parsedWs) && parsedWs >= 0) writeSleepMs = parsedWs; + } + } catch (e) { } + try { + if (options.writeRetryDelayMs != null) { + const parsedRetry = Math.floor(options.writeRetryDelayMs as number); + if (!isNaN(parsedRetry) && parsedRetry >= 0) writeRetryDelay = parsedRetry; + } + } catch (e) { } + try { + if (options.writeMaxAttempts != null) { + const parsedAttempts = Math.floor(options.writeMaxAttempts as number); + if (!isNaN(parsedAttempts) && parsedAttempts > 0) writeMaxAttempts = parsedAttempts; + } + } catch (e) { } + try { + if (options.writeGiveupTimeoutMs != null) { + const parsedGiveupTimeout = Math.floor(options.writeGiveupTimeoutMs as number); + if (!isNaN(parsedGiveupTimeout) && parsedGiveupTimeout > 0) writeGiveupTimeout = parsedGiveupTimeout; + } + } catch (e) { } + try { + if (options.drainOutstandingTimeoutMs != null) { + const parsedDrain = Math.floor(options.drainOutstandingTimeoutMs as number); + if (!isNaN(parsedDrain) && parsedDrain >= 0) drainOutstandingTimeout = parsedDrain; + } + } catch (e) { } + } + if (configuredMaxOutstanding < 1) configuredMaxOutstanding = 1; + if (writeSleepMs < 0) writeSleepMs = 0; + } catch (e) { } + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + if (configuredMaxOutstanding > 1) configuredMaxOutstanding = 1; + if (writeSleepMs < 15) writeSleepMs = 15; + if (writeRetryDelay < 150) writeRetryDelay = 150; + if (writeMaxAttempts < 40) writeMaxAttempts = 40; + if (writeGiveupTimeout < 120000) writeGiveupTimeout = 120000; + console.log('[DFU] packet char only supports WRITE_NO_RESPONSE; serializing writes with conservative pacing'); + } + const maxOutstandingCeiling = configuredMaxOutstanding; + let adaptiveMaxOutstanding = configuredMaxOutstanding; + const minOutstandingWindow = 1; + + while (offset < total) { + const end = Math.min(offset + chunkSize, total); + const slice = firmwareBytes.subarray(offset, end); + // Decide whether to wait for response per-chunk. Honor characteristic support. + // Generator-friendly: avoid 'undefined' and use explicit boolean check. + let finalWaitForResponse = true; + if (options != null) { + try { + const maybe = options.waitForResponse; + if (maybe == true && supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + // caller requested response but characteristic cannot provide it; keep true to ensure we await the write promise. + finalWaitForResponse = true; + } else if (maybe == false) { + finalWaitForResponse = false; + } else if (maybe == true) { + finalWaitForResponse = true; + } + } catch (e) { finalWaitForResponse = true; } + } + + const writeOpts: WriteCharacteristicOptions = { + waitForResponse: finalWaitForResponse, + retryDelayMs: writeRetryDelay, + maxAttempts: writeMaxAttempts, + giveupTimeoutMs: writeGiveupTimeout, + forceWriteTypeNoResponse: finalWaitForResponse == false + }; + console.log('[DFU] writing packet chunk offset=', offset, 'len=', slice.length, 'waitForResponse=', finalWaitForResponse, 'outstanding=', outstandingWrites); + + // Fire-and-forget path: do not await the write if waitForResponse == false. + if (finalWaitForResponse == false) { + if (failureBackoffMs > 0) { + console.log('[DFU] applying failure backoff', failureBackoffMs, 'ms before next write for', deviceId); + await this._sleep(failureBackoffMs); + failureBackoffMs = Math.floor(failureBackoffMs / 2); + } + while (outstandingWrites >= adaptiveMaxOutstanding) { + await this._sleep(Math.max(1, writeSleepMs)); + } + // increment outstanding counter and kick the write without awaiting. + outstandingWrites = outstandingWrites + 1; + // fire-and-forget: start the write but don't await its Promise + const writeOffset = offset; + serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts).then((res) => { + outstandingWrites = Math.max(0, outstandingWrites - 1); + if (res == true) { + if (adaptiveMaxOutstanding < maxOutstandingCeiling) { + adaptiveMaxOutstanding = Math.min(maxOutstandingCeiling, adaptiveMaxOutstanding + 1); + } + if (failureBackoffMs > 0) failureBackoffMs = Math.floor(failureBackoffMs / 2); + } + // log occasional completions + if ((outstandingWrites & 0x1f) == 0) { + console.log('[DFU] write completion callback, outstandingWrites=', outstandingWrites, 'adaptiveWindow=', adaptiveMaxOutstanding, 'device=', deviceId); + } + // detect write failure signaled by service manager + if (res !== true) { + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)); + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))); + console.error('[DFU] writeCharacteristic returned false for device=', deviceId, 'offset=', writeOffset, 'adaptiveWindow now=', adaptiveMaxOutstanding); + try { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: 'write returned false' }); } catch (e) { } + } + }).catch((e) => { + outstandingWrites = Math.max(0, outstandingWrites - 1); + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)); + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))); + console.warn('[DFU] fire-and-forget write failed for device=', deviceId, e, 'adaptiveWindow now=', adaptiveMaxOutstanding); + try { + const errMsg ='[DFU] fire-and-forget write failed for device='; + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: errMsg }); + } catch (e2) { } + }); + // account bytes for throughput + throughputWindowBytes += slice.length; + _logThroughputIfNeeded(false); + } else { + console.log('[DFU] awaiting write for chunk offset=', offset); + try { + const writeResult = await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts); + if (writeResult !== true) { + console.error('[DFU] writeCharacteristic(await) returned false at offset=', offset, 'device=', deviceId); + try { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: 'write returned false' }); } catch (e) { } + // abort DFU by throwing + throw new Error('write failed'); + } + } catch (e) { + console.error('[DFU] awaiting write failed at offset=', offset, 'device=', deviceId, e); + try { + const errMsg = '[DFU] awaiting write failed '; + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: errMsg }); + } catch (e2) { } + throw e; + } + // account bytes for throughput + throughputWindowBytes += slice.length; + _logThroughputIfNeeded(false); + } + // update PRN counters and wait when window reached + const sessAfter = this.sessions.get(deviceId); + if (sessAfter != null && sessAfter.useNordic == true && typeof sessAfter.prn == 'number' && (sessAfter.prn ?? 0) > 0) { + sessAfter.packetsSincePrn = (sessAfter.packetsSincePrn ?? 0) + 1; + if ((sessAfter.packetsSincePrn ?? 0) >= (sessAfter.prn ?? 0) && (sessAfter.prn ?? 0) > 0) { + // wait for PRN (device notification) before continuing + try { + console.log('[DFU] reached PRN window, waiting for PRN for', deviceId, 'packetsSincePrn=', sessAfter.packetsSincePrn, 'prn=', sessAfter.prn); + await this._waitForPrn(deviceId, prnTimeoutMs); + console.log('[DFU] PRN received, resuming transfer for', deviceId); + } catch (e) { + console.warn('[DFU] PRN wait failed/timed out, continuing anyway for', deviceId, e); + if (disablePrnOnTimeout) { + console.warn('[DFU] disabling PRN waits after timeout for', deviceId); + sessAfter.prn = 0; + } + } + // reset counter + sessAfter.packetsSincePrn = 0; + } + } + offset = end; + // 如果启用 nordic 模式,统计已发送字节 + const sess = this.sessions.get(deviceId); + if (sess != null && typeof sess.bytesSent == 'number') { + sess.bytesSent = (sess.bytesSent ?? 0) + slice.length; + } + // 简单节流与日志,避免过快。默认睡眠非常短以提高吞吐量; 可在设备上调节 + console.log('[DFU] wrote chunk for', deviceId, 'offset=', offset, '/', total, 'chunkSize=', slice.length, 'bytesSent=', sess != null ? sess.bytesSent : null, 'outstanding=', outstandingWrites); + // emit upload progress event (percent) if available + if (sess != null && typeof sess.bytesSent == 'number' && typeof sess.totalBytes == 'number') { + const p = Math.floor((sess.bytesSent / sess.totalBytes) * 100); + this._emitDfuEvent(deviceId, 'onProgress', p); + } + // yield to event loop and avoid starving the Android BLE stack + await this._sleep(Math.max(0, writeSleepMs)); + } + // wait for outstanding writes to drain before continuing with control commands + if (outstandingWrites > 0) { + const drainStart = Date.now(); + while (outstandingWrites > 0 && (Date.now() - drainStart) < drainOutstandingTimeout) { + await this._sleep(Math.max(0, writeSleepMs)); + } + if (outstandingWrites > 0) { + console.warn('[DFU] outstandingWrites remain after drain timeout, continuing with', outstandingWrites); + } else { + console.log('[DFU] outstandingWrites drained before control phase'); + } + } + this._emitDfuEvent(deviceId, 'onUploadingCompleted', null); + + // force final throughput log before activate/validate + _logThroughputIfNeeded(true); + + // 发送 activate/validate 命令到 control point(需根据设备协议实现) + // 下面为占位:请替换为实际的 opcode + // 在写入前先启动控制结果等待,防止设备快速响应导致丢失通知 + const controlTimeout = 20000; + const controlResultPromise = this._waitForControlResult(deviceId, controlTimeout); + try { + // control writes: pass undefined options explicitly to satisfy the generator/typechecker + const activatePayload = new Uint8Array([0x04]); + console.log('[DFU] sending activate/validate payload=', Array.from(activatePayload)); + await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, activatePayload, null); + console.log('[DFU] activate/validate write returned for', deviceId); + } catch (e) { + // 写入失败时取消控制等待,避免悬挂定时器 + try { + const sessOnWriteFail = this.sessions.get(deviceId); + if (sessOnWriteFail != null && typeof sessOnWriteFail.reject == 'function') { + sessOnWriteFail.reject(e); + } + } catch (rejectErr) { } + await controlResultPromise.catch(() => { }); + try { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e2) { } + this.sessions.delete(deviceId); + throw e; + } + console.log('[DFU] sent control activate/validate command to control point for', deviceId); + this._emitDfuEvent(deviceId, 'onValidating', null); + + // 等待 control-point 返回最终结果(成功或失败),超时可配置 + console.log('[DFU] waiting for control result (timeout=', controlTimeout, ') for', deviceId); + try { + await controlResultPromise; + console.log('[DFU] control result resolved for', deviceId); + } catch (err) { + // 清理订阅后抛出 + try { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e) { } + this.sessions.delete(deviceId); + throw err; + } + + // 取消订阅 + try { + await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); + } catch (e) { } + console.log('[DFU] unsubscribed control point for', deviceId); + + // 清理会话 + this.sessions.delete(deviceId); + console.log('[DFU] session cleared for', deviceId); + + return; + } + + async _requestMtu(gatt : BluetoothGatt, mtu : number, timeoutMs : number) : Promise { + return new Promise((resolve, reject) => { + // 在当前项目,BluetoothGattCallback.onMtuChanged 未被封装;简单发起请求并等待短超时 + try { + const ok = gatt.requestMtu(Math.floor(mtu) as Int); + if (!ok) { + return reject(new Error('requestMtu failed')); + } + } catch (e) { + return reject(e); + } + // 无 callback 监听时退回,等待一小段时间以便成功 + setTimeout(() => resolve(), Math.min(2000, timeoutMs)); + }); + } + + _sleep(ms : number) { + return new Promise((r) => { setTimeout(() => { r() }, ms); }); + } + + _waitForPrn(deviceId : string, timeoutMs : number) : Promise { + const session = this.sessions.get(deviceId); + if (session == null) return Promise.reject(new Error('no dfu session')); + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + // timeout waiting for PRN + // clear pending handlers + session.prnResolve = null; + session.prnReject = null; + reject(new Error('PRN timeout')); + }, timeoutMs); + const prnResolve = () => { + clearTimeout(timer); + resolve(); + }; + const prnReject = (err ?: any) => { + clearTimeout(timer); + reject(err); + }; + session.prnResolve = prnResolve; + session.prnReject = prnReject; + }); + } + + // 默认 control point 解析器(非常通用的尝试解析:如果设备发送 progress byte 或成功码) + _defaultControlParser(data : Uint8Array) : ControlParserResult | null { + // 假设协议:第一个字节为 opcode, 第二字节可为状态或进度 + if (data == null || data.length === 0) return null; + const op = data[0]; + // Nordic-style response: [0x10, requestOp, resultCode] + if (op === 0x10 && data.length >= 3) { + const requestOp = data[1]; + const resultCode = data[2]; + if (resultCode === 0x01) { + return { type: 'success' }; + } + return { type: 'error', error: { requestOp: requestOp, resultCode: resultCode, raw: Array.from(data) } }; + } + // Nordic PRN notification: [0x11, LSB, MSB] -> return as progress (bytes received) + if (op === 0x11 && data.length >= 3) { + const lsb = data[1]; + const msb = data[2]; + const received = (msb << 8) | lsb; + return { type: 'progress', progress: received }; + } + // vendor-specific opcode example: 0x60 may mean 'response/progress' for some firmwares + if (op === 0x60) { + if (data.length >= 3) { + const requestOp = data[1]; + const status = data[2]; + // Known success/status codes observed in field devices + if (status === 0x00 || status === 0x01 || status === 0x0A) { + return { type: 'success' }; + } + return { type: 'error', error: { requestOp: requestOp, resultCode: status, raw: Array.from(data) } }; + } + if (data.length >= 2) { + return { type: 'progress', progress: data[1] }; + } + } + // 通用进度回退:若第二字节位于 0-100 之间,当作百分比 + if (data.length >= 2) { + const maybeProgress = data[1]; + if (maybeProgress >= 0 && maybeProgress <= 100) { + return { type: 'progress', progress: maybeProgress }; + } + } + // 若找到明显的 success opcode (示例 0x01) 或 error 0xFF + if (op === 0x01) return { type: 'success' }; + if (op === 0xFF) return { type: 'error', error: data }; + return { type: 'info' }; + } + + // Nordic DFU control-parser(支持 Response and Packet Receipt Notification) + _nordicControlParser(data : Uint8Array) : ControlParserResult | null { + // Nordic opcodes (简化): + // - 0x10 : Response (opcode, requestOp, resultCode) + // - 0x11 : Packet Receipt Notification (opcode, value LSB, value MSB) + if (data == null || data.length == 0) return null; + const op = data[0]; + if (op == 0x11 && data.length >= 3) { + // packet receipt notif: bytes received (little endian) + const lsb = data[1]; + const msb = data[2]; + const received = (msb << 8) | lsb; + // Return received bytes as progress value; parser does not resolve device-specific session here. + return { type: 'progress', progress: received }; + } + // Nordic vendor-specific progress/response opcode (example 0x60) + if (op == 0x60) { + if (data.length >= 3) { + const requestOp = data[1]; + const status = data[2]; + if (status == 0x00 || status == 0x01 || status == 0x0A) { + return { type: 'success' }; + } + return { type: 'error', error: { requestOp, resultCode: status, raw: Array.from(data) } }; + } + if (data.length >= 2) { + return { type: 'progress', progress: data[1] }; + } + } + // Response: check result code for success (0x01 may indicate success in some stacks) + if (op == 0x10 && data.length >= 3) { + const requestOp = data[1]; + const resultCode = data[2]; + // Nordic resultCode 0x01 = SUCCESS typically + if (resultCode == 0x01) return { type: 'success' }; + else return { type: 'error', error: { requestOp, resultCode } }; + } + return null; + } + + _handleControlNotification(deviceId : string, data : Uint8Array) { + const session = this.sessions.get(deviceId); + if (session == null) { + console.warn('[DFU] control notification received but no session for', deviceId, 'data=', Array.from(data)); + return; + } + try { + // human readable opcode mapping + let opcodeName = 'unknown'; + switch (data[0]) { + case 0x10: opcodeName = 'Response'; break; + case 0x11: opcodeName = 'PRN'; break; + case 0x60: opcodeName = 'VendorProgress'; break; + case 0x01: opcodeName = 'SuccessOpcode'; break; + case 0xFF: opcodeName = 'ErrorOpcode'; break; + } + console.log('[DFU] _handleControlNotification deviceId=', deviceId, 'opcode=0x' + data[0].toString(16), 'name=', opcodeName, 'raw=', Array.from(data)); + const parsed = session.controlParser != null ? session.controlParser(data) : null; + if (session.onLog != null) session.onLog('DFU control notify: ' + Array.from(data).join(',')); + console.log('[DFU] parsed control result=', parsed); + if (parsed == null) return; + if (parsed.type == 'progress' && parsed.progress != null) { + // 如果在 nordic 模式 parsed.progress 可能是已接收字节数,则转换为百分比 + if (session.useNordic == true && session.totalBytes != null && session.totalBytes > 0) { + const percent = Math.floor((parsed.progress / session.totalBytes) * 100); + session.onProgress?.(percent); + // If we have written all bytes locally, log that event + if (session.bytesSent != null && session.totalBytes != null && session.bytesSent >= session.totalBytes) { + console.log('[DFU] all bytes written locally for', deviceId, 'bytesSent=', session.bytesSent, 'total=', session.totalBytes); + // emit uploading completed once + this._emitDfuEvent(deviceId, 'onUploadingCompleted', null); + } + // If a PRN wait is pending, resolve it (PRN indicates device received packets) + if (typeof session.prnResolve == 'function') { + try { session.prnResolve(); } catch (e) { } + session.prnResolve = null; + session.prnReject = null; + session.packetsSincePrn = 0; + } + } else { + const progress = parsed.progress + if (progress != null) { + console.log('[DFU] progress for', deviceId, 'progress=', progress); + session.onProgress?.(progress); + // also resolve PRN if was waiting (in case device reports numeric progress) + if (typeof session.prnResolve == 'function') { + try { session.prnResolve(); } catch (e) { } + session.prnResolve = null; + session.prnReject = null; + session.packetsSincePrn = 0; + } + } + } + } else if (parsed.type == 'success') { + console.log('[DFU] parsed success for', deviceId, 'resolving session'); + session.resolve(); + // Log final device-acknowledged success + console.log('[DFU] device reported DFU success for', deviceId); + this._emitDfuEvent(deviceId, 'onDfuCompleted', null); + } else if (parsed.type == 'error') { + console.error('[DFU] parsed error for', deviceId, parsed.error); + session.reject(parsed.error ?? new Error('DFU device error')); + this._emitDfuEvent(deviceId, 'onError', parsed.error ?? {}); + } else { + // info - just log + } + } catch (e) { + session.onLog?.('control parse error: ' + e); + console.error('[DFU] control parse exception for', deviceId, e); + } + } + + _waitForControlResult(deviceId : string, timeoutMs : number) : Promise { + const session = this.sessions.get(deviceId); + if (session == null) return Promise.reject(new Error('no dfu session')); + return new Promise((resolve, reject) => { + // wrap resolve/reject to clear timer + const timer = setTimeout(() => { + // 超时 + console.error('[DFU] _waitForControlResult timeout for', deviceId); + reject(new Error('DFU control timeout')); + }, timeoutMs); + const origResolve = () => { + clearTimeout(timer); + console.log('[DFU] _waitForControlResult resolved for', deviceId); + resolve(); + }; + const origReject = (err ?: any) => { + clearTimeout(timer); + console.error('[DFU] _waitForControlResult rejected for', deviceId, 'err=', err); + reject(err); + }; + // replace session handlers temporarily (guard nullable) + if (session != null) { + session.resolve = origResolve; + session.reject = origReject; + } + }); + } +} + +export const dfuManager = new DfuManager(); \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/utssdk/app-android/index.uts b/uni_modules/ak-sbsrv/utssdk/app-android/index.uts new file mode 100644 index 0000000..dbb0ad7 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/app-android/index.uts @@ -0,0 +1,110 @@ +import * as BluetoothManager from './bluetooth_manager.uts'; +import { ServiceManager } from './service_manager.uts'; +import type { ScanDevicesOptions, BleConnectOptionsExt, MultiProtocolDevice, BleEvent, BleEventCallback, BleService, BleCharacteristic, WriteCharacteristicOptions, AutoBleInterfaces, BleDataReceivedCallback } from '../interface.uts'; +import { DeviceManager } from './device_manager.uts'; + +const serviceManager = ServiceManager.getInstance(); + +export class BluetoothService { + scanDevices(options?: ScanDevicesOptions) { return BluetoothManager.scanDevices(options); } + connectDevice(deviceId: string, protocol: string, options?: BleConnectOptionsExt) { return BluetoothManager.connectDevice(deviceId, protocol, options); } + disconnectDevice(deviceId: string, protocol: string) { return BluetoothManager.disconnectDevice(deviceId, protocol); } + getConnectedDevices(): MultiProtocolDevice[] { return BluetoothManager.getConnectedDevices(); } + on(event: BleEvent, callback: BleEventCallback) { return BluetoothManager.on(event, callback); } + off(event: BleEvent, callback?: BleEventCallback) { return BluetoothManager.off(event, callback); } + getServices(deviceId: string): Promise { + return new Promise((resolve, reject) => { + serviceManager.getServices(deviceId, (list, err) => { + console.log('getServices:', list, err); // 新增日志 + if (err != null) reject(err); + else resolve((list as BleService[]) ?? []); + }); + }); + } + getCharacteristics(deviceId: string, serviceId: string): Promise { + return new Promise((resolve, reject) => { + console.log(deviceId,serviceId) + serviceManager.getCharacteristics(deviceId, serviceId, (list, err) => { + if (err != null) reject(err); + else resolve((list as BleCharacteristic[]) ?? []); + }); + }); + } + /** + * 自动发现服务和特征,返回可用的写入和通知特征ID + * @param deviceId 设备ID + * @returns {Promise} + */ + async getAutoBleInterfaces(deviceId: string): Promise { + // 1. 获取服务列表 + const services = await this.getServices(deviceId); + if (services == null || services.length == 0) throw new Error('未发现服务'); + + // 2. 选择目标服务(优先bae前缀,可根据需要调整) + let serviceId = ''; + for (let i = 0; i < services.length; i++) { + const s = services[i]; + const uuidCandidate: string | null = (s.uuid != null ? s.uuid : null) + const uuid: string = uuidCandidate != null ? uuidCandidate : '' + // prefer regex test to avoid nullable receiver calls in generated Kotlin + if (/^bae/i.test(uuid)) { + serviceId = uuid + break; + } + } + console.log(serviceId) + if (serviceId == null || serviceId == '') serviceId = services[0].uuid; + + // 3. 获取特征列表 + const characteristics = await this.getCharacteristics(deviceId, serviceId); + console.log(characteristics) + if (characteristics == null || characteristics.length == 0) throw new Error('未发现特征值'); + + // 4. 筛选write和notify特征 + let writeCharId = ''; + let notifyCharId = ''; + for (let i = 0; i < characteristics.length; i++) { + + const c = characteristics[i]; + console.log(c) + if ((writeCharId == null || writeCharId == '') && c.properties != null && (c.properties.write || c.properties.writeWithoutResponse==true)) writeCharId = c.uuid; + if ((notifyCharId == null || notifyCharId == '') && c.properties != null && (c.properties.notify || c.properties.indicate)) notifyCharId = c.uuid; + } + console.log(serviceId, writeCharId, notifyCharId); + if ((writeCharId == null || writeCharId == '') || (notifyCharId == null || notifyCharId == '')) throw new Error('未找到合适的写入或通知特征'); + console.log(serviceId, writeCharId, notifyCharId); + // // 发现服务和特征后 + const deviceManager = DeviceManager.getInstance(); + console.log(deviceManager); + const device = deviceManager.getDevice(deviceId); + console.log(deviceId,device) + device!.serviceId = serviceId; + device!.writeCharId = writeCharId; + device!.notifyCharId = notifyCharId; + console.log(device); + return { serviceId, writeCharId, notifyCharId }; + } + async subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, onData: BleDataReceivedCallback): Promise { + return serviceManager.subscribeCharacteristic(deviceId, serviceId, characteristicId, onData); + } + async readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + return serviceManager.readCharacteristic(deviceId, serviceId, characteristicId); + } + async writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, data: Uint8Array, options?: WriteCharacteristicOptions): Promise { + return serviceManager.writeCharacteristic(deviceId, serviceId, characteristicId, data, options); + } + async unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + return serviceManager.unsubscribeCharacteristic(deviceId, serviceId, characteristicId); + } + async autoDiscoverAll(deviceId: string): Promise { + return serviceManager.autoDiscoverAll(deviceId); + } + async subscribeAllNotifications(deviceId: string, onData: BleDataReceivedCallback): Promise { + return serviceManager.subscribeAllNotifications(deviceId, onData); + } +} + +export const bluetoothService = new BluetoothService(); + +// Ensure protocol handlers are registered when this module is imported. + // import './protocol_registry.uts'; diff --git a/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts b/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts new file mode 100644 index 0000000..c67091a --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts @@ -0,0 +1,663 @@ +import type { BleService, BleCharacteristic, BleDataReceivedCallback, BleCharacteristicProperties, WriteCharacteristicOptions, ByteArray } from '../interface.uts' +import BluetoothGatt from "android.bluetooth.BluetoothGatt"; +import BluetoothGattService from "android.bluetooth.BluetoothGattService"; +import BluetoothGattCharacteristic from "android.bluetooth.BluetoothGattCharacteristic"; +import BluetoothGattDescriptor from "android.bluetooth.BluetoothGattDescriptor"; +import BluetoothGattCallback from "android.bluetooth.BluetoothGattCallback"; + +import UUID from "java.util.UUID"; +import { DeviceManager } from './device_manager.uts' +import { AkBleErrorImpl, AkBluetoothErrorCode } from '../unierror.uts' +import { AutoDiscoverAllResult } from '../interface.uts' + + + + +// 补全UUID格式,将短格式转换为标准格式 +function getFullUuid(shortUuid : string) : string { + return `0000${shortUuid}-0000-1000-8000-00805f9b34fb` +} + + +const deviceWriteQueues = new Map>(); + +function enqueueDeviceWrite(deviceId : string, work : () => Promise) : Promise { + const previous = deviceWriteQueues.get(deviceId) ?? Promise.resolve(); + const next = (async () : Promise => { + try { + await previous; + } catch (e) { /* ignore previous rejection to keep queue alive */ } + return await work(); + })(); + const queued = next.then(() => { }, () => { }); + deviceWriteQueues.set(deviceId, queued); + return next.finally(() => { + if (deviceWriteQueues.get(deviceId) == queued) { + deviceWriteQueues.delete(deviceId); + } + }); +} + + + +function createCharProperties(props : number) : BleCharacteristicProperties { + const result : BleCharacteristicProperties = { + read: false, + write: false, + notify: false, + indicate: false, + canRead: false, + canWrite: false, + canNotify: false, + writeWithoutResponse: false + }; + result.read = (props & BluetoothGattCharacteristic.PROPERTY_READ) !== 0; + result.write = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0; + result.notify = (props & BluetoothGattCharacteristic.PROPERTY_NOTIFY) !== 0; + result.indicate = (props & BluetoothGattCharacteristic.PROPERTY_INDICATE) !== 0; + result.writeWithoutResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0; + + result.canRead = result.read; + const writeWithoutResponse = result.writeWithoutResponse; + result.canWrite = (result.write != null && result.write) || (writeWithoutResponse != null && writeWithoutResponse); + result.canNotify = result.notify; + return result; +} + +// 定义 PendingCallback 类型和实现类 +interface PendingCallback { + resolve : (data : any) => void; + reject : (err ?: any) => void; + timer ?: number; // Changed from any to number +} + +class PendingCallbackImpl implements PendingCallback { + resolve : (data : any) => void; + reject : (err ?: any) => void; + timer ?: number; // Changed from any to number + + constructor(resolve : (data : any) => void, reject : (err ?: any) => void, timer ?: number) { + this.resolve = resolve; + this.reject = reject; + this.timer = timer; + } +} + +// 全局回调管理(必须在类外部声明) +let pendingCallbacks : Map; +let notifyCallbacks : Map; + +// 在全局范围内初始化 +pendingCallbacks = new Map(); +notifyCallbacks = new Map(); + +// 服务发现等待队列:deviceId -> 回调数组 +const serviceDiscoveryWaiters = new Map void)[]>(); +// 服务发现状态:deviceId -> 是否已发现 +const serviceDiscovered = new Map(); + +// 特征发现等待队列:deviceId|serviceId -> 回调数组 +const characteristicDiscoveryWaiters = new Map void)[]>(); + +class GattCallback extends BluetoothGattCallback { + constructor() { + super(); + } + + override onServicesDiscovered(gatt : BluetoothGatt, status : Int) : void { + console.log('ak onServicesDiscovered') + const deviceId = gatt.getDevice().getAddress(); + if (status == BluetoothGatt.GATT_SUCCESS) { + console.log(`服务发现成功: ${deviceId}`); + serviceDiscovered.set(deviceId, true); + // 统一回调所有等待 getServices 的调用 + const waiters = serviceDiscoveryWaiters.get(deviceId); + if (waiters != null && waiters.length > 0) { + const services = gatt.getServices(); + const result : BleService[] = []; + if (services != null) { + const servicesList = services; + const size = servicesList.size; + for (let i = 0; i < size; i++) { + const service = servicesList.get(i as Int); + if (service != null) { + const bleService : BleService = { + uuid: service.getUuid().toString(), + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + result.push(bleService); + } + } + } + for (let i = 0; i < waiters.length; i++) { + const cb = waiters[i]; + if (cb != null) { cb(result, null); } + } + serviceDiscoveryWaiters.delete(deviceId); + } + } else { + console.log(`服务发现失败: ${deviceId}, status: ${status}`); + // 失败时也要通知等待队列 + const waiters = serviceDiscoveryWaiters.get(deviceId); + if (waiters != null && waiters.length > 0) { + for (let i = 0; i < waiters.length; i++) { + const cb = waiters[i]; + if (cb != null) { cb(null, new Error('服务发现失败')); } + } + serviceDiscoveryWaiters.delete(deviceId); + } + } + } + override onConnectionStateChange(gatt : BluetoothGatt, status : Int, newState : Int) : void { + const deviceId = gatt.getDevice().getAddress(); + if (newState == BluetoothGatt.STATE_CONNECTED) { + console.log(`设备已连接: ${deviceId}`); + DeviceManager.handleConnectionStateChange(deviceId, 2, null); // 2 = STATE_CONNECTED + } else if (newState == BluetoothGatt.STATE_DISCONNECTED) { + console.log(`设备已断开: ${deviceId}`); + serviceDiscovered.delete(deviceId); + DeviceManager.handleConnectionStateChange(deviceId, 0, null); // 0 = STATE_DISCONNECTED + } + } + override onCharacteristicChanged(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic) : void { + console.log('ak onCharacteristicChanged') + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|notify`; + const callback = notifyCallbacks.get(key); + const value = characteristic.getValue(); + console.log('[onCharacteristicChanged]', key, value); + if (callback != null && value != null) { + const valueLength = value.size; + const arr = new Uint8Array(valueLength); + for (let i = 0 as Int; i < valueLength; i++) { + const v = value[i as Int]; + arr[i] = v != null ? v : 0; + } + // 保存接收日志 + console.log(` + INSERT INTO ble_data_log (device_id, service_id, char_id, direction, data, timestamp) + VALUES ('${deviceId}', '${serviceId}', '${charId}', 'recv', '${Array.from(arr).join(',')}', ${Date.now()}) + `) + + callback(arr); + } + } + override onCharacteristicRead(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void { + console.log('ak onCharacteristicRead', status) + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|read`; + const pending = pendingCallbacks.get(key); + const value = characteristic.getValue(); + console.log('[onCharacteristicRead]', key, 'status=', status, 'value=', value); + if (pending != null) { + try { + const timer = pending.timer; + if (timer != null) { + clearTimeout(timer); + pending.timer = null; + } + pendingCallbacks.delete(key); + if (status == BluetoothGatt.GATT_SUCCESS && value != null) { + const valueLength = value.size + const arr = new Uint8Array(valueLength); + for (let i = 0 as Int; i < valueLength; i++) { + const v = value[i as Int]; + arr[i] = v != null ? v : 0; + } + + // resolve with ArrayBuffer + pending.resolve(arr.buffer as ArrayBuffer); + } else { + pending.reject(new Error('Characteristic read failed')); + } + } catch (e) { + try { pending.reject(e); } catch (e2) { console.error(e2); } + } + } + } + + override onCharacteristicWrite(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void { + console.log('ak onCharacteristicWrite', status) + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|write`; + const pending = pendingCallbacks.get(key); + console.log('[onCharacteristicWrite]', key, 'status=', status); + if (pending != null) { + try { + const timer = pending.timer; + if (timer != null) { + clearTimeout(timer); + } + pendingCallbacks.delete(key); + if (status == BluetoothGatt.GATT_SUCCESS) { + pending.resolve('ok'); + } else { + pending.reject(new Error('Characteristic write failed')); + } + } catch (e) { + try { pending.reject(e); } catch (e2) { console.error(e2); } + } + } + } +} + +// 导出单例实例供外部使用 +export const gattCallback = new GattCallback(); + +export class ServiceManager { + private static instance : ServiceManager | null = null; + private services = new Map(); + private characteristics = new Map>(); + private deviceManager = DeviceManager.getInstance(); + private constructor() { } + static getInstance() : ServiceManager { + if (ServiceManager.instance == null) { + ServiceManager.instance = new ServiceManager(); + } + return ServiceManager.instance!; + } + + getServices(deviceId : string, callback ?: (services : BleService[] | null, error ?: Error) => void) : any | Promise { + console.log('ak start getservice', deviceId); + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) { + if (callback != null) { callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); } + return Promise.reject(new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); + } + console.log('ak serviceDiscovered', gatt) + // 如果服务已发现,直接返回 + if (serviceDiscovered.get(deviceId) == true) { + const services = gatt.getServices(); + console.log(services) + const result : BleService[] = []; + if (services != null) { + const servicesList = services; + const size = servicesList.size; + if (size > 0) { + for (let i = 0 as Int; i < size; i++) { + const service = servicesList != null ? servicesList.get(i) : servicesList[i]; + if (service != null) { + const bleService : BleService = { + uuid: service.getUuid().toString(), + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + result.push(bleService); + + if (bleService.uuid == getFullUuid('0001')) { + const device = this.deviceManager.getDevice(deviceId); + if (device != null) { + device.serviceId = bleService.uuid; + this.getCharacteristics(deviceId, device.serviceId, (chars, err) => { + if (err == null && chars != null) { + const writeChar = chars.find(c => c.uuid == getFullUuid('0010')); + const notifyChar = chars.find(c => c.uuid == getFullUuid('0011')); + if (writeChar != null) device.writeCharId = writeChar.uuid; + if (notifyChar != null) device.notifyCharId = notifyChar.uuid; + } + }); + } + } + } + } + } + } + if (callback != null) { callback(result, null); } + return Promise.resolve(result); + } + // 未发现则发起服务发现并加入等待队列 + if (!serviceDiscoveryWaiters.has(deviceId)) { + serviceDiscoveryWaiters.set(deviceId, []); + gatt.discoverServices(); + } + return new Promise((resolve, reject) => { + const cb = (services : BleService[] | null, error ?: Error) => { + if (error != null) reject(error); + else resolve(services ?? []); + if (callback != null) callback(services, error); + }; + const arr = serviceDiscoveryWaiters.get(deviceId); + if (arr != null) arr.push(cb); + }); + } + getCharacteristics(deviceId : string, serviceId : string, callback : (characteristics : BleCharacteristic[] | null, error ?: Error) => void) : void { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); + // 如果服务还没发现,等待服务发现后再查特征 + if (serviceDiscovered.get(deviceId) !== true) { + // 先注册到服务发现等待队列 + this.getServices(deviceId, (services, err) => { + if (err != null) { + callback(null, err); + } else { + this.getCharacteristics(deviceId, serviceId, callback); + } + }); + return; + } + // 服务已发现,正常获取特征 + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "")); + const chars = service.getCharacteristics(); + console.log(chars) + const result : BleCharacteristic[] = []; + if (chars != null) { + const characteristicsList = chars; + const size = characteristicsList.size; + const bleService : BleService = { + uuid: serviceId, + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + for (let i = 0 as Int; i < size; i++) { + const char = characteristicsList != null ? characteristicsList.get(i as Int) : characteristicsList[i]; + if (char != null) { + const props = char.getProperties(); + try { + const charUuid = char.getUuid() != null ? char.getUuid().toString() : ''; + console.log('[ServiceManager] characteristic uuid=', charUuid); + } catch (e) { console.warn('[ServiceManager] failed to read char uuid', e); } + console.log(props); + const bleCharacteristic : BleCharacteristic = { + uuid: char.getUuid().toString(), + service: bleService, + properties: createCharProperties(props) + }; + result.push(bleCharacteristic); + } + } + } + callback(result, null); + } + + public async readCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|read`; + console.log(key) + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + pendingCallbacks.delete(key); + reject(new AkBleErrorImpl(AkBluetoothErrorCode.ConnectionTimeout, "Connection timeout", "")); + }, 5000); + const resolveAdapter = (data : any) => { console.log('read resolve:', data); resolve(data as ArrayBuffer); }; + const rejectAdapter = (err ?: any) => { reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")); }; + pendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)); + if (gatt.readCharacteristic(char) == false) { + clearTimeout(timer); + pendingCallbacks.delete(key); + reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")); + } + else { + console.log('read should be succeed', key) + } + }); + } + + public async writeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, data : Uint8Array, options ?: WriteCharacteristicOptions) : Promise { + console.log('[writeCharacteristic] deviceId:', deviceId, 'serviceId:', serviceId, 'characteristicId:', characteristicId, 'data:', data); + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) { + console.error('[writeCharacteristic] gatt is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + } + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) { + console.error('[writeCharacteristic] service is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + } + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) { + console.error('[writeCharacteristic] characteristic is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + } + const key = `${deviceId}|${serviceId}|${characteristicId}|write`; + const wantsNoResponse = options != null && options.waitForResponse == false; + let retryMaxAttempts = 20; + let retryDelay = 100; + let giveupTimeout = 20000; + if (options != null) { + try { + if (options.maxAttempts != null) { + const parsedAttempts = Math.floor(options.maxAttempts as number); + if (!isNaN(parsedAttempts) && parsedAttempts > 0) retryMaxAttempts = parsedAttempts; + } + } catch (e) { } + try { + if (options.retryDelayMs != null) { + const parsedDelay = Math.floor(options.retryDelayMs as number); + if (!isNaN(parsedDelay) && parsedDelay >= 0) retryDelay = parsedDelay; + } + } catch (e) { } + try { + if (options.giveupTimeoutMs != null) { + const parsedGiveup = Math.floor(options.giveupTimeoutMs as number); + if (!isNaN(parsedGiveup) && parsedGiveup > 0) giveupTimeout = parsedGiveup; + } + } catch (e) { } + } + const gattInstance = gatt; + const executeWrite = () : Promise => { + + return new Promise((resolve) => { + const initialTimeout = Math.max(giveupTimeout + 5000, 10000); + let timer = setTimeout(() => { + pendingCallbacks.delete(key); + console.error('[writeCharacteristic] timeout'); + resolve(false); + }, initialTimeout); + console.log('[writeCharacteristic] initial timeout set to', initialTimeout, 'ms for', key); + const resolveAdapter = (data : any) => { + console.log('[writeCharacteristic] resolveAdapter called'); + resolve(true); + }; + const rejectAdapter = (err ?: any) => { + console.error('[writeCharacteristic] rejectAdapter called', err); + resolve(false); + }; + pendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)); + const byteArray = new ByteArray(data.length as Int); + for (let i = 0 as Int; i < data.length; i++) { + byteArray[i] = data[i].toByte(); + } + const forceWriteTypeNoResponse = options != null && options.forceWriteTypeNoResponse == true; + let usesNoResponse = forceWriteTypeNoResponse || wantsNoResponse; + try { + const props = char.getProperties(); + console.log('[writeCharacteristic] characteristic properties mask=', props); + if (usesNoResponse == false) { + const supportsWriteWithResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0; + const supportsWriteNoResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0; + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + usesNoResponse = true; + } + } + if (usesNoResponse) { + try { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_NO_RESPONSE); } catch (e) { } + console.log('[writeCharacteristic] using WRITE_TYPE_NO_RESPONSE'); + } else { + try { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT); } catch (e) { } + console.log('[writeCharacteristic] using WRITE_TYPE_DEFAULT'); + } + } catch (e) { + console.warn('[writeCharacteristic] failed to inspect/set write type', e); + } + const maxAttempts = retryMaxAttempts; + function attemptWrite(att : Int) : void { + try { + let setOk = true; + try { + const setRes = char.setValue(byteArray); + if (typeof setRes == 'boolean' && setRes == false) { + setOk = false; + console.warn('[writeCharacteristic] setValue returned false for', key, 'attempt', att); + } + } catch (e) { + setOk = false; + console.warn('[writeCharacteristic] setValue threw for', key, 'attempt', att, e); + } + if (setOk == false) { + if (att >= maxAttempts) { + try { clearTimeout(timer); } catch (e) { } + pendingCallbacks.delete(key); + resolve(false); + return; + } + setTimeout(() => { attemptWrite((att + 1) as Int); }, retryDelay); + return; + } + try { + console.log('[writeCharacteristic] attempt', att, 'calling gatt.writeCharacteristic'); + const r = gattInstance.writeCharacteristic(char); + console.log('[writeCharacteristic] attempt', att, 'result=', r); + if (r == true) { + if (usesNoResponse) { + console.log('[writeCharacteristic] WRITE_TYPE_NO_RESPONSE success for', key); + try { clearTimeout(timer); } catch (e) { } + pendingCallbacks.delete(key); + resolve(true); + return; + } + try { clearTimeout(timer); } catch (e) { } + const extra = 20000; + timer = setTimeout(() => { + pendingCallbacks.delete(key); + console.error('[writeCharacteristic] timeout after write initiated'); + resolve(false); + }, extra); + const pendingEntry = pendingCallbacks.get(key); + if (pendingEntry != null) pendingEntry.timer = timer; + return; + } + } catch (e) { + console.error('[writeCharacteristic] attempt', att, 'exception when calling writeCharacteristic', e); + } + if (att < maxAttempts) { + const nextAtt = (att + 1) as Int; + setTimeout(() => { attemptWrite(nextAtt); }, retryDelay); + return; + } + if (usesNoResponse) { + try { clearTimeout(timer); } catch (e) { } + pendingCallbacks.delete(key); + console.warn('[writeCharacteristic] all attempts failed with WRITE_NO_RESPONSE for', key); + resolve(false); + return; + } + try { clearTimeout(timer); } catch (e) { } + const giveupTimeoutLocal = giveupTimeout; + console.warn('[writeCharacteristic] all attempts failed; waiting for late callback up to', giveupTimeoutLocal, 'ms for', key); + const giveupTimer = setTimeout(() => { + pendingCallbacks.delete(key); + console.error('[writeCharacteristic] giveup timeout expired for', key); + resolve(false); + }, giveupTimeoutLocal); + const pendingEntryAfter = pendingCallbacks.get(key); + if (pendingEntryAfter != null) pendingEntryAfter.timer = giveupTimer; + } catch (e) { + clearTimeout(timer); + pendingCallbacks.delete(key); + console.error('[writeCharacteristic] Exception in attemptWrite', e); + resolve(false); + } + } + + try { + attemptWrite(1 as Int); + } catch (e) { + clearTimeout(timer); + pendingCallbacks.delete(key); + console.error('[writeCharacteristic] Exception before attempting write', e); + resolve(false); + } + }); + }; + return enqueueDeviceWrite(deviceId, executeWrite); + } + + public async subscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, onData : BleDataReceivedCallback) : Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|notify`; + notifyCallbacks.set(key, onData); + if (gatt.setCharacteristicNotification(char, true) == false) { + notifyCallbacks.delete(key); + throw new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", ""); + } else { + // 写入 CCCD 描述符,启用 notify + const descriptor = char.getDescriptor(UUID.fromString("00002902-0000-1000-8000-00805f9b34fb")); + if (descriptor != null) { + // 设置描述符值 + const value = + BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE; + + descriptor.setValue(value); + const writedescript = gatt.writeDescriptor(descriptor); + console.log('subscribeCharacteristic: CCCD written for notify', writedescript); + } else { + console.warn('subscribeCharacteristic: CCCD descriptor not found!'); + } + console.log('subscribeCharacteristic ok!!'); + } + } + + public async unsubscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|notify`; + notifyCallbacks.delete(key); + if (gatt.setCharacteristicNotification(char, false) == false) { + throw new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", ""); + } + } + + + // 自动发现所有服务和特征 + public async autoDiscoverAll(deviceId : string) : Promise { + const services = await this.getServices(deviceId, null) as BleService[]; + const allCharacteristics : BleCharacteristic[] = []; + for (const service of services) { + await new Promise((resolve, reject) => { + this.getCharacteristics(deviceId, service.uuid, (chars, err) => { + if (err != null) reject(err); + else { + if (chars != null) allCharacteristics.push(...chars); + resolve(); + } + }); + }); + } + return { services, characteristics: allCharacteristics }; + } + + // 自动订阅所有支持 notify/indicate 的特征 + public async subscribeAllNotifications(deviceId : string, onData : BleDataReceivedCallback) : Promise { + const { services, characteristics } = await this.autoDiscoverAll(deviceId); + for (const char of characteristics) { + if (char.properties.notify || char.properties.indicate) { + try { + await this.subscribeCharacteristic(deviceId, char.service.uuid, char.uuid, onData); + } catch (e) { + // 可以选择忽略单个特征订阅失败 + console.warn(`订阅特征 ${char.uuid} 失败:`, e); + } + } + } + } +} \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/utssdk/interface.uts b/uni_modules/ak-sbsrv/utssdk/interface.uts new file mode 100644 index 0000000..c02b46d --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/interface.uts @@ -0,0 +1,481 @@ +// 蓝牙相关接口和类型定义 + +// 基础设备信息类型 +export type BleDeviceInfo = { + deviceId : string; + name : string; + RSSI ?: number; + connected ?: boolean; + // 新增 + serviceId ?: string; + writeCharId ?: string; + notifyCharId ?: string; +} +export type AutoDiscoverAllResult = { + services : BleService[]; + characteristics : BleCharacteristic[]; +} + +// 服务信息类型 +export type BleServiceInfo = { + uuid : string; + isPrimary : boolean; +} + +// 特征值属性类型 +export type BleCharacteristicProperties = { + read : boolean; + write : boolean; + notify : boolean; + indicate : boolean; + writeWithoutResponse ?: boolean; + canRead ?: boolean; + canWrite ?: boolean; + canNotify ?: boolean; +} + +// 特征值信息类型 +export type BleCharacteristicInfo = { + uuid : string; + serviceId : string; + properties : BleCharacteristicProperties; +} + +// 错误状态码 +export enum BleErrorCode { + UNKNOWN_ERROR = 0, + BLUETOOTH_UNAVAILABLE = 1, + PERMISSION_DENIED = 2, + DEVICE_NOT_CONNECTED = 3, + SERVICE_NOT_FOUND = 4, + CHARACTERISTIC_NOT_FOUND = 5, + OPERATION_TIMEOUT = 6 +} + +// 命令类型 +export enum CommandType { + BATTERY = 1, + DEVICE_INFO = 2, + CUSTOM = 99, + TestBatteryLevel = 0x01 +} + +// 错误接口 +export type BleError { + errCode : number; + errMsg : string; + errSubject ?: string; +} + + +// 连接选项 +export type BleConnectOptions = { + deviceId : string; + timeout ?: number; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 断开连接选项 +export type BleDisconnectOptions = { + deviceId : string; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 获取特征值选项 +export type BleCharacteristicOptions = { + deviceId : string; + serviceId : string; + characteristicId : string; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 写入特征值选项 +export type BleWriteOptions = { + deviceId : string; + serviceId : string; + characteristicId : string; + value : Uint8Array; + writeType ?: number; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// Options for writeCharacteristic helper +export type WriteCharacteristicOptions = { + waitForResponse ?: boolean; + maxAttempts ?: number; + retryDelayMs ?: number; + giveupTimeoutMs ?: number; + forceWriteTypeNoResponse ?: boolean; +} + +// 通知特征值回调函数 +export type BleNotifyCallback = (data : Uint8Array) => void; + +// 通知特征值选项 +export type BleNotifyOptions = { + deviceId : string; + serviceId : string; + characteristicId : string; + state ?: boolean; // true: 启用通知,false: 禁用通知 + onCharacteristicValueChange : BleNotifyCallback; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 获取服务选项 +export type BleDeviceServicesOptions = { + deviceId : string; + success ?: (result : BleServicesResult) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 获取特征值选项 +export type BleDeviceCharacteristicsOptions = { + deviceId : string; + serviceId : string; + success ?: (result : BleCharacteristicsResult) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 蓝牙扫描选项 +export type BluetoothScanOptions = { + services ?: string[]; + timeout ?: number; + onDeviceFound ?: (device : BleDeviceInfo) => void; + success ?: (result : BleScanResult) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 扫描结果 + +// 服务结果 +export type BleServicesResult = { + services : BleServiceInfo[]; + errMsg ?: string; +} + +// 特征值结果 +export type BleCharacteristicsResult = { + characteristics : BleCharacteristicInfo[]; + errMsg ?: string; +} + +// 定义连接状态枚举 +export enum BLE_CONNECTION_STATE { + DISCONNECTED = 0, + CONNECTING = 1, + CONNECTED = 2, + DISCONNECTING = 3 +} + +// 电池状态类型定义 +export type BatteryStatus = { + batteryLevel : number; // 电量百分比 + isCharging : boolean; // 充电状态 +} + +// 蓝牙服务接口类型定义 - 转换为type类型 +export type BleService = { + uuid : string; + isPrimary : boolean; +} + +// 蓝牙特征值接口定义 - 转换为type类型 +export type BleCharacteristic = { + uuid : string; + service : BleService; + properties : BleCharacteristicProperties; +} + +// PendingPromise接口定义 +export interface PendingCallback { + resolve : (data : any) => void; + reject : (err ?: any) => void; + timer ?: number; +} + +// 蓝牙相关接口和类型定义 +export type BleDevice = { + deviceId : string; + name : string; + rssi ?: number; + lastSeen ?: number; // 新增 + // 新增 + serviceId ?: string; + writeCharId ?: string; + notifyCharId ?: string; +} + +// BLE常规选项 +export type BleOptions = { + timeout ?: number; + success ?: (result : any) => void; + fail ?: (error : any) => void; + complete ?: () => void; +} + +export type BleConnectionState = number; // 0: DISCONNECTED, 1: CONNECTING, 2: CONNECTED, 3: DISCONNECTING + +export type BleConnectOptionsExt = { + timeout ?: number; + services ?: string[]; + requireResponse ?: boolean; + autoReconnect ?: boolean; + maxAttempts ?: number; + interval ?: number; +}; + +// 回调函数类型 +export type BleDeviceFoundCallback = (device : BleDevice) => void; +export type BleConnectionStateChangeCallback = (deviceId : string, state : BleConnectionState) => void; + +export type BleDataPayload = { + deviceId : string; + serviceId ?: string; + characteristicId ?: string; + data : string | ArrayBuffer; + format ?: number; // 0: JSON, 1: XML, 2: RAW +} + +export type BleDataSentCallback = (payload : BleDataPayload, success : boolean, error ?: BleError) => void; +export type BleErrorCallback = (error : BleError) => void; + +// 健康数据类型定义 +export enum HealthDataType { + HEART_RATE = 1, + BLOOD_OXYGEN = 2, + TEMPERATURE = 3, + STEP_COUNT = 4, + SLEEP_DATA = 5, + HEALTH_DATA = 6 +} + +// Platform-specific services should be imported from per-platform entrypoints +// (e.g. './app-android/index.uts' or './web/index.uts'). +// Avoid re-exporting platform modules at the SDK root to prevent bundlers +// Platform-specific services should be imported from per-platform entrypoints +// (e.g. './app-android/index.uts' or './web/index.uts'). +// Avoid re-exporting platform modules at the SDK root to prevent bundlers +// from pulling android.* symbols into web bundles. +// If a typed ambient reference is required, declare the shape here instead of importing implementation. +// Example lightweight typed placeholder (do not import platform code here): +// export type BluetoothService = any; // platform-specific implementation exported from platform index files + + + +// ====== 新增多协议、统一事件、协议适配、状态管理支持 ====== +export type BleProtocolType = + | 'standard' + | 'custom' + | 'health' + | 'ibeacon' + | 'mesh'; + +export type BleEvent = + | 'deviceFound' + | 'scanFinished' + | 'connectionStateChanged' + | 'dataReceived' + | 'dataSent' + | 'error' + | 'servicesDiscovered' + | 'connected' // 新增 + | 'disconnected'; // 新增 + +// 事件回调参数 +export type BleEventPayload = { + event : BleEvent; + device ?: BleDevice; + protocol ?: BleProtocolType; + state ?: BleConnectionState; + data ?: ArrayBuffer | string | object; + format ?: string; + error ?: BleError; + extra ?: any; +} + +// 事件回调函数 +export type BleEventCallback = (payload : BleEventPayload) => void; + +// 多协议设备信息(去除交叉类型,直接展开字段) +export type MultiProtocolDevice = { + deviceId : string; + name : string; + rssi ?: number; + protocol : BleProtocolType; +}; + +export type ScanDevicesOptions = { + protocols ?: BleProtocolType[]; + optionalServices ?: string[]; + timeout ?: number; + onDeviceFound ?: (device : BleDevice) => void; + onScanFinished ?: () => void; +}; +// Named payload type used by sendData +export type SendDataPayload = { + deviceId : string; + serviceId ?: string; + characteristicId ?: string; + data : string | ArrayBuffer; + format ?: number; + protocol : BleProtocolType; +} +// 协议处理器接口(为 protocol-handler 适配器预留) +export type ScanHandler = { + protocol : BleProtocolType; + scanDevices ?: (options : ScanDevicesOptions) => Promise; + connect : (device : BleDevice, options ?: BleConnectOptionsExt) => Promise; + disconnect : (device : BleDevice) => Promise; + // Optional: send arbitrary data via the protocol's write characteristic + sendData ?: (device : BleDevice, payload : SendDataPayload, options ?: BleOptions) => Promise; + // Optional: try to connect and discover service/characteristic ids for this device + autoConnect ?: (device : BleDevice, options ?: BleConnectOptionsExt) => Promise; + +} + + +// 自动发现服务和特征返回类型 +export type AutoBleInterfaces = { + serviceId : string; + writeCharId : string; + notifyCharId : string; +} +export type ResponseCallbackEntry = { + cb : (data : Uint8Array) => boolean | void; + multi : boolean; +}; + +// Result returned by a DFU control parser. Use a plain string `type` to keep +// the generated Kotlin simple and avoid inline union types which the generator +// does not handle well. +export type ControlParserResult = { + type : string; // e.g. 'progress', 'success', 'error', 'info' + progress ?: number; + error ?: any; +} + +// DFU types +export type DfuOptions = { + mtu ?: number; + useNordic ?: boolean; + // If true, the DFU upload will await a write response per-packet. Set false to use + // WRITE_NO_RESPONSE (fire-and-forget) for higher throughput. Default: false. + waitForResponse ?: boolean; + // Maximum number of outstanding NO_RESPONSE writes to allow before throttling. + // This implements a simple sliding window. Default: 32. + maxOutstanding ?: number; + // Per-chunk sleep (ms) to yield to event loop / Android BLE stack. Default: 2. + writeSleepMs ?: number; + // Retry delay (ms) used by the Android write helper when gatt.writeCharacteristic + // returns false. Smaller values can improve throughput on congested stacks. + writeRetryDelayMs ?: number; + // Maximum number of immediate write attempts before falling back to the give-up timeout. + writeMaxAttempts ?: number; + // Timeout (ms) to wait for a late onCharacteristicWrite callback after all retries fail. + writeGiveupTimeoutMs ?: number; + // Packet Receipt Notification (PRN) window size in packets. If set, DFU + // manager will send a Set PRN command to the device and wait for PRN + // notifications after this many packets. Default: 12. + prn ?: number; + // Timeout (ms) to wait for a PRN notification once the window is reached. + // Default: 10000 (10s). + prnTimeoutMs ?: number; + // When true, disable PRN waits automatically after the first timeout to prevent + // repeated long stalls on devices that do not send PRNs. Default: true. + disablePrnOnTimeout ?: boolean; + // Time (ms) to wait for outstanding fire-and-forget writes to drain before issuing + // the activate/validate control command. Default: 3000. + drainOutstandingTimeoutMs ?: number; + controlTimeout ?: number; + onProgress ?: (percent : number) => void; + onLog ?: (message : string) => void; + controlParser ?: (data : Uint8Array) => ControlParserResult | null; +} + +export type DfuManagerType = { + startDfu : (deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) => Promise; +} + +// Lightweight runtime / UTS shims and missing types +// These are conservative placeholders to satisfy typings used across platform files. +// UTSJSONObject: bundler environments used by the build may not support +// TypeScript-style index signatures in this .uts context. Use a conservative +// 'any' alias so generated code doesn't rely on unsupported syntax while +// preserving a usable type at the source level. +export type UTSJSONObject = any; + +// ByteArray / Int are used in the Android platform code to interop with Java APIs. +// Define minimal aliases so source can compile. Runtime uses Uint8Array and number. +export type ByteArray = any; // runtime will use Java byte[] via UTS bridge; keep as any here + +// Callback types used by service_manager and index wrappers +export type BleDataReceivedCallback = (data: Uint8Array) => void; +export type BleScanResult = { + deviceId: string; + name?: string; + rssi?: number; + advertising?: any; +}; + +// Minimal UI / framework placeholders (some files reference these in types only) +export type ComponentPublicInstance = any; +export type UniElement = any; +export type UniPage = any; + +// Platform service placeholder (actual implementation exported from platform index files) +// Provide a lightweight, strongly-shaped class skeleton so source-level code +// (and the code generator) can rely on concrete method names and signatures. +// Implementations are platform-specific and exported from per-platform index +// files (e.g. './app-android/index.uts' or './web/index.uts'). This class is +// intentionally thin — it declares method signatures used across pages and +// platform shims so the generator emits resolvable Kotlin symbols. +export class BluetoothService { + // Event emitter style + on(event: BleEvent | string, callback: BleEventCallback): void {} + off(event: BleEvent | string, callback?: BleEventCallback): void {} + + // Scanning / discovery + scanDevices(options?: ScanDevicesOptions): Promise { return Promise.resolve(); } + + // Connection management + connectDevice(deviceId: string, protocol?: string, options?: BleConnectOptionsExt): Promise { return Promise.resolve(); } + disconnectDevice(deviceId: string, protocol?: string): Promise { return Promise.resolve(); } + getConnectedDevices(): MultiProtocolDevice[] { return []; } + + // Services / characteristics + getServices(deviceId: string): Promise { return Promise.resolve([]); } + getCharacteristics(deviceId: string, serviceId: string): Promise { return Promise.resolve([]); } + + // Read / write / notify + readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(new ArrayBuffer(0)); } + writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, value: Uint8Array | ArrayBuffer, options?: WriteCharacteristicOptions): Promise { return Promise.resolve(true); } + subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, callback: BleNotifyCallback): Promise { return Promise.resolve(); } + unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(); } + + // Convenience helpers + getAutoBleInterfaces(deviceId: string): Promise { + const res: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' }; + return Promise.resolve(res); + } +} + +// Runtime protocol handler base class. Exporting a concrete class ensures the +// generator emits a resolvable runtime type that platform handlers can extend. +// Source-level code can still use the ScanHandler type for typing. +// Runtime ProtocolHandler is implemented in `protocol_handler.uts`. +// Keep the public typing in this file minimal to avoid duplicate runtime +// declarations. Consumers that need the runtime class should import it from +// './protocol_handler.uts'. \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts b/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts new file mode 100644 index 0000000..d762fd6 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts @@ -0,0 +1,115 @@ +// Minimal ProtocolHandler runtime class used by pages and components. +// This class adapts the platform `BluetoothService` to a small protocol API +// expected by pages: setConnectionParameters, initialize, testBatteryLevel, +// testVersionInfo. Implemented conservatively to avoid heavy dependencies. + +import type { BluetoothService, AutoBleInterfaces, AutoDiscoverAllResult, BleService, BleCharacteristic, BleProtocolType, BleDevice, ScanDevicesOptions, BleConnectOptionsExt, SendDataPayload, BleOptions } from './interface.uts' + +export class ProtocolHandler { + // bluetoothService may be omitted for lightweight wrappers; allow null + bluetoothService: BluetoothService | null = null + protocol: BleProtocolType = 'standard' + deviceId: string | null = null + serviceId: string | null = null + writeCharId: string | null = null + notifyCharId: string | null = null + initialized: boolean = false + + // Accept an optional BluetoothService so wrapper subclasses can call + // `super()` without forcing a runtime instance. + constructor(bluetoothService?: BluetoothService) { + if (bluetoothService != null) this.bluetoothService = bluetoothService + } + + setConnectionParameters(deviceId: string, serviceId: string, writeCharId: string, notifyCharId: string) { + this.deviceId = deviceId + this.serviceId = serviceId + this.writeCharId = writeCharId + this.notifyCharId = notifyCharId + } + + // initialize: optional setup, returns a Promise that resolves when ready + async initialize(): Promise { + // Simple async initializer — keep implementation minimal and generator-friendly. + try { + // If bluetoothService exposes any protocol-specific setup, call it here. + this.initialized = true + return + } catch (e) { + throw e + } + } + + // Protocol lifecycle / operations — default no-ops so generated code has + // concrete member references and platform-specific handlers can override. + async scanDevices(options?: ScanDevicesOptions): Promise { return; } + async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return; } + async disconnect(device: BleDevice): Promise { return; } + async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { return; } + async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return { serviceId: '', writeCharId: '', notifyCharId: '' }; } + + // Example: testBatteryLevel will attempt to read the battery characteristic + // if write/notify-based protocol is not available. Returns number percentage. + async testBatteryLevel(): Promise { + if (this.deviceId == null) throw new Error('deviceId not set') + // copy to local so Kotlin generator can smart-cast the value across awaits + const deviceId = this.deviceId + // try reading standard Battery characteristic (180F -> 2A19) + if (this.bluetoothService == null) throw new Error('bluetoothService not set') + const services = await this.bluetoothService.getServices(deviceId) + + + let found: BleService | null = null + for (let i = 0; i < services.length; i++) { + const s = services[i] + const uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null) + const uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : '' + if (uuid.indexOf('180f') !== -1) { found = s; break } + } + if (found == null) { + // fallback: if writeCharId exists and notify available use protocol (not implemented) + return 0 + } + const foundUuid = found!.uuid + const charsRaw = await this.bluetoothService.getCharacteristics(deviceId, foundUuid) + const chars: BleCharacteristic[] = charsRaw + const batChar = chars.find((c: BleCharacteristic) => ((c.properties != null && c.properties.read) || (c.uuid != null && ('' + c.uuid).toLowerCase().includes('2a19')))) + if (batChar == null) return 0 + const buf = await this.bluetoothService.readCharacteristic(deviceId, foundUuid, batChar.uuid) + const arr = new Uint8Array(buf) + if (arr.length > 0) { + return arr[0] + } + return 0 + } + + // testVersionInfo: try to read Device Information characteristics or return empty + async testVersionInfo(hw: boolean): Promise { + // copy to local so Kotlin generator can smart-cast the value across awaits + const deviceId = this.deviceId + if (deviceId == null) return '' + // Device Information service 180A, characteristics: 2A26 (SW), 2A27 (HW) sometimes + if (this.bluetoothService == null) return '' + const _services = await this.bluetoothService.getServices(deviceId) + const services2: BleService[] = _services + let found2: BleService | null = null + for (let i = 0; i < services2.length; i++) { + const s = services2[i] + const uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null) + const uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : '' + if (uuid.indexOf('180a') !== -1) { found2 = s; break } + } + if (found2 == null) return '' + const _found2 = found2 + const found2Uuid = _found2!.uuid + const chars = await this.bluetoothService.getCharacteristics(deviceId, found2Uuid) + const target = chars.find((c) => { + const id = ('' + c.uuid).toLowerCase() + if (hw) return id.includes('2a27') || id.includes('hardware') + return id.includes('2a26') || id.includes('software') + }) + if (target == null) return '' + const buf = await this.bluetoothService.readCharacteristic(deviceId, found2Uuid, target.uuid) + try { return new TextDecoder().decode(new Uint8Array(buf)) } catch (e) { return '' } + } +} diff --git a/uni_modules/ak-sbsrv/utssdk/unierror.uts b/uni_modules/ak-sbsrv/utssdk/unierror.uts new file mode 100644 index 0000000..09c394a --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/unierror.uts @@ -0,0 +1,34 @@ +// Minimal error definitions used across the BLE module. +// Keep this file small and avoid runtime dependencies; it's mainly for typing and +// simple runtime error construction used by native platform code. + +export enum AkBluetoothErrorCode { + UnknownError = 0, + DeviceNotFound = 1, + ServiceNotFound = 2, + CharacteristicNotFound = 3, + ConnectionTimeout = 4, + Unspecified = 99 +} + +export class AkBleErrorImpl extends Error { + public code: AkBluetoothErrorCode; + public detail: any|null; + constructor(code: AkBluetoothErrorCode, message?: string, detail: any|null = null) { + super(message ?? AkBleErrorImpl.defaultMessage(code)); + this.name = 'AkBleError'; + this.code = code; + this.detail = detail; + } + static defaultMessage(code: AkBluetoothErrorCode) { + switch (code) { + case AkBluetoothErrorCode.DeviceNotFound: return 'Device not found'; + case AkBluetoothErrorCode.ServiceNotFound: return 'Service not found'; + case AkBluetoothErrorCode.CharacteristicNotFound: return 'Characteristic not found'; + case AkBluetoothErrorCode.ConnectionTimeout: return 'Connection timed out'; + case AkBluetoothErrorCode.UnknownError: default: return 'Unknown Bluetooth error'; + } + } +} + +export default AkBleErrorImpl; diff --git a/uni_modules/ak-sbsrv/utssdk/web/bluetooth_manager.uts b/uni_modules/ak-sbsrv/utssdk/web/bluetooth_manager.uts new file mode 100644 index 0000000..be3be50 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/web/bluetooth_manager.uts @@ -0,0 +1,91 @@ +// H5平台 Web Bluetooth 设备扫描实现 +import { DeviceManager } from './device-manager.uts'; +import { ServiceManager } from './service-manager.uts'; +import { BleDataProcessor } from '../data-processor.uts'; +import * as BleUtils from '../ble-utils.uts'; +import type { BleDevice, BleOptions, BleConnectOptionsExt, BleDataReceivedCallback, BleConnectionStateChangeCallback } from '../interface.uts' + +export const BLE_SERVICE_PREFIXES = ['bae']; // 这里写你的实际前缀 + +// 实例化各个管理器 +const deviceManager = new DeviceManager(); +const serviceManager = new ServiceManager(); +const dataProcessor = BleDataProcessor.getInstance(); + +// 导出简化接口 +export const scanDevices = async (options?: { optionalServices?: string[] }) => deviceManager.startScan(options); +export const connectDevice = async (deviceId: string, options?: BleConnectOptionsExt) => deviceManager.connectDevice(deviceId, options); +export const disconnectDevice = async (deviceId: string) => deviceManager.disconnectDevice(deviceId); +export const getConnectedDevices = () => deviceManager.getConnectedDevices(); +export const discoverServices = async (deviceId: string) => { + // 获取 server 实例 + const server = deviceManager.servers[deviceId]; + if (!server) throw new Error('设备未连接'); + return serviceManager.discoverServices(deviceId, server); +}; +export const getCharacteristics = async (deviceId: string, serviceId: string) => serviceManager.getCharacteristics(deviceId, serviceId); +export const writeCharacteristic = async (deviceId: string, serviceId: string, characteristicId: string, data: string | ArrayBuffer) => serviceManager.writeCharacteristic(deviceId, serviceId, characteristicId, data); +export const subscribeCharacteristic = async (deviceId: string, serviceId: string, characteristicId: string, callback) => serviceManager.subscribeCharacteristic(deviceId, serviceId, characteristicId, callback); +export const readCharacteristic = async (deviceId: string, serviceId: string, characteristicId: string) => serviceManager.readCharacteristic(deviceId, serviceId, characteristicId); +export const sendCommand = async (deviceId: string, serviceId: string, writeCharId: string, notifyCharId: string, command: string, params: any = null, timeout: number = 5000) => dataProcessor.sendAndReceive(deviceId, serviceId, writeCharId, notifyCharId, command, params, timeout); +// Event adapter helpers: translate DeviceManager callbacks into payload objects +export const onDeviceFound = (listener) => deviceManager.onDeviceFound((device) => { + try { listener({ device }); } catch (e) { /* ignore listener errors */ } +}); + +export const onScanFinished = (listener) => deviceManager.onScanFinished(() => { + try { listener({}); } catch (e) {} +}); + +export const onConnectionStateChange = (listener) => deviceManager.onConnectionStateChange((deviceId, state) => { + try { listener({ device: { deviceId }, state }); } catch (e) {} +}); + +/** + * 自动连接并初始化蓝牙设备,获取可用serviceId、writeCharId、notifyCharId + * @param deviceId 设备ID + * @returns {Promise<{serviceId: string, writeCharId: string, notifyCharId: string}>} + */ +export const autoConnect = async (deviceId: string): Promise<{serviceId: string, writeCharId: string, notifyCharId: string}> => { + // 1. 连接设备 + await connectDevice(deviceId); + + // 2. 服务发现 + const services = await discoverServices(deviceId); + if (!services || services.length === 0) throw new Error('未发现服务'); + + // 3. 获取私有serviceId(优先bae前缀或通过dataProcessor模板) + let serviceId = ''; + for (const s of services) { + if (s.uuid && BLE_SERVICE_PREFIXES.some(prefix => s.uuid.startsWith(prefix))) { + serviceId = s.uuid; + break; + } + } + if (!serviceId) { + // 可扩展:通过dataProcessor获取模板serviceId + serviceId = services[0].uuid; + } + + // 4. 获取特征值 + const characteristics = await getCharacteristics(deviceId, serviceId); + if (!characteristics || characteristics.length === 0) throw new Error('未发现特征值'); + + // 5. 找到write和notify特征 + let writeCharId = ''; + let notifyCharId = ''; + for (const c of characteristics) { + if (!writeCharId && (c.properties.write || c.properties.writeWithoutResponse)) writeCharId = c.uuid; + if (!notifyCharId && (c.properties.notify || c.properties.indicate)) notifyCharId = c.uuid; + } + if (!writeCharId || !notifyCharId) throw new Error('未找到可用的写/通知特征'); + + // 6. 注册notification + await subscribeCharacteristic(deviceId, serviceId, notifyCharId, (data) => { + // 可在此处分发/处理notification + // console.log('Notification:', data); + }); + + // 7. 返回结果 + return { serviceId, writeCharId, notifyCharId }; +}; \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/utssdk/web/device-manager.uts b/uni_modules/ak-sbsrv/utssdk/web/device-manager.uts new file mode 100644 index 0000000..20ac5b7 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/web/device-manager.uts @@ -0,0 +1,188 @@ +// 设备管理相关:扫描、连接、断开、重连 +import { BleDevice, BLE_CONNECTION_STATE } from '../interface.uts'; +import type { BleConnectOptionsExt } from '../interface.uts'; + +export class DeviceManager { + private devices = {}; + private servers = {}; + private connectionStates = {}; + private allowedServices = {}; + private reconnectAttempts: number = 0; + private maxReconnectAttempts: number = 5; + private reconnectDelay: number = 2000; + private reconnectTimeoutId: number = 0; + private autoReconnect: boolean = false; + private connectionStateChangeListeners: Function[] = []; + + private deviceFoundListeners: ((device: BleDevice) => void)[] = []; + private scanFinishedListeners: (() => void)[] = []; + + onDeviceFound(listener: (device: BleDevice) => void) { + this.deviceFoundListeners.push(listener); + } + onScanFinished(listener: () => void) { + this.scanFinishedListeners.push(listener); + } + private emitDeviceFound(device: BleDevice) { + for (const listener of this.deviceFoundListeners) { + try { listener(device); } catch (e) {} + } + } + private emitScanFinished() { + for (const listener of this.scanFinishedListeners) { + try { listener(); } catch (e) {} + } + } + + async startScan(options?: { optionalServices?: string[] } ): Promise { + if (!navigator.bluetooth) throw new Error('Web Bluetooth API not supported'); + try { + const scanOptions: any = { acceptAllDevices: true }; + // allow callers to request optionalServices (required by Web Bluetooth to access custom services) + if (options && Array.isArray(options.optionalServices) && options.optionalServices.length > 0) { + scanOptions.optionalServices = options.optionalServices; + } + // Log the exact options passed to requestDevice for debugging optionalServices propagation + try { + console.log('[DeviceManager] requestDevice options:', JSON.stringify(scanOptions)); + } catch (e) { + console.log('[DeviceManager] requestDevice options (raw):', scanOptions); + } + const device = await navigator.bluetooth.requestDevice(scanOptions); + try { + console.log('[DeviceManager] requestDevice result:', device); + } catch (e) { + console.log('[DeviceManager] requestDevice result (raw):', device); + } + if (device) { + console.log(device) + // 格式化 deviceId 为 MAC 地址格式 + const formatDeviceId = (id: string): string => { + // 如果是12位16进制字符串(如 'AABBCCDDEEFF'),转为 'AA:BB:CC:DD:EE:FF' + if (/^[0-9A-Fa-f]{12}$/.test(id)) { + return id.match(/.{1,2}/g)!.join(":").toUpperCase(); + } + // 如果是base64,无法直接转MAC,保留原样 + // 你可以根据实际情况扩展此处 + return id; + }; + const isConnected = !!this.servers[device.id]; + const formattedId = formatDeviceId(device.id); + const bleDevice = { deviceId: formattedId, name: device.name, connected: isConnected }; + this.devices[formattedId] = device; + this.emitDeviceFound(bleDevice); + } + this.emitScanFinished(); + } catch (e) { + this.emitScanFinished(); + throw e; + } + } + + onConnectionStateChange(listener: (deviceId: string, state: string) => void) { + this.connectionStateChangeListeners.push(listener); + } + private emitConnectionStateChange(deviceId: string, state: string) { + for (const listener of this.connectionStateChangeListeners) { + try { + listener(deviceId, state); + } catch (e) { + // 忽略单个回调异常 + } + } + } + + async connectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise { + this.autoReconnect = options?.autoReconnect ?? false; + try { + const device = this.devices[deviceId]; + if (!device) throw new Error('设备未找到'); + const server = await device.gatt.connect(); + this.servers[deviceId] = server; + this.connectionStates[deviceId] = BLE_CONNECTION_STATE.CONNECTED; + this.reconnectAttempts = 0; + this.emitConnectionStateChange(deviceId, 'connected'); + // 监听物理断开 + if (device.gatt) { + device.gatt.onconnectionstatechanged = null; + device.gatt.onconnectionstatechanged = () => { + if (!device.gatt.connected) { + this.emitConnectionStateChange(deviceId, 'disconnected'); + } + }; + } + return true; + } catch (error) { + if (this.autoReconnect && this.reconnectAttempts < this.maxReconnectAttempts) { + return this.scheduleReconnect(deviceId); + } + throw error; + } + } + + async disconnectDevice(deviceId: string): Promise { + const device = this.devices[deviceId]; + if (!device) throw new Error('设备未找到'); + try { + if (device.gatt && device.gatt.connected) { + device.gatt.disconnect(); + } + delete this.servers[deviceId]; + this.connectionStates[deviceId] = BLE_CONNECTION_STATE.DISCONNECTED; + this.emitConnectionStateChange(deviceId, 'disconnected'); + } catch (e) { + throw e; + } + } + + getConnectedDevices(): BleDevice[] { + const connectedDevices: BleDevice[] = []; + for (const deviceId in this.servers) { + const device = this.devices[deviceId]; + if (device) { + connectedDevices.push({ deviceId: device.id, name: device.name || '未知设备', connected: true }); + } + } + return connectedDevices; + } + + handleDisconnect(deviceId: string) { + this.connectionStates[deviceId] = BLE_CONNECTION_STATE.DISCONNECTED; + this.emitConnectionStateChange(deviceId, 'disconnected'); + if (this.autoReconnect && this.reconnectAttempts < this.maxReconnectAttempts) { + this.scheduleReconnect(deviceId); + } + } + + private scheduleReconnect(deviceId: string): Promise { + this.reconnectAttempts++; + return new Promise((resolve, reject) => { + this.reconnectTimeoutId = setTimeout(() => { + this.connectDevice(deviceId, { autoReconnect: true }) + .then(resolve) + .catch(reject); + }, this.reconnectDelay); + }); + } + + cancelReconnect() { + if (this.reconnectTimeoutId) { + clearTimeout(this.reconnectTimeoutId); + this.reconnectTimeoutId = 0; + } + this.autoReconnect = false; + this.reconnectAttempts = 0; + } + + setMaxReconnectAttempts(attempts: number) { + this.maxReconnectAttempts = attempts; + } + + setReconnectDelay(delay: number) { + this.reconnectDelay = delay; + } + + isDeviceConnected(deviceId: string): boolean { + return !!this.servers[deviceId]; + } +} \ No newline at end of file diff --git a/uni_modules/ak-sbsrv/utssdk/web/dfu_manager.uts b/uni_modules/ak-sbsrv/utssdk/web/dfu_manager.uts new file mode 100644 index 0000000..e041c89 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/web/dfu_manager.uts @@ -0,0 +1,136 @@ +import * as BluetoothManager from './bluetooth_manager.uts' + +// 默认 Nordic DFU UUIDs (web 模式也可用,如设备使用自定义请传入 options) +const DFU_SERVICE_UUID = '00001530-1212-EFDE-1523-785FEABCD123' +const DFU_CONTROL_POINT_UUID = '00001531-1212-EFDE-1523-785FEABCD123' +const DFU_PACKET_UUID = '00001532-1212-EFDE-1523-785FEABCD123' + +export class WebDfuManager { + // startDfu: deviceId, firmwareBytes (Uint8Array), options + // options: { serviceId?, writeCharId?, notifyCharId?, chunkSize?, onProgress?, onLog?, useNordic?, controlParser?, controlTimeout? } + async startDfu(deviceId: string, firmwareBytes: Uint8Array, options?: any): Promise { + options = options || {}; + // 1. ensure connected and discover services + let svcInfo; + if (options.serviceId && options.writeCharId && options.notifyCharId) { + svcInfo = { serviceId: options.serviceId, writeCharId: options.writeCharId, notifyCharId: options.notifyCharId }; + } else { + svcInfo = await BluetoothManager.autoConnect(deviceId); + } + const serviceId = svcInfo.serviceId; + const writeCharId = svcInfo.writeCharId; + const notifyCharId = svcInfo.notifyCharId; + + const chunkSize = options.chunkSize ?? 20; + + // control parser + const controlParser = options.controlParser ?? (options.useNordic ? this._nordicControlParser.bind(this) : this._defaultControlParser.bind(this)); + + // subscribe notifications on control/notify char + let finalizeSub; + let resolved = false; + const promise = new Promise(async (resolve, reject) => { + const cb = (payload) => { + try { + const data = payload.data instanceof Uint8Array ? payload.data : new Uint8Array(payload.data); + options.onLog?.('control notify: ' + Array.from(data).join(',')); + const parsed = controlParser(data); + if (!parsed) return; + if (parsed.type === 'progress' && parsed.progress != null) { + if (options.useNordic && svcInfo && svcInfo.totalBytes) { + const percent = Math.floor((parsed.progress / svcInfo.totalBytes) * 100); + options.onProgress?.(percent); + } else { + options.onProgress?.(parsed.progress); + } + } else if (parsed.type === 'success') { + resolved = true; + resolve(); + } else if (parsed.type === 'error') { + reject(parsed.error ?? new Error('DFU device error')); + } + } catch (e) { + options.onLog?.('control handler error: ' + e); + } + }; + await BluetoothManager.subscribeCharacteristic(deviceId, serviceId, notifyCharId, cb); + finalizeSub = async () => { try { await BluetoothManager.subscribeCharacteristic(deviceId, serviceId, notifyCharId, () => {}); } catch(e){} }; + // write firmware in chunks + try { + let offset = 0; + const total = firmwareBytes.length; + // attach totalBytes for nordic if needed + svcInfo.totalBytes = total; + while (offset < total) { + const end = Math.min(offset + chunkSize, total); + const slice = firmwareBytes.subarray(offset, end); + // writeValue accepts ArrayBuffer + await BluetoothManager.writeCharacteristic(deviceId, serviceId, writeCharId, slice.buffer); + offset = end; + // optimistic progress + options.onProgress?.(Math.floor((offset / total) * 100)); + await this._sleep(options.chunkDelay ?? 6); + } + + // send validate/activate command to control point (placeholder) + try { + await BluetoothManager.writeCharacteristic(deviceId, serviceId, writeCharId, new Uint8Array([0x04]).buffer); + } catch (e) { + // ignore + } + + // wait for control success or timeout + const timeoutMs = options.controlTimeout ?? 20000; + const t = setTimeout(() => { + if (!resolved) reject(new Error('DFU control timeout')); + }, timeoutMs); + } catch (e) { + reject(e); + } + }); + + try { + await promise; + } finally { + // unsubscribe notifications + try { await BluetoothManager.unsubscribeCharacteristic(deviceId, serviceId, notifyCharId); } catch(e) {} + } + } + + _sleep(ms: number) { + return new Promise((r) => setTimeout(r, ms)); + } + + _defaultControlParser(data: Uint8Array) { + if (!data || data.length === 0) return null; + if (data.length >= 2) { + const maybeProgress = data[1]; + if (maybeProgress >= 0 && maybeProgress <= 100) return { type: 'progress', progress: maybeProgress }; + } + const op = data[0]; + if (op === 0x01) return { type: 'success' }; + if (op === 0xFF) return { type: 'error', error: data }; + return { type: 'info' }; + } + + _nordicControlParser(data: Uint8Array) { + if (!data || data.length === 0) return null; + const op = data[0]; + // 0x11 = Packet Receipt Notification + if (op === 0x11 && data.length >= 3) { + const lsb = data[1]; + const msb = data[2]; + const received = (msb << 8) | lsb; + return { type: 'progress', progress: received }; + } + // 0x10 = Response + if (op === 0x10 && data.length >= 3) { + const resultCode = data[2]; + if (resultCode === 0x01) return { type: 'success' }; + return { type: 'error', error: { resultCode } }; + } + return null; + } +} + +export const dfuManager = new WebDfuManager(); diff --git a/uni_modules/ak-sbsrv/utssdk/web/index.uts b/uni_modules/ak-sbsrv/utssdk/web/index.uts new file mode 100644 index 0000000..02aef1d --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/web/index.uts @@ -0,0 +1,46 @@ +import * as BluetoothManager from './bluetooth_manager.uts'; + +export const bluetoothService = { + scanDevices: BluetoothManager.scanDevices, + connectDevice: BluetoothManager.connectDevice, + disconnectDevice: BluetoothManager.disconnectDevice, + getConnectedDevices: BluetoothManager.getConnectedDevices, + discoverServices: BluetoothManager.discoverServices, + // compatibility aliases used by app code + getServices: BluetoothManager.discoverServices, + getCharacteristics: BluetoothManager.getCharacteristics, + readCharacteristic: BluetoothManager.readCharacteristic, + writeCharacteristic: BluetoothManager.writeCharacteristic, + subscribeCharacteristic: BluetoothManager.subscribeCharacteristic, + unsubscribeCharacteristic: BluetoothManager.unsubscribeCharacteristic, + sendCommand: BluetoothManager.sendCommand, + onConnectionStateChange: BluetoothManager.onConnectionStateChange, + // 兼容旧接口,如有 readCharacteristic 可补充 +}; + +// Provide a minimal EventEmitter-style `.on(eventName, handler)` to match app code +// Supported events: 'deviceFound', 'scanFinished', 'connectionStateChanged' +bluetoothService.on = function(eventName: string, handler: Function) { + if (!eventName || typeof handler !== 'function') return; + switch (eventName) { + case 'deviceFound': + return BluetoothManager.onDeviceFound(handler); + case 'scanFinished': + return BluetoothManager.onScanFinished(handler); + case 'connectionStateChanged': + return BluetoothManager.onConnectionStateChange(handler); + default: + // no-op for unsupported events + return; + } +}; + +// Backwards-compat: getAutoBleInterfaces expected by pages -> maps to autoConnect +if (!bluetoothService.getAutoBleInterfaces) { + bluetoothService.getAutoBleInterfaces = function(deviceId: string) { + return BluetoothManager.autoConnect(deviceId); + } +} + +import { dfuManager as webDfuManager } from './dfu_manager.uts' +export const dfuManager = webDfuManager; diff --git a/uni_modules/ak-sbsrv/utssdk/web/service-manager.uts b/uni_modules/ak-sbsrv/utssdk/web/service-manager.uts new file mode 100644 index 0000000..2125944 --- /dev/null +++ b/uni_modules/ak-sbsrv/utssdk/web/service-manager.uts @@ -0,0 +1,186 @@ +// 服务与特征值操作相关:服务发现、特征值读写、订阅 +import { BleService, BleCharacteristic } from '../interface.uts'; +import { BLE_SERVICE_PREFIXES } from './bluetooth_manager.uts'; + +// Helper: normalize UUIDs (accept 16-bit like '180F' and expand to full 128-bit) +function normalizeUuid(uuid: string): string { + if (!uuid) return uuid; + const u = uuid.toLowerCase(); + // already full form + if (u.length === 36 && u.indexOf('-') > 0) return u; + // allow forms like '180f' or '0x180f' + const hex = u.replace(/^0x/, '').replace(/[^0-9a-f]/g, ''); + if (/^[0-9a-f]{4}$/.test(hex)) { + return `0000${hex}-0000-1000-8000-00805f9b34fb`; + } + return uuid; +} + +export class ServiceManager { + private services = {}; + private characteristics = {}; + private characteristicCallbacks = {}; + private characteristicListeners = {}; + + constructor() { + } + + async discoverServices(deviceId: string, server: any): Promise { + // 获取设备的 GATT 服务器 + console.log(deviceId) + // 由外部传入 server + if (!server) throw new Error('设备未连接'); + const bleServices: BleService[] = []; + if (!this.services[deviceId]) this.services[deviceId] = {}; + try { + console.log('[ServiceManager] discoverServices called for', deviceId) + console.log('[ServiceManager] server param:', server) + let services = null; + // Typical case: server is a BluetoothRemoteGATTServer and has getPrimaryServices + if (server && typeof server.getPrimaryServices === 'function') { + console.log('server.getPrimaryServices') + services = await server.getPrimaryServices(); + } + if (server && server.gatt && typeof server.gatt.getPrimaryServices === 'function') { + // sometimes a BluetoothDevice object is passed instead of the server + console.log('server.gatt.getPrimaryServices') + + services = await server.gatt.getPrimaryServices(); + } + if (server && server.device && server.device.gatt && typeof server.device.gatt.getPrimaryServices === 'function') { + console.log('server.device.gatt.getPrimaryServices') + services = await server.device.gatt.getPrimaryServices(); + } else { + console.log('other getPrimaryServices') + // Last resort: if server is a wrapper with a connect method, try to ensure connected + if (server && typeof server.connect === 'function') { + console.log('[ServiceManager] attempting to connect via server.connect()') + try { + const s = await server.connect(); + if (s && typeof s.getPrimaryServices === 'function') services = await s.getPrimaryServices(); + } catch (e) { + console.warn('[ServiceManager] server.connect() failed', e) + } + } + } + console.log('[ServiceManager] services resolved:', services) + if (!services) throw new Error('无法解析 GATT services 对象 —— server 参数不包含 getPrimaryServices'); + for (let i = 0; i < services.length; i++) { + const service = services[i]; + const rawUuid = service.uuid; + const uuid = normalizeUuid(rawUuid); + bleServices.push({ uuid, isPrimary: true }); + this.services[deviceId][uuid] = service; + // ensure service UUID detection supports standard BLE services like Battery (0x180F) + const lower = uuid.toLowerCase(); + const isBattery = lower === '0000180f-0000-1000-8000-00805f9b34fb'; + if (isBattery || isBaeService(uuid) || isBleService(uuid, BLE_SERVICE_PREFIXES)) { + await this.getCharacteristics(deviceId, uuid); + } + } + return bleServices; + } catch (err) { + console.error('[ServiceManager] discoverServices error:', err) + throw err; + } + } + + async getCharacteristics(deviceId: string, serviceId: string): Promise { + const service = this.services[deviceId]?.[serviceId]; + if (!service) throw new Error('服务未找到'); + const characteristics = await service.getCharacteristics(); + console.log(characteristics) + const bleCharacteristics: BleCharacteristic[] = []; + if (!this.characteristics[deviceId]) this.characteristics[deviceId] = {}; + if (!this.characteristics[deviceId][serviceId]) this.characteristics[deviceId][serviceId] = {}; + for (const characteristic of characteristics) { + const properties = { + read: characteristic.properties.read || false, + write: characteristic.properties.write || characteristic.properties.writableAuxiliaries || characteristic.properties.reliableWrite || characteristic.properties.writeWithoutResponse || false, + notify: characteristic.properties.notify || false, + indicate: characteristic.properties.indicate || false + }; + console.log(characteristic.properties) + console.log(properties) + // Construct a BleCharacteristic-shaped object including the required `service` property + const bleCharObj = { + uuid: characteristic.uuid, + service: { uuid: serviceId, isPrimary: true }, + properties + }; + bleCharacteristics.push(bleCharObj); + // keep native characteristic reference for read/write/notify operations + this.characteristics[deviceId][serviceId][characteristic.uuid] = characteristic; + } + return bleCharacteristics; + } + + async writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, data: string | ArrayBuffer): Promise { + const characteristic = this.characteristics[deviceId]?.[serviceId]?.[characteristicId]; + if (!characteristic) throw new Error('特征值未找到'); + let buffer; + if (typeof data === 'string') { + buffer = new TextEncoder().encode(data).buffer; + } else { + buffer = data; + } + await characteristic.writeValue(buffer); + } + + async subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, callback): Promise { + const characteristic = this.characteristics[deviceId]?.[serviceId]?.[characteristicId]; + if (!characteristic) throw new Error('特征值未找到'); + if (!characteristic.properties.notify && !characteristic.properties.indicate) { + throw new Error('特征值不支持通知'); + } + if (!this.characteristicCallbacks[deviceId]) this.characteristicCallbacks[deviceId] = {}; + if (!this.characteristicCallbacks[deviceId][serviceId]) this.characteristicCallbacks[deviceId][serviceId] = {}; + this.characteristicCallbacks[deviceId][serviceId][characteristicId] = callback; + await characteristic.startNotifications(); + const listener = (event) => { + const value = event.target.value; + const data = new Uint8Array(value.buffer); + const cb = this.characteristicCallbacks[deviceId][serviceId][characteristicId]; + if (cb) { + cb({ deviceId, serviceId, characteristicId, data }); + } + }; + // store listener so it can be removed later + if (!this.characteristicListeners[deviceId]) this.characteristicListeners[deviceId] = {}; + if (!this.characteristicListeners[deviceId][serviceId]) this.characteristicListeners[deviceId][serviceId] = {}; + this.characteristicListeners[deviceId][serviceId][characteristicId] = { characteristic, listener }; + characteristic.addEventListener('characteristicvaluechanged', listener); + } + + async unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + const entry = this.characteristicListeners[deviceId]?.[serviceId]?.[characteristicId]; + if (!entry) return; + try { + const { characteristic, listener } = entry; + characteristic.removeEventListener('characteristicvaluechanged', listener); + await characteristic.stopNotifications(); + } catch (e) { + // ignore + } + // cleanup + delete this.characteristicListeners[deviceId][serviceId][characteristicId]; + delete this.characteristicCallbacks[deviceId][serviceId][characteristicId]; + } + + // Read a characteristic value and return ArrayBuffer + async readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + const characteristic = this.characteristics[deviceId]?.[serviceId]?.[characteristicId]; + if (!characteristic) throw new Error('特征值未找到'); + // Web Bluetooth returns a DataView from readValue() + const value = await characteristic.readValue(); + if (!value) return new ArrayBuffer(0); + // DataView.buffer is a shared ArrayBuffer; return a copy slice to be safe + try { + return value.buffer ? value.buffer.slice(0) : new Uint8Array(value).buffer; + } catch (e) { + // fallback + const arr = new Uint8Array(value); + return arr.buffer; + } + } +} \ No newline at end of file diff --git a/uni_modules/ak-sqlite/changelog.md b/uni_modules/ak-sqlite/changelog.md new file mode 100644 index 0000000..e69de29 diff --git a/uni_modules/ak-sqlite/package.json b/uni_modules/ak-sqlite/package.json new file mode 100644 index 0000000..bc9f31f --- /dev/null +++ b/uni_modules/ak-sqlite/package.json @@ -0,0 +1,92 @@ +{ + "id": "ak-sqlite", + "displayName": "适用于UNIAPP-X的SQLite API", + "version": "1.0.0", + "description": "createSQLiteContext", + "keywords": [ + "sqlite", + "uni-ext-api", + "uniapp-x", + "uts" + ], + "repository": "", + "engines": { + "HBuilderX": "^4.19" + }, + "dcloudext": { + "category": [ + "UTS插件", + "API插件" + ], + "contact": { + "qq": "" + }, + "declaration": { + "ads": "无", + "data": "none", + "permissions": "none" + }, + "npmurl": "" + }, + "uni_modules": { + "dependencies": [], + "uni-ext-api": { + "uni": { + "createSQLiteContext": { + "name": "createSQLiteContext", + "app": { + "js": false, + "kotlin": true, + "swift": false + } + } + } + }, + "encrypt": [], + "platforms": { + "cloud": { + "tcb": "u", + "aliyun": "u" + }, + "client": { + "Vue": { + "vue2": "u", + "vue3": "u" + }, + "App": { + "app-android": "u", + "app-ios": "u" + }, + "H5-mobile": { + "Safari": "n", + "Android Browser": "n", + "微信浏览器(Android)": "n", + "QQ浏览器(Android)": "n" + }, + "H5-pc": { + "Chrome": "n", + "IE": "n", + "Edge": "n", + "Firefox": "n", + "Safari": "n" + }, + "小程序": { + "微信": "n", + "阿里": "n", + "百度": "n", + "字节跳动": "n", + "QQ": "n", + "钉钉": "u", + "快手": "u", + "飞书": "u", + "京东": "u" + }, + "快应用": { + "华为": "n", + "联盟": "n" + } + } + } + }, + "name": "适用于UNIAPP-X的SQLite API" +} \ No newline at end of file diff --git a/uni_modules/ak-sqlite/readme.md b/uni_modules/ak-sqlite/readme.md new file mode 100644 index 0000000..2aff34f --- /dev/null +++ b/uni_modules/ak-sqlite/readme.md @@ -0,0 +1,56 @@ +# uni-createSQLiteContext +### 开发文档 +[UTS 语法](https://uniapp.dcloud.net.cn/tutorial/syntax-uts.html) +[UTS API插件](https://uniapp.dcloud.net.cn/plugin/uts-plugin.html) +[UTS 组件插件](https://uniapp.dcloud.net.cn/plugin/uts-component.html) +[Hello UTS](https://gitcode.net/dcloud/hello-uts) + +### 注意事项 + +本插件本质上是一个uni ext api,所以直接使用即可,无需显式调用import导入。 + +### 使用方法 + +```javascript +//创建查询的上下文 +const sqliteContext = uni.createSQLiteContext({ + name: 'test.db', +}); + +//执行查询 +sqliteContext.selectSql({ + sql: 'select * from test', + success: function(res) { + console.log(res); + }, + fail: function(err) { + console.log(err); + } +}) + +//执行事务 +sqliteContext.transaction({ + operation:"begin", //begin,commit,rollback + success: function(res) { + console.log(res); + }, + fail: function(err) { + console.log(err); + } +}) + +//执行增删改 +sqliteContext.executeSql({ + sql: 'insert into test values(1, "test")', + success: function(res) { + console.log(res); + }, + fail: function(err) { + console.log(err); + } +}) + +//关闭数据库 +sqliteContext.close() + +``` \ No newline at end of file diff --git a/uni_modules/ak-sqlite/utssdk/app-android/config.json b/uni_modules/ak-sqlite/utssdk/app-android/config.json new file mode 100644 index 0000000..5defc8f --- /dev/null +++ b/uni_modules/ak-sqlite/utssdk/app-android/config.json @@ -0,0 +1,3 @@ +{ + "minSdkVersion": "21" +} diff --git a/uni_modules/ak-sqlite/utssdk/app-android/index.uts b/uni_modules/ak-sqlite/utssdk/app-android/index.uts new file mode 100644 index 0000000..9c4009a --- /dev/null +++ b/uni_modules/ak-sqlite/utssdk/app-android/index.uts @@ -0,0 +1,178 @@ +import Cursor from 'android.database.Cursor'; +import SQLiteDatabase from 'android.database.sqlite.SQLiteDatabase'; +import SQLiteOpenHelper from 'android.database.sqlite.SQLiteOpenHelper'; + +import { createSQLiteContextOptions, executeSqlOptions, selectSqlOptions, executeSqlOptionsResult, selectSqlOptionsResult, transactionOptions,transactionResult } from '../interface.uts'; + +class SQLiteContext extends SQLiteOpenHelper { + private databaseName: string | null; + + constructor(name: string) { + super(UTSAndroid.getAppContext()!, name, null, 1); + this.databaseName = name; + } + + public executeSql(options: executeSqlOptions): void { + const database: SQLiteDatabase = this.getReadableDatabase(); + const SqlArray = options.sql.split(';'); + let result: executeSqlOptionsResult = { + data: [] as boolean[], + errMsg: 'executeSql:ok', + errCode: 0, + errSubject: '', + cause: null + } + try { + for (let i = 0; i < SqlArray.length; i++) { + if (SqlArray[i].length > 0) { + const sql = SqlArray[i].replace(/^\s+/, ''); + try { + database.execSQL(sql); + result.data.push(true); + } catch (err) { + console.error('database.execSQL 出错:', err, 'SQL:', sql); + result.data.push(false); + // 立即调用 fail 并返回 + result.errMsg = 'executeSql:fail'; + result.errCode = 1000002; + result.cause = err; + options.fail?.(result); + options.complete?.(result); + return; + } + } + } + options.success?.(result); + } catch (e) { + console.error('executeSql 外层出错:', e); + const data = result.data; + result = { + errCode: 1000002, + errMsg: 'executeSql:fail', + errSubject: '', + cause: e, + data: data + }; + options.fail?.(result); + } + options.complete?.(result); + } + + public selectSql(options: selectSqlOptions): void { + const database: SQLiteDatabase = this.getReadableDatabase(); + const SqlArray = options.sql.split(';'); + let result: selectSqlOptionsResult = { + data: [] as string[][], + errMsg: 'selectSql:ok', + errCode: 0, + errSubject: '', + cause: null + } + try { + for (let i = 0; i < SqlArray.length; i++) { + if (SqlArray[i].length > 0) { + const sql = SqlArray[i].replace(/^\s+/, ''); + try { + const cursor: Cursor = database.rawQuery(sql, null); + //获取查询结果的字符串并push到result.data中 + if (cursor.moveToFirst()) { + do { + const row = cursor.getColumnCount(); + const rowArray = [] as string[]; + for (let j = 0; j < row; j++) { + rowArray.push(cursor.getString(j.toInt())); + } + result.data.push(rowArray); + } while (cursor.moveToNext()); + } + cursor.close(); + } catch { + result.data.push([] as string[]); + } + } + } + options.success?.(result); + } catch (e) { + const data = result.data; + result = { + errCode: 1000003, + errMsg: 'selectSql:fail', + errSubject: '', + cause: e, + data: data + }; + options.fail?.(result); + } + options.complete?.(result); + } + + public transaction(options: transactionOptions): void { + const database: SQLiteDatabase = this.getReadableDatabase(); + const transaction = options.transaction; + let result: transactionResult = { + errMsg: 'transaction:ok', + errCode: 0, + errSubject: '', + cause: null + }; + try { + if (transaction == 'begin') { + database.execSQL('BEGIN TRANSACTION'); + } else if (transaction == 'commit') { + database.execSQL('COMMIT'); + } else if (transaction == 'rollback') { + database.execSQL('ROLLBACK'); + } + options.success?.(result); + } catch (e) { + let errCode = 1000008; + if (transaction == 'begin') { + errCode = 1000004; + } else if (transaction == 'commit') { + errCode = 1000005; + } else if (transaction == 'rollback') { + errCode = 1000006; + } + result = { + errCode: errCode, + errMsg: 'transaction:fail', + errSubject: '', + cause: e + }; + options.fail?.(result); + } + options.complete?.(result); + } + + public override onCreate(db: SQLiteDatabase): void { + // 可选:初始化表结构 + } + + public override onUpgrade(db: SQLiteDatabase, oldVersion: Int, newVersion: Int): void { + // 可选:数据库升级逻辑 + } +} + +export const createSQLiteContext = function (options: createSQLiteContextOptions) { + const name = options.name + '.db'; + return new SQLiteContext(name); // 必须返回对象 +} + + + +export type executeSqlOptionsResultType = { + errCode: number; + errSubject?: string; + cause?: any; + errMsg: string; + date?: boolean[]; +}; + +export type selectSqlOptionsResultType = { + errCode: number; + errSubject?: string; + cause?: any; + errMsg: string; + date?: string[]; +}; + diff --git a/uni_modules/ak-sqlite/utssdk/app-ios/config.json b/uni_modules/ak-sqlite/utssdk/app-ios/config.json new file mode 100644 index 0000000..2046150 --- /dev/null +++ b/uni_modules/ak-sqlite/utssdk/app-ios/config.json @@ -0,0 +1,13 @@ +{ + "deploymentTarget": "9.0", + "dependencies-pods": [ + { + "name": "FMDB", + "version": "2.7.8", + "repo": { + "git": "https://github.com/ccgus/fmdb.git", + "tag": "2.7.8" + } + } + ] +} \ No newline at end of file diff --git a/uni_modules/ak-sqlite/utssdk/app-ios/index.uts b/uni_modules/ak-sqlite/utssdk/app-ios/index.uts new file mode 100644 index 0000000..e834429 --- /dev/null +++ b/uni_modules/ak-sqlite/utssdk/app-ios/index.uts @@ -0,0 +1,116 @@ +import { FMDatabase } from 'FMDB'; + +import { createSQLiteContextOptions, executeSqlOptions, selectSqlOptions, executeSqlOptionsResult, selectSqlOptionsResult, CreateSQLiteContext, transactionOptions } from '../interface.uts'; +import { createSQLiteContextFailImpl } from '../unierror.uts'; + +class SQLiteContext extends FMDatabase { + private databaseName: string | null; + + constructor(name: string) { + let version = 1; + const path = UTSiOS.getDataPath() + '/sqlite/' + name; + super(path); + this.databaseName = name; + } + + public executeSql(options: executeSqlOptions) { + const SqlArray = options.sql.split(';'); + let result: executeSqlOptionsResult = { + data: [] as boolean[], + errMsg: 'executeSql:ok', + } + try { + for (let i = 0; i < SqlArray.length; i++) { + if (SqlArray[i].length > 0) { + const sql = SqlArray[i].replace(/^\s+/, ''); + try { + this.executeQuery(sql); + result.data.push(true); + } catch { + result.data.push(false); + } + } + } + options.success?.(result); + } catch (e) { + const data = result.data; + result = new createSQLiteContextFailImpl(1000002); + result.data = data; + options.fail?.(result); + } + options.complete?.(result); + return result; + } + + public selectSql(options: selectSqlOptions) { + const SqlArray = options.sql.split(';'); + let result: selectSqlOptionsResult = { + data: [] as boolean[], + errMsg: 'selectSql:ok', + } + try { + for (let i = 0; i < SqlArray.length; i++) { + if (SqlArray[i].length > 0) { + const sql = SqlArray[i].replace(/^\s+/, ''); + try { + const cursor = this.executeQueryWithFormat(sql); + //获取查询结果的字符串并push到result.data中 + while (cursor.next()) { + const row = cursor.getRow(); + result.data.push(row); + } + cursor.close(); + } catch { + result.data.push(""); + } + } + } + options.success?.(result); + } catch (e) { + const data = result.data; + result = new createSQLiteContextFailImpl(1000003); + result.data = data; + options.fail?.(result); + } + options.complete?.(result); + return result; + } + + public transaction(options: transactionOptions) { + const transaction = options.transaction; + let result: executeSqlOptionsResult = { + errMsg: 'transaction:ok', + } + try { + if (transaction == 'begin') { + //开启事务 + this.beginTransaction(); + } else if (transaction == 'commit') { + //提交事务 + this.commit(); + } else if (transaction == 'rollback') { + //回滚事务 + this.rollback(); + } + options.success?.(result); + } catch (e) { + let errCode = 1000008; + if (transaction == 'begin') { + errCode = 1000004; + } else if (transaction == 'commit') { + errCode = 1000005; + } else if (transaction == 'rollback') { + errCode = 1000006; + } + result = new createSQLiteContextFailImpl(errCode); + options.fail?.(result); + } + options.complete?.(result); + return result; + } +} + +export const createSQLiteContext: CreateSQLiteContext = function (options: createSQLiteContextOptions) { + const name = options.name + '.db'; + return new SQLiteContext(name); +} \ No newline at end of file diff --git a/uni_modules/ak-sqlite/utssdk/interface.uts b/uni_modules/ak-sqlite/utssdk/interface.uts new file mode 100644 index 0000000..83bacbd --- /dev/null +++ b/uni_modules/ak-sqlite/utssdk/interface.uts @@ -0,0 +1,153 @@ +/** + * 初始化数据库时的相关配置 + * @param name 数据库名称 + */ +export type createSQLiteContextOptions = { + /** + * 数据库名称 + */ + name: string, +} + +/** + * 执行增删改等操作的SQL语句的相关配置 + * @param sql SQL语句 + * @param success 成功回调 + * @param fail 失败回调 + * @param complete 完成回调 + */ +export type executeSqlOptions = { + /** + * SQL语句 + */ + sql: string, + /** + * 执行增删改等操作的SQL语句的成功回调 + */ + success?: executeSqlOptionsSuccessCallback | null, + /** + * 执行增删改等操作的SQL语句的失败回调 + */ + fail?: executeSqlOptionsFailCallback | null, + /** + * 执行增删改等操作的SQL语句的完成回调 + */ + complete?: executeSqlOptionsCompleteCallback | null, +} + +/** + * 执行增删改等操作的SQL语句的成功回调 + */ +export type executeSqlOptionsSuccessCallback = (res: executeSqlOptionsResult) => void + +/** + * 执行增删改等操作的SQL语句的失败回调 + */ +export type executeSqlOptionsFailCallback = (res: executeSqlOptionsResult) => void + +/** + * 执行增删改等操作的SQL语句的完成回调 + */ +export type executeSqlOptionsCompleteCallback = (res: executeSqlOptionsResult) => void + +export type transactionResult = { + errCode: number; + errSubject?: string; + cause?: any; + errMsg: string; +}; + +export type ICreateSQLiteContextError = { + errCode: number; + errSubject?: string; + cause?: any; + errMsg: string; +}; + +export type executeSqlOptionsResult = { + errCode: number; + errSubject?: string; + cause?: any; + errMsg: string; + data: boolean[]; +} + +/** + * 执行查询操作的SQL语句的相关配置 + */ +export type selectSqlOptions = { + /** + * SQL语句 + */ + sql: string, + /** + * 执行查询操作的SQL语句的成功回调 + */ + success?: selectSqlOptionsSuccessCallback | null, + /** + * 执行查询操作的SQL语句的失败回调 + */ + fail?: selectSqlOptionsFailCallback | null, + /** + * 执行查询操作的SQL语句的完成回调 + */ + complete?: selectSqlOptionsCompleteCallback | null, +} + +/** + * 执行查询操作的SQL语句的成功回调 + */ +export type selectSqlOptionsSuccessCallback = (res: selectSqlOptionsResult) => void + +/** + * 执行查询操作的SQL语句的失败回调 + */ +export type selectSqlOptionsFailCallback = (res: selectSqlOptionsResult) => void + +/** + * 执行查询操作的SQL语句的完成回调 + */ +export type selectSqlOptionsCompleteCallback = (res: selectSqlOptionsResult) => void + + +export type selectSqlOptionsResult = { + errCode: number; + errSubject?: string; + cause?: any; + errMsg: string; + data: string[][]; +} + + +export type transactionOptions = { + transaction: transactionOperation; + success?: (res: transactionResult) => void; + fail?: (res: transactionResult) => void; + complete?: (res: transactionResult) => void; +} + +/** + * 事务操作类型 + * @param begin 开始事务 + * @param commit 提交事务 + * @param rollback 回滚事务 + */ +export type transactionOperation = 'begin' | 'commit' | 'rollback' + +/** + * 事务执行的成功回调 + */ +export type transactionSuccessCallback = (res: transactionResult) => void + +/** + * 事务执行的失败回调 + */ +export type transactionFailCallback = (res: transactionResult) => void + +/** + * 事务执行的完成回调 + */ +export type transactionCompleteCallback = (res: transactionResult) => void + + + diff --git a/uni_modules/ak-sqlite/utssdk/unierror.uts b/uni_modules/ak-sqlite/utssdk/unierror.uts new file mode 100644 index 0000000..4a0155b --- /dev/null +++ b/uni_modules/ak-sqlite/utssdk/unierror.uts @@ -0,0 +1,65 @@ +import { ICreateSQLiteContextError } from "./interface.uts" + +/** + * 错误主题 + */ +export const UniErrorSubject = 'uni-create-sql-context'; + +/** + * 错误码 + * @UniError + */ +export const UniErrors: Map = new Map([ + /** + * 数据库启动失败 + */ + [1000001, 'Database startup failed'], + /** + * 执行SQL增删改语句失败 + */ + [1000002, 'Failed to execute SQL insert, update, delete statement'], + /** + * 执行SQL查询语句失败 + */ + [1000003, 'Failed to execute SQL query statement'], + /** + * 事务开始失败 + */ + [1000004, 'Transaction start failed'], + /** + * 事务提交失败 + */ + [1000005, 'Transaction commit failed'], + /** + * 事务回滚失败 + */ + [1000006, 'Transaction rollback failed'], + /** + * 数据库关闭失败 + */ + [1000007, 'Database shutdown failed'], + /** + * 未知错误 + */ + [1000008, 'Unknown error'], +]); + +export class createSQLiteContextFailImpl extends UniError { + override errCode: number; + override errSubject: string; + override cause?: UTSError | null; + override errMsg: string; + + constructor( + errCode: number, + errMsg: string = '', + errSubject: string = '', + cause?: UTSError | null + ) { + super(); + this.errCode = errCode; + this.errMsg = errMsg; + this.errSubject = errSubject; + this.cause = cause ?? null; + } +} \ No newline at end of file diff --git a/uni_modules/uni-getbatteryinfo/changelog.md b/uni_modules/uni-getbatteryinfo/changelog.md new file mode 100644 index 0000000..03f2110 --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/changelog.md @@ -0,0 +1,14 @@ +## 1.3.1(2023-09-15) +app端适配使用UniError + +## 1.3.0(2023-05-30) +新增 同步获取电量api + +## 1.2.0(2022-10-17) +实现百度小程序/支付宝小程序/QQ小程序获取电量 + +## 1.1.0(2022-10-17) +实现ios平台获取电量 + +## 1.0.0(2022-09-01) +实现android/web/微信小程序平台获取电量 diff --git a/uni_modules/uni-getbatteryinfo/package.json b/uni_modules/uni-getbatteryinfo/package.json new file mode 100644 index 0000000..0fc760c --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/package.json @@ -0,0 +1,93 @@ +{ + "id": "uni-getbatteryinfo", + "displayName": "uni-getbatteryinfo", + "version": "1.3.1", + "description": "使用uts开发,实现在多个平台获取电池电量功能", + "keywords": [ + "battery" +], + "repository": "", + "engines": { + "HBuilderX": "^3.9.0" + }, + "dcloudext": { + "type": "uts", + "sale": { + "regular": { + "price": "0.00" + }, + "sourcecode": { + "price": "0.00" + } + }, + "contact": { + "qq": "" + }, + "declaration": { + "ads": "无", + "data": "插件不采集任何数据", + "permissions": "无" + }, + "npmurl": "" + }, + "uni_modules": { + "uni-ext-api": { + "uni": { + "getBatteryInfo": "getBatteryInfo", + "getBatteryInfoSync": { + "web": false + } + } + }, + "dependencies": [], + "encrypt": [], + "platforms": { + "cloud": { + "tcb": "y", + "aliyun": "y" + }, + "client": { + "Vue": { + "vue2": "n", + "vue3": "y" + }, + "App": { + "app-android": { + "minVersion": "21" + }, + "app-ios": { + "minVersion": "9" + } + }, + "H5-mobile": { + "Safari": "y", + "Android Browser": "y", + "微信浏览器(Android)": "y", + "QQ浏览器(Android)": "y" + }, + "H5-pc": { + "Chrome": "y", + "IE": "y", + "Edge": "y", + "Firefox": "y", + "Safari": "y" + }, + "小程序": { + "微信": "y", + "阿里": "y", + "百度": "y", + "字节跳动": "u", + "QQ": "y", + "钉钉": "u", + "快手": "u", + "飞书": "u", + "京东": "u" + }, + "快应用": { + "华为": "u", + "联盟": "u" + } + } + } + } +} \ No newline at end of file diff --git a/uni_modules/uni-getbatteryinfo/readme.md b/uni_modules/uni-getbatteryinfo/readme.md new file mode 100644 index 0000000..0609fee --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/readme.md @@ -0,0 +1,38 @@ +# uni-getbatteryinfo + +## 使用文档 + +```ts + // 获取电量信息 +uni.getBatteryInfo({ + success(res) { + console.log(res); + uni.showToast({ + title: "当前电量:" + res.level + '%', + icon: 'none' + }); + } +}) +``` + + + +### 参数 + +Object object + +|属性|类型|必填|说明| +|----|---|----|----| +|success|function|否|接口调用成功的回调函数| +|fail|function|否|接口调用失败的回调函数| +|complete|function|否|接口调用结束的回调函数(调用成功、失败都会执行)| + + + +object.success 回调函数 + + +|属性|类型|说明| +|----|---|----| +|level|number|设备电量,范围 1 - 100| +|isCharging|boolean|是否正在充电中| diff --git a/uni_modules/uni-getbatteryinfo/utssdk/app-android/config.json b/uni_modules/uni-getbatteryinfo/utssdk/app-android/config.json new file mode 100644 index 0000000..bf95925 --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/app-android/config.json @@ -0,0 +1,3 @@ +{ + "minSdkVersion": "21" +} \ No newline at end of file diff --git a/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts b/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts new file mode 100644 index 0000000..8343697 --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts @@ -0,0 +1,76 @@ +import Context from "android.content.Context"; +import BatteryManager from "android.os.BatteryManager"; + +import { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts' +import IntentFilter from 'android.content.IntentFilter'; +import Intent from 'android.content.Intent'; + +import { GetBatteryInfoFailImpl } from '../unierror'; + +/** + * 异步获取电量 + */ +export const getBatteryInfo : GetBatteryInfo = function (options : GetBatteryInfoOptions) { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const manager = context.getSystemService( + Context.BATTERY_SERVICE + ) as BatteryManager; + const level = manager.getIntProperty( + BatteryManager.BATTERY_PROPERTY_CAPACITY + ); + + let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED); + let batteryStatus = context.registerReceiver(null, ifilter); + let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1); + let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL; + + const res : GetBatteryInfoSuccess = { + errMsg: 'getBatteryInfo:ok', + level, + isCharging: isCharging + } + options.success?.(res) + options.complete?.(res) + } else { + let res = new GetBatteryInfoFailImpl(1001); + options.fail?.(res) + options.complete?.(res) + } +} + +/** + * 同步获取电量 + */ +export const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const manager = context.getSystemService( + Context.BATTERY_SERVICE + ) as BatteryManager; + const level = manager.getIntProperty( + BatteryManager.BATTERY_PROPERTY_CAPACITY + ); + + let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED); + let batteryStatus = context.registerReceiver(null, ifilter); + let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1); + let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL; + + const res : GetBatteryInfoResult = { + level: level, + isCharging: isCharging + }; + return res; + } + else { + /** + * 无有效上下文 + */ + const res : GetBatteryInfoResult = { + level: -1, + isCharging: false + }; + return res; + } +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/app-ios/config.json b/uni_modules/uni-getbatteryinfo/utssdk/app-ios/config.json new file mode 100644 index 0000000..721b81e --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/app-ios/config.json @@ -0,0 +1,3 @@ +{ + "deploymentTarget": "9" +} \ No newline at end of file diff --git a/uni_modules/uni-getbatteryinfo/utssdk/app-ios/index.uts b/uni_modules/uni-getbatteryinfo/utssdk/app-ios/index.uts new file mode 100644 index 0000000..5578c9f --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/app-ios/index.uts @@ -0,0 +1,36 @@ +// 引用 iOS 原生平台 api +import { UIDevice } from "UIKit"; + +import { GetBatteryInfo, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts'; + +/** + * 异步获取电量 + */ +export const getBatteryInfo : GetBatteryInfo = function (options) { + // 开启电量检测 + UIDevice.current.isBatteryMonitoringEnabled = true + + // 返回数据 + const res : GetBatteryInfoSuccess = { + errMsg: "getBatteryInfo:ok", + level: Math.abs(Number(UIDevice.current.batteryLevel * 100)), + isCharging: UIDevice.current.batteryState == UIDevice.BatteryState.charging, + }; + options.success?.(res); + options.complete?.(res); +} + +/** + * 同步获取电量 + */ +export const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult { + // 开启电量检测 + UIDevice.current.isBatteryMonitoringEnabled = true + + // 返回数据 + const res : GetBatteryInfoResult = { + level: Math.abs(Number(UIDevice.current.batteryLevel * 100)), + isCharging: UIDevice.current.batteryState == UIDevice.BatteryState.charging, + }; + return res; +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/index.d.ts b/uni_modules/uni-getbatteryinfo/utssdk/index.d.ts new file mode 100644 index 0000000..367327b --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/index.d.ts @@ -0,0 +1,43 @@ +declare namespace UniNamespace { + interface GetBatteryInfoSuccessCallbackResult { + /** + * 是否正在充电中 + */ + isCharging: boolean; + /** + * 设备电量,范围 1 - 100 + */ + level: number; + errMsg: string; + } + + interface GetBatteryInfoOption { + /** + * 接口调用结束的回调函数(调用成功、失败都会执行) + */ + complete?: Function + /** + * 接口调用失败的回调函数 + */ + fail?: Function + /** + * 接口调用成功的回调函数 + */ + success?: (result: GetBatteryInfoSuccessCallbackResult) => void + } +} + +declare interface Uni { + /** + * 获取设备电量 + * + * @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html + */ + getBatteryInfo(option?: UniNamespace.GetBatteryInfoOption): void; + + /** + * 同步获取电池电量信息 + * @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html + */ + getBatteryInfoSync(): UniNamespace.GetBatteryInfoSuccessCallbackResult; +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/interface.uts b/uni_modules/uni-getbatteryinfo/utssdk/interface.uts new file mode 100644 index 0000000..6b413ab --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/interface.uts @@ -0,0 +1,138 @@ +export type GetBatteryInfoSuccess = { + errMsg : string, + /** + * 设备电量,范围1 - 100 + */ + level : number, + /** + * 是否正在充电中 + */ + isCharging : boolean +} + +export type GetBatteryInfoOptions = { + /** + * 接口调用结束的回调函数(调用成功、失败都会执行) + */ + success ?: (res : GetBatteryInfoSuccess) => void + /** + * 接口调用失败的回调函数 + */ + fail ?: (res : UniError) => void + /** + * 接口调用成功的回调 + */ + complete ?: (res : any) => void +} + +export type GetBatteryInfoResult = { + /** + * 设备电量,范围1 - 100 + */ + level : number, + /** + * 是否正在充电中 + */ + isCharging : boolean +} + +/** + * 错误码 + * - 1001 getAppContext is null + */ +export type GetBatteryInfoErrorCode = 1001 ; +/** + * GetBatteryInfo 的错误回调参数 + */ +export interface GetBatteryInfoFail extends IUniError { + errCode : GetBatteryInfoErrorCode +}; + +/** +* 获取电量信息 +* @param {GetBatteryInfoOptions} options +* +* +* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html +* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22 +* @since 3.6.11 +* +* @assert () => success({errCode: 0, errSubject: "uni-getBatteryInfo", errMsg: "getBatteryInfo:ok", level: 60, isCharging: false }) +* @assert () => fail({errCode: 1001, errSubject: "uni-getBatteryInfo", errMsg: "getBatteryInfo:fail getAppContext is null" }) +*/ +export type GetBatteryInfo = (options : GetBatteryInfoOptions) => void + + +export type GetBatteryInfoSync = () => GetBatteryInfoResult + +interface Uni { + + /** + * 获取电池电量信息 + * @description 获取电池电量信息 + * @param {GetBatteryInfoOptions} options + * @example + * ```typescript + * uni.getBatteryInfo({ + * success(res) { + * console.log(res); + * } + * }) + * ``` + * @remark + * - 该接口需要同步调用 + * @uniPlatform { + * "app": { + * "android": { + * "osVer": "4.4.4", + * "uniVer": "3.6.11", + * "unixVer": "3.9.0" + * }, + * "ios": { + * "osVer": "12.0", + * "uniVer": "3.6.11", + * "unixVer": "4.11" + * } + * }, + * "web": { + * "uniVer": "3.6.11", + * "unixVer": "4.0" + * } + * } + * @uniVueVersion 2,3 //支持的vue版本 + * + */ + getBatteryInfo (options : GetBatteryInfoOptions) : void, + /** + * 同步获取电池电量信息 + * @description 获取电池电量信息 + * @example + * ```typescript + * uni.getBatteryInfo() + * ``` + * @remark + * - 该接口需要同步调用 + * @uniPlatform { + * "app": { + * "android": { + * "osVer": "4.4.4", + * "uniVer": "3.6.11", + * "unixVer": "3.9.0" + * }, + * "ios": { + * "osVer": "12.0", + * "uniVer": "3.6.11", + * "unixVer": "4.11" + * } + * }, + * "web": { + * "uniVer": "3.6.11", + * "unixVer": "4.0" + * } + * } + * @uniVueVersion 2,3 //支持的vue版本 + * + */ + getBatteryInfoSync():GetBatteryInfoResult + +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/mp-alipay/index.js b/uni_modules/uni-getbatteryinfo/utssdk/mp-alipay/index.js new file mode 100644 index 0000000..473f1a0 --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/mp-alipay/index.js @@ -0,0 +1,6 @@ +export function getBatteryInfo(options) { + return my.getBatteryInfo(options) +} +export function getBatteryInfoSync(options) { + return my.getBatteryInfoSync(options) +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/mp-baidu/index.js b/uni_modules/uni-getbatteryinfo/utssdk/mp-baidu/index.js new file mode 100644 index 0000000..1ee373a --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/mp-baidu/index.js @@ -0,0 +1,6 @@ +export function getBatteryInfo(options) { + return swan.getBatteryInfo(options) +} +export function getBatteryInfoSync(options) { + return swan.getBatteryInfoSync(options) +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/mp-qq/index.js b/uni_modules/uni-getbatteryinfo/utssdk/mp-qq/index.js new file mode 100644 index 0000000..6eabfcf --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/mp-qq/index.js @@ -0,0 +1,6 @@ +export function getBatteryInfo(options) { + return qq.getBatteryInfo(options) +} +export function getBatteryInfoSync(options) { + return qq.getBatteryInfoSync(options) +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/mp-weixin/index.js b/uni_modules/uni-getbatteryinfo/utssdk/mp-weixin/index.js new file mode 100644 index 0000000..3bdfa91 --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/mp-weixin/index.js @@ -0,0 +1,6 @@ +export function getBatteryInfo(options) { + return wx.getBatteryInfo(options) +} +export function getBatteryInfoSync(options) { + return wx.getBatteryInfoSync(options) +} diff --git a/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts b/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts new file mode 100644 index 0000000..43d0be5 --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts @@ -0,0 +1,34 @@ +import { GetBatteryInfoErrorCode, GetBatteryInfoFail } from "./interface.uts" +/** + * 错误主题 + */ +export const UniErrorSubject = 'uni-getBatteryInfo'; + + +/** + * 错误信息 + * @UniError + */ +export const UniErrors : Map = new Map([ + /** + * 错误码及对应的错误信息 + */ + [1001, 'getBatteryInfo:fail getAppContext is null'], +]); + + +/** + * 错误对象实现 + */ +export class GetBatteryInfoFailImpl extends UniError implements GetBatteryInfoFail { + + /** + * 错误对象构造函数 + */ + constructor(errCode : GetBatteryInfoErrorCode) { + super(); + this.errSubject = UniErrorSubject; + this.errCode = errCode; + this.errMsg = UniErrors[errCode] ?? ""; + } +} \ No newline at end of file diff --git a/uni_modules/uni-getbatteryinfo/utssdk/web/index.uts b/uni_modules/uni-getbatteryinfo/utssdk/web/index.uts new file mode 100644 index 0000000..1542de5 --- /dev/null +++ b/uni_modules/uni-getbatteryinfo/utssdk/web/index.uts @@ -0,0 +1,20 @@ +import { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess } from '../interface.uts' +export const getBatteryInfo : GetBatteryInfo = function (options : GetBatteryInfoOptions) { + if (navigator.getBattery) { + navigator.getBattery().then(battery => { + const res = { + errCode: 0, + errSubject: "uni-getBatteryInfo", + errMsg: 'getBatteryInfo:ok', + level: battery.level * 100, + isCharging: battery.charging + } as GetBatteryInfoSuccess + options.success && options.success(res) + options.complete && options.complete(res) + }) + } else { + const res = new UniError("uni-getBatteryInfo", 1002, "getBatteryInfo:fail navigator.getBattery is unsupported") + options.fail && options.fail(res) + options.complete && options.complete(res) + } +} diff --git a/unpackage/OmFw2509140009.zip b/unpackage/OmFw2509140009.zip new file mode 100644 index 0000000..5b7b661 Binary files /dev/null and b/unpackage/OmFw2509140009.zip differ diff --git a/unpackage/aa.txt b/unpackage/aa.txt new file mode 100644 index 0000000..d8e95e3 --- /dev/null +++ b/unpackage/aa.txt @@ -0,0 +1,32 @@ +20:00:59.350 [sendCommandWithResponse] 发送命令: ‍[⁠io.dcloud.uts.Uint8Array⁠]‍ {BYTES_PER_ELEMENT: 1} cmdId: ‍[number]‍ 89 at uni_modules/ak-sbsrv/utssdk/protocol-handler.uts:111 +20:00:59.362 05-08 20:00:58.378 17863 17863 E UniDomManager: batch--start-----midd---5 +20:00:59.362 05-08 20:00:58.379 17863 17863 E UniDomManager: layoutUpdateRecursive--耗时:1 +20:00:59.362 05-08 20:00:58.379 17863 17863 E UniDomManager: batch----time=6 +20:00:59.374 05-08 20:00:58.386 17863 17863 E UniDomManager: flushPendingBatches--tiem=7 task size=5 +20:00:59.374 05-08 20:00:58.393 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"ak check entry::"},{"type":"number","subType":"number","value":"89"},{"className":"uni.UNI95B2570.ResponseCallbackEntry","type":"object","subType":"object","__$originalPosition":{"name":"ResponseCallbackEntry","file":"uni_modules/ak-sbsrv/utssdk/interface.uts","column":13,"line":293},"value":{"properties":[{"type":"function","name":"cb","parameter":["io.dcloud.uts.Uint8Array"],"returned":"kotlin.Boolean"},{"type":"boolean","name":"multi","value":"true"}],"methods":[]}},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/protocol-handler.uts:114"}]---END:CONSOLE--- +20:00:59.382 ak check entry:: ‍[number]‍ 89 ‍[⁠ResponseCallbackEntry⁠]‍ {cb: function (io.dcloud.uts.Uint8Array) : kotlin.Boolean { [native code] }, multi: true} at uni_modules/ak-sbsrv/utssdk/protocol-handler.uts:114 +20:00:59.382 05-08 20:00:58.395 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"className":"io.dcloud.uts.Uint8Array","type":"object","subType":"object","value":{"properties":[{"type":"number","subType":"number","name":"BYTES_PER_ELEMENT","value":"1"}],"methods":[]}},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/protocol-handler.uts:119"}]---END:CONSOLE--- +20:00:59.382 ‍[⁠io.dcloud.uts.Uint8Array⁠]‍ {BYTES_PER_ELEMENT: 1} at uni_modules/ak-sbsrv/utssdk/protocol-handler.uts:119 +20:00:59.382 [writeCharacteristic] deviceId: B0:03:12:00:09:B8 serviceId: bae80001-4f05-4503-8e65-3af1f7329d1f characteristicId: bae80010-4f05-4503-8e65-3af1f7329d1f data: ‍[⁠io.dcloud.uts.Uint8Array⁠]‍ {BYTES_PER_ELEMENT: 1} at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:298 +20:00:59.393 [writeCharacteristic] setValue ‍[kotlin.ByteArray]‍ [ 0, 89, 50, 0, 30, ⁠...⁠ ] at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:335 +20:00:59.401 [writeCharacteristic] writeCharacteristic result: [boolean] true at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:338 +20:00:59.401 writeCharacteristic ok at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:347 +20:00:59.401 05-08 20:00:58.405 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"[writeCharacteristic] deviceId:"},{"type":"string","value":"B0:03:12:00:09:B8"},{"type":"string","value":"serviceId:"},{"type":"string","value":"bae80001-4f05-4503-8e65-3af1f7329d1f"},{"type":"string","value":"characteristicId:"},{"type":"string","value":"bae80010-4f05-4503-8e65-3af1f7329d1f"},{"type":"string","value":"data:"},{"className":"io.dcloud.uts.Uint8Array","type":"object","subType":"object","value":{"properties":[{"type":"number","subType":"number","name":"BYTES_PER_ELEMENT","value":"1"}],"methods":[]}},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:298"}]---END:CONSOLE--- +20:00:59.401 05-08 20:00:58.406 17863 19385 E libc : MUNMTEST11 pthread_join thread t=491651396848 thread=0x7278b4f4f0 tid = 0 addr=0x7278a52000 size=1040384 +20:00:59.401 05-08 20:00:58.406 17863 19385 E libc : MUNMTEST11 __pthread_internal_free thread thread=0x7278b4f4f0 tid = 0 addr=0x7278a52000 size=1040384 join_state=2 +20:00:59.401 05-08 20:00:58.406 17863 19385 W bionic-munmap: addr = 0x7278a52000, size = 0x1040384 +20:00:59.405 05-08 20:00:58.406 17863 19385 E libc : pthread_create thread thread=0x7278b4f4f0 tid = 19532 addr=0x7278a52000 size=1040384 +20:00:59.405 05-08 20:00:58.408 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"[writeCharacteristic] setValue"},{"className":"kotlin.ByteArray","type":"object","subType":"array","value":{"properties":[{"type":"number","subType":"number","value":"0","name":0},{"type":"number","subType":"number","value":"89","name":1},{"type":"number","subType":"number","value":"50","name":2},{"type":"number","subType":"number","value":"0","name":3},{"type":"number","subType":"number","value":"30","name":4},{"type":"number","subType":"number","value":"50","name":5},{"type":"number","subType":"number","value":"1","name":6},{"type":"number","subType":"number","value":"1","name":7}]}},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:335"}]---END:CONSOLE--- +20:00:59.405 05-08 20:00:58.409 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"[writeCharacteristic] writeCharacteristic result:"},{"type":"boolean","value":"true"},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:338"}]---END:CONSOLE--- +20:00:59.405 05-08 20:00:58.411 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"writeCharacteristic ok"},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:347"}]---END:CONSOLE--- +20:00:59.405 05-08 20:00:58.412 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"[sendCommandWithResponse] 写入成功"},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/protocol-handler.uts:126"}]---END:CONSOLE--- +20:00:59.405 [sendCommandWithResponse] 写入成功 at uni_modules/ak-sbsrv/utssdk/protocol-handler.uts:126 +20:01:05.086 05-08 20:01:04.091 17863 19377 D BluetoothGatt: onClientConnectionState() - status=8 clientIf=7 device=B0:03:12:00:09:B8 +20:01:05.086 05-08 20:01:04.093 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"设备已断开: B0:03:12:00:09:B8"},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:126"}]---END:CONSOLE--- +20:01:05.090 设备已断开: B0:03:12:00:09:B8 at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:126 +20:01:05.090 05-08 20:01:04.094 17863 19473 I console : [LOG]---BEGIN:CONSOLE---[{"type":"string","value":"[AKBLE] handleConnectionStateChange:"},{"type":"string","value":"B0:03:12:00:09:B8"},{"type":"string","value":"newState:"},{"type":"number","subType":"number","value":"0"},{"type":"string","value":"error:"},{"type":"null","value":"null"},{"type":"string","value":"pendingConnects:"},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:196"}]---END:CONSOLE--- +20:01:05.090 [AKBLE] handleConnectionStateChange: B0:03:12:00:09:B8 newState: ‍[number]‍ 0 error: null pendingConnects: at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:196 +20:01:05.090 05-08 20:01:04.095 17863 19473 I console : [WARN]---BEGIN:CONSOLE---[{"type":"string","value":"[AKBLE] handleConnectionStateChange: 未找到 pendingConnects"},{"type":"string","value":"B0:03:12:00:09:B8"},{"type":"number","subType":"number","value":"0"},{"type":"string","value":" at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:218"}]---END:CONSOLE--- +20:01:05.094 [AKBLE] handleConnectionStateChange: 未找到 pendingConnects B0:03:12:00:09:B8 ‍[number]‍ 0 at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:218 +20:01:09.391 05-08 20:01:08.408 17863 19532 E libc : MUNMTEST pthread_exit thread tid = 19532 sigaddress=0x7276e70000 size=5000 +20:01:09.391 05-08 20:01:08.408 17863 19532 E libc : MUNMTEST __pthread_unmap_tls thread tid = 19532 allocation addr=0x7279b8a000 size=5000 diff --git a/unpackage/cache/.app-android/class/META-INF/main-1759235211288.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1759235211288.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1759235211288.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1759305093781.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1759305093781.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1759305093781.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1759307496330.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1759307496330.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1759307496330.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1759307777751.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1759307777751.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1759307777751.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760401355676.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760401355676.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760401355676.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760402135695.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760402135695.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760402135695.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760448632884.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760448632884.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760448632884.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760448726597.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760448726597.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760448726597.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760448776211.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760448776211.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760448776211.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760448968064.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760448968064.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760448968064.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760448995129.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760448995129.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760448995129.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760449213679.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760449213679.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760449213679.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760449280686.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760449280686.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760449280686.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760449579789.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760449579789.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760449579789.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760449928242.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760449928242.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760449928242.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760450007605.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760450007605.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760450007605.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760501243891.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760501243891.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760501243891.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760504394191.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760504394191.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760504394191.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760504426915.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760504426915.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760504426915.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760514260126.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760514260126.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760514260126.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760515807318.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760515807318.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760515807318.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760515830183.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760515830183.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760515830183.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760515845898.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760515845898.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760515845898.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760515942599.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760515942599.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760515942599.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760515961142.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760515961142.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760515961142.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760515968666.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760515968666.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760515968666.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760516219726.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760516219726.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760516219726.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760516337643.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760516337643.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760516337643.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760516407250.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760516407250.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760516407250.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760516539957.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760516539957.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760516539957.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760517170966.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760517170966.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760517170966.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760517766699.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760517766699.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760517766699.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760517792874.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760517792874.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760517792874.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760521382843.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760521382843.kotlin_module new file mode 100644 index 0000000..0c6ef6e Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760521382843.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/META-INF/main-1760522387166.kotlin_module b/unpackage/cache/.app-android/class/META-INF/main-1760522387166.kotlin_module new file mode 100644 index 0000000..1e9f2ca Binary files /dev/null and b/unpackage/cache/.app-android/class/META-INF/main-1760522387166.kotlin_module differ diff --git a/unpackage/cache/.app-android/class/ktClasss.ser b/unpackage/cache/.app-android/class/ktClasss.ser new file mode 100644 index 0000000..c12ece9 Binary files /dev/null and b/unpackage/cache/.app-android/class/ktClasss.ser differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl$Companion$WhenMappings.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl$Companion$WhenMappings.class new file mode 100644 index 0000000..e9e0339 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl$Companion$WhenMappings.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl$Companion.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl$Companion.class new file mode 100644 index 0000000..83e0989 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl$Companion.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl.class new file mode 100644 index 0000000..228a6df Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBleErrorImpl.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBluetoothErrorCode.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBluetoothErrorCode.class new file mode 100644 index 0000000..888be06 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/AkBluetoothErrorCode.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoBleInterfaces.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoBleInterfaces.class new file mode 100644 index 0000000..9a704d9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoBleInterfaces.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoBleInterfacesReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoBleInterfacesReactiveObject.class new file mode 100644 index 0000000..b6cd886 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoBleInterfacesReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoDiscoverAllResult.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoDiscoverAllResult.class new file mode 100644 index 0000000..20d4c40 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/AutoDiscoverAllResult.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristic.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristic.class new file mode 100644 index 0000000..eadf9e6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristic.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicProperties.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicProperties.class new file mode 100644 index 0000000..86b980f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicProperties.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicPropertiesReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicPropertiesReactiveObject.class new file mode 100644 index 0000000..8900f5e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicPropertiesReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicReactiveObject.class new file mode 100644 index 0000000..06e7073 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleCharacteristicReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleConnectOptionsExt.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleConnectOptionsExt.class new file mode 100644 index 0000000..f25c0fc Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleConnectOptionsExt.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleConnectOptionsExtReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleConnectOptionsExtReactiveObject.class new file mode 100644 index 0000000..b37814b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleConnectOptionsExtReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleDevice.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleDevice.class new file mode 100644 index 0000000..637d556 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleDevice.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleDeviceReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleDeviceReactiveObject.class new file mode 100644 index 0000000..61b86a7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleDeviceReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleError.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleError.class new file mode 100644 index 0000000..2403b8b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleError.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleEventPayload.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleEventPayload.class new file mode 100644 index 0000000..1687b91 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleEventPayload.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleOptions.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleOptions.class new file mode 100644 index 0000000..a46ab22 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleOptions.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleOptionsReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleOptionsReactiveObject.class new file mode 100644 index 0000000..c5b434c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleOptionsReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleService.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleService.class new file mode 100644 index 0000000..be5d7a7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleService.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BleServiceReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleServiceReactiveObject.class new file mode 100644 index 0000000..a928c5d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BleServiceReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService.class new file mode 100644 index 0000000..adc6c79 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$autoDiscoverAll$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$autoDiscoverAll$1.class new file mode 100644 index 0000000..0fdb27f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$autoDiscoverAll$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getAutoBleInterfaces$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getAutoBleInterfaces$1.class new file mode 100644 index 0000000..948eac9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getAutoBleInterfaces$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getCharacteristics$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getCharacteristics$1$1.class new file mode 100644 index 0000000..af0670a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getCharacteristics$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getCharacteristics$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getCharacteristics$1.class new file mode 100644 index 0000000..51acb99 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getCharacteristics$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getServices$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getServices$1$1.class new file mode 100644 index 0000000..d0a99ed Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getServices$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getServices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getServices$1.class new file mode 100644 index 0000000..7fedca2 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$getServices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$readCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$readCharacteristic$1.class new file mode 100644 index 0000000..29bd228 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$readCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$subscribeAllNotifications$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$subscribeAllNotifications$1.class new file mode 100644 index 0000000..53a3ebb Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$subscribeAllNotifications$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$subscribeCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$subscribeCharacteristic$1.class new file mode 100644 index 0000000..3c8784e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$subscribeCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$unsubscribeCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$unsubscribeCharacteristic$1.class new file mode 100644 index 0000000..adf3791 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$unsubscribeCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$writeCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$writeCharacteristic$1.class new file mode 100644 index 0000000..95f7e50 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1$writeCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1.class new file mode 100644 index 0000000..5aa2aa7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/BluetoothService1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ControlParserResult.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ControlParserResult.class new file mode 100644 index 0000000..7a6e757 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ControlParserResult.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceContext.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceContext.class new file mode 100644 index 0000000..32c4cd1 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceContext.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$Companion.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$Companion.class new file mode 100644 index 0000000..a6b2a96 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$Companion.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$rejectAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$rejectAdapter$1.class new file mode 100644 index 0000000..9941eaa Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$rejectAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$resolveAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$resolveAdapter$1.class new file mode 100644 index 0000000..290da8f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$resolveAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$timer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$timer$1.class new file mode 100644 index 0000000..e2af3f5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1$timer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1.class new file mode 100644 index 0000000..3d708e1 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1.class new file mode 100644 index 0000000..75e81e7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$connectDevice$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$disconnectDevice$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$disconnectDevice$1.class new file mode 100644 index 0000000..6e44b53 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$disconnectDevice$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$getConnectedDevices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$getConnectedDevices$1.class new file mode 100644 index 0000000..e9dbc3c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$getConnectedDevices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1$1$1.class new file mode 100644 index 0000000..0bf3e5f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1$1.class new file mode 100644 index 0000000..bdfcb45 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1.class new file mode 100644 index 0000000..a399deb Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$reconnectDevice$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$1.class new file mode 100644 index 0000000..e86a3b7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$2.class new file mode 100644 index 0000000..62b2025 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$MyScanCallback.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$MyScanCallback.class new file mode 100644 index 0000000..19d59e1 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager$startScan$MyScanCallback.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager.class new file mode 100644 index 0000000..9b64a0e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DeviceManager.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1$1$1.class new file mode 100644 index 0000000..921b9ea Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1$1.class new file mode 100644 index 0000000..c6b6292 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1.class new file mode 100644 index 0000000..023e9b8 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_requestMtu$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_sleep$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_sleep$1$1.class new file mode 100644 index 0000000..cd00f84 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_sleep$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_sleep$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_sleep$1.class new file mode 100644 index 0000000..47fde3d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_sleep$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$origReject$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$origReject$1.class new file mode 100644 index 0000000..118e477 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$origReject$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$origResolve$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$origResolve$1.class new file mode 100644 index 0000000..c7b4891 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$origResolve$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$timer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$timer$1.class new file mode 100644 index 0000000..973a21a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1$timer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1.class new file mode 100644 index 0000000..a79abb5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForControlResult$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$prnReject$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$prnReject$1.class new file mode 100644 index 0000000..92b9e17 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$prnReject$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$prnResolve$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$prnResolve$1.class new file mode 100644 index 0000000..6acb6ad Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$prnResolve$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$timer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$timer$1.class new file mode 100644 index 0000000..fcf90ed Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1$timer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1.class new file mode 100644 index 0000000..e9aca48 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$_waitForPrn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$1.class new file mode 100644 index 0000000..488b634 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$2.class new file mode 100644 index 0000000..fb8d266 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$3.class new file mode 100644 index 0000000..313d5a4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$4.class new file mode 100644 index 0000000..2281a9d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$5$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$5$1.class new file mode 100644 index 0000000..959f743 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$5$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$5.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$5.class new file mode 100644 index 0000000..b9c860b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$5.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$6$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$6$1.class new file mode 100644 index 0000000..5c4a04a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$6$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$6.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$6.class new file mode 100644 index 0000000..ddd726b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$6.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$7.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$7.class new file mode 100644 index 0000000..6b06450 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$7.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$byteToHex$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$byteToHex$1.class new file mode 100644 index 0000000..2f41db3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$byteToHex$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$controlHandler$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$controlHandler$1.class new file mode 100644 index 0000000..8ca6303 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1$controlHandler$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1.class new file mode 100644 index 0000000..0c3dba6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager$startDfu$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager.class new file mode 100644 index 0000000..e916e19 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuManager.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuOptions.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuOptions.class new file mode 100644 index 0000000..45b20ad Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuOptions.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuSession.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuSession.class new file mode 100644 index 0000000..04d4812 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/DfuSession.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GattCallback.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GattCallback.class new file mode 100644 index 0000000..a495996 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GattCallback.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$1.class new file mode 100644 index 0000000..5f5a903 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$2.class new file mode 100644 index 0000000..d028a23 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$3.class new file mode 100644 index 0000000..242a586 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$4$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$4$1.class new file mode 100644 index 0000000..51e7b05 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$4$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$4.class new file mode 100644 index 0000000..c8adb6c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$5.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$5.class new file mode 100644 index 0000000..0ef430c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$5.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$Companion$styles$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$Companion$styles$2.class new file mode 100644 index 0000000..203f804 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$Companion$styles$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$Companion.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$Companion.class new file mode 100644 index 0000000..ee0184b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp$Companion.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp.class new file mode 100644 index 0000000..20e462b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenApp.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$1.class new file mode 100644 index 0000000..62655da Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$1.class new file mode 100644 index 0000000..879689b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$2.class new file mode 100644 index 0000000..c3a9bac Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$3.class new file mode 100644 index 0000000..4579890 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$4.class new file mode 100644 index 0000000..c32ef76 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$5.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$5.class new file mode 100644 index 0000000..66af302 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$5.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$6.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$6.class new file mode 100644 index 0000000..576a9e1 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$6.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$7.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$7.class new file mode 100644 index 0000000..eef3462 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2$7.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2.class new file mode 100644 index 0000000..145027b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$3.class new file mode 100644 index 0000000..153328a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$4$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$4$1.class new file mode 100644 index 0000000..2f6208d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$4$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$4.class new file mode 100644 index 0000000..e28fdf0 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$1.class new file mode 100644 index 0000000..e2817a4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$2.class new file mode 100644 index 0000000..7d2629d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$3.class new file mode 100644 index 0000000..c58c307 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5.class new file mode 100644 index 0000000..64079e0 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$$render$5.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$1.class new file mode 100644 index 0000000..5f54400 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$2$exists$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$2$exists$1.class new file mode 100644 index 0000000..15d486a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$2$exists$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$2.class new file mode 100644 index 0000000..b79d55c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$3.class new file mode 100644 index 0000000..a4a3f48 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$4$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$4$1.class new file mode 100644 index 0000000..561dea2 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$4$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$4.class new file mode 100644 index 0000000..30638e7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1.class new file mode 100644 index 0000000..d348f07 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$Companion$styles$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$Companion$styles$2.class new file mode 100644 index 0000000..a087554 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$Companion$styles$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$Companion.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$Companion.class new file mode 100644 index 0000000..592bd69 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$Companion.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_base64ToUint8Array$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_base64ToUint8Array$1.class new file mode 100644 index 0000000..a038b80 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_base64ToUint8Array$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_fmt$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_fmt$1.class new file mode 100644 index 0000000..03d60c4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_fmt$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_readFileAsUint8Array$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_readFileAsUint8Array$1.class new file mode 100644 index 0000000..73fea11 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$_readFileAsUint8Array$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$autoConnect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$autoConnect$1.class new file mode 100644 index 0000000..f2de137 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$autoConnect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$autoDiscoverInterfaces$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$autoDiscoverInterfaces$1.class new file mode 100644 index 0000000..89d6cde Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$autoDiscoverInterfaces$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$charProps$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$charProps$1.class new file mode 100644 index 0000000..e9fa3fb Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$charProps$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$closeCharacteristics$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$closeCharacteristics$1.class new file mode 100644 index 0000000..26dfa81 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$closeCharacteristics$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$closeServices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$closeServices$1.class new file mode 100644 index 0000000..4e7e870 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$closeServices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$connect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$connect$1.class new file mode 100644 index 0000000..2c8068c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$connect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$1.class new file mode 100644 index 0000000..d5c7444 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$2.class new file mode 100644 index 0000000..fa44762 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$3.class new file mode 100644 index 0000000..9fb2999 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$4.class new file mode 100644 index 0000000..08eca7b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$5.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$5.class new file mode 100644 index 0000000..98dd915 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$5.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$6.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$6.class new file mode 100644 index 0000000..6f90971 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$6.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$7.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$7.class new file mode 100644 index 0000000..ab8587b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$data$7.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$disconnect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$disconnect$1.class new file mode 100644 index 0000000..d976fbd Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$disconnect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1$1.class new file mode 100644 index 0000000..f584fbb Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1$2.class new file mode 100644 index 0000000..97afcff Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1.class new file mode 100644 index 0000000..0b2d790 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen__readFileAsUint8Array_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$1.class new file mode 100644 index 0000000..ec5051c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$2.class new file mode 100644 index 0000000..17031e2 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$3.class new file mode 100644 index 0000000..7e417c5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$1$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$toConnect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$toConnect$1.class new file mode 100644 index 0000000..743c5a8 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoConnect_fn$toConnect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoDiscoverInterfaces_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoDiscoverInterfaces_fn$1.class new file mode 100644 index 0000000..5e58562 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoDiscoverInterfaces_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoDiscoverInterfaces_fn$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoDiscoverInterfaces_fn$2.class new file mode 100644 index 0000000..81980c2 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_autoDiscoverInterfaces_fn$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$1.class new file mode 100644 index 0000000..532f9d5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$2.class new file mode 100644 index 0000000..aa4519e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$3.class new file mode 100644 index 0000000..0f8d8c3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_connect_fn$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$1$1.class new file mode 100644 index 0000000..159883a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$1.class new file mode 100644 index 0000000..afc1caa Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$2.class new file mode 100644 index 0000000..e0db037 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$3.class new file mode 100644 index 0000000..f99a03e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_disconnect_fn$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$found$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$found$1.class new file mode 100644 index 0000000..272aa02 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$found$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$hex$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$hex$1.class new file mode 100644 index 0000000..44f49e6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$hex$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$stdServices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$stdServices$1.class new file mode 100644 index 0000000..40bfa86 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1$stdServices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1.class new file mode 100644 index 0000000..b064a64 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getDeviceInfo_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getOrInitProtocolHandler_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getOrInitProtocolHandler_fn$1.class new file mode 100644 index 0000000..07d4c6c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_getOrInitProtocolHandler_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_readCharacteristic_fn$1$hex$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_readCharacteristic_fn$1$hex$1.class new file mode 100644 index 0000000..ad823fa Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_readCharacteristic_fn$1$hex$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_readCharacteristic_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_readCharacteristic_fn$1.class new file mode 100644 index 0000000..b353990 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_readCharacteristic_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$1.class new file mode 100644 index 0000000..d63520a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$2.class new file mode 100644 index 0000000..7952cff Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$normalize$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$normalize$1.class new file mode 100644 index 0000000..30a177e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$normalize$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$optionalServices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$optionalServices$1.class new file mode 100644 index 0000000..53947bc Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$optionalServices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$optionalServices$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$optionalServices$2.class new file mode 100644 index 0000000..15ba2be Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_scanDevices_fn$optionalServices$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$1.class new file mode 100644 index 0000000..35b0910 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$2.class new file mode 100644 index 0000000..15ce258 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$notifyChar$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$notifyChar$1.class new file mode 100644 index 0000000..bc646e9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$notifyChar$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$writeChar$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$writeChar$1.class new file mode 100644 index 0000000..b08980f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1$writeChar$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1.class new file mode 100644 index 0000000..9fc5b25 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$2.class new file mode 100644 index 0000000..86292b5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showCharacteristics_fn$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$1.class new file mode 100644 index 0000000..edd314d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$2.class new file mode 100644 index 0000000..270d997 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$3.class new file mode 100644 index 0000000..804f532 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_showServices_fn$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1$1$hex$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1$1$hex$1.class new file mode 100644 index 0000000..f691d29 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1$1$hex$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1$1.class new file mode 100644 index 0000000..edab443 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1.class new file mode 100644 index 0000000..7e00fc4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_toggleNotify_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_writeCharacteristic_fn$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_writeCharacteristic_fn$1.class new file mode 100644 index 0000000..234c85c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$gen_writeCharacteristic_fn$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$getDeviceInfo$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$getDeviceInfo$1.class new file mode 100644 index 0000000..c5ebe78 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$getDeviceInfo$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$getOrInitProtocolHandler$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$getOrInitProtocolHandler$1.class new file mode 100644 index 0000000..00e2a2d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$getOrInitProtocolHandler$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$isNotifying$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$isNotifying$1.class new file mode 100644 index 0000000..f60b2c4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$isNotifying$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$log$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$log$1.class new file mode 100644 index 0000000..6f68dd6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$log$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$onPresetChange$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$onPresetChange$1.class new file mode 100644 index 0000000..1f0ff64 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$onPresetChange$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$readCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$readCharacteristic$1.class new file mode 100644 index 0000000..7e62d91 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$readCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$scanDevices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$scanDevices$1.class new file mode 100644 index 0000000..a62f18c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$scanDevices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$showCharacteristics$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$showCharacteristics$1.class new file mode 100644 index 0000000..3931c26 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$showCharacteristics$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$showServices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$showServices$1.class new file mode 100644 index 0000000..cc9d8a6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$showServices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$1.class new file mode 100644 index 0000000..802d04c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$2.class new file mode 100644 index 0000000..b7e2e4c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1$1.class new file mode 100644 index 0000000..835aea3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1$2.class new file mode 100644 index 0000000..da42a26 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1.class new file mode 100644 index 0000000..ade02bd Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1$res$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1.class new file mode 100644 index 0000000..478e437 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$startDfuFlow$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$toggleNotify$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$toggleNotify$1.class new file mode 100644 index 0000000..81b78a6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$toggleNotify$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$writeCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$writeCharacteristic$1.class new file mode 100644 index 0000000..c7d4675 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest$writeCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest.class new file mode 100644 index 0000000..c2f50e4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenPagesAkbletest.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/GenUniApp.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenUniApp.class new file mode 100644 index 0000000..012ec45 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/GenUniApp.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenAppClass$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenAppClass$1.class new file mode 100644 index 0000000..ab6cf8c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenAppClass$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenAppClass$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenAppClass$2.class new file mode 100644 index 0000000..58ed046 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenAppClass$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenPagesAkbletestClass$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenPagesAkbletestClass$1.class new file mode 100644 index 0000000..a8e2ca3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenPagesAkbletestClass$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenPagesAkbletestClass$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenPagesAkbletestClass$2.class new file mode 100644 index 0000000..a4f5421 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$GenPagesAkbletestClass$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$connectDevice$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$connectDevice$1$1.class new file mode 100644 index 0000000..7f4d85e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$connectDevice$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$connectDevice$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$connectDevice$1.class new file mode 100644 index 0000000..2c422e1 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$connectDevice$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$defineAppConfig$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$defineAppConfig$1.class new file mode 100644 index 0000000..af896b4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$defineAppConfig$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$disconnectDevice$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$disconnectDevice$1$1.class new file mode 100644 index 0000000..913e6c6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$disconnectDevice$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$disconnectDevice$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$disconnectDevice$1.class new file mode 100644 index 0000000..9132416 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$disconnectDevice$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$1.class new file mode 100644 index 0000000..2c91c12 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$next$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$next$1$1.class new file mode 100644 index 0000000..a38305e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$next$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$queued$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$queued$1.class new file mode 100644 index 0000000..3bce5a4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$queued$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$queued$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$queued$2.class new file mode 100644 index 0000000..4de7a74 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$enqueueDeviceWrite$queued$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$getConnectedDevices$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$getConnectedDevices$1$1.class new file mode 100644 index 0000000..69c72a3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$getConnectedDevices$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$getConnectedDevices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$getConnectedDevices$1.class new file mode 100644 index 0000000..429a233 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$getConnectedDevices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocket$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocket$1$1.class new file mode 100644 index 0000000..320756f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocket$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocket$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocket$1.class new file mode 100644 index 0000000..e6838b7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocket$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$1.class new file mode 100644 index 0000000..7c7ede7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$2.class new file mode 100644 index 0000000..c530408 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$3$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$3$1.class new file mode 100644 index 0000000..b053ca6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$3$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$3.class new file mode 100644 index 0000000..5648de3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$4.class new file mode 100644 index 0000000..2023f2b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$initRuntimeSocketService$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$off$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$off$1.class new file mode 100644 index 0000000..feb3357 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$off$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$on$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$on$1.class new file mode 100644 index 0000000..9fdb282 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$on$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock1$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock1$1$1.class new file mode 100644 index 0000000..769d79d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock1$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$1.class new file mode 100644 index 0000000..702e29d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$2.class new file mode 100644 index 0000000..fcee30c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$3.class new file mode 100644 index 0000000..3acfe6d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$4.class new file mode 100644 index 0000000..2ee3d5a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock3$1$_raw$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$1.class new file mode 100644 index 0000000..10844fa Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$2.class new file mode 100644 index 0000000..4628846 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$3.class new file mode 100644 index 0000000..acec8a2 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$4.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$4.class new file mode 100644 index 0000000..23cd19d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$runBlock4$1$_raw$4.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1$scanOptions$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1$scanOptions$1.class new file mode 100644 index 0000000..c68f1b3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1$scanOptions$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1$scanOptions$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1$scanOptions$2.class new file mode 100644 index 0000000..b2d7bd9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1$scanOptions$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1.class new file mode 100644 index 0000000..a0647ce Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1.class new file mode 100644 index 0000000..cf2acce Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$scanDevices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$1.class new file mode 100644 index 0000000..e8ab1ee Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$2.class new file mode 100644 index 0000000..db71627 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$3.class new file mode 100644 index 0000000..6ee4ced Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$socket$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$socket$1.class new file mode 100644 index 0000000..b76f57c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$socket$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$timer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$timer$1.class new file mode 100644 index 0000000..3753ac5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1$timer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1.class new file mode 100644 index 0000000..8d4321c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt$tryConnectSocket$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt.class new file mode 100644 index 0000000..6ba3fc5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/IndexKt.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/MultiProtocolDevice.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/MultiProtocolDevice.class new file mode 100644 index 0000000..f11b113 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/MultiProtocolDevice.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/MultiProtocolDeviceReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/MultiProtocolDeviceReactiveObject.class new file mode 100644 index 0000000..7673667 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/MultiProtocolDeviceReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingCallback.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingCallback.class new file mode 100644 index 0000000..a3cc562 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingCallback.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingCallbackImpl.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingCallbackImpl.class new file mode 100644 index 0000000..712cd51 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingCallbackImpl.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingConnect.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingConnect.class new file mode 100644 index 0000000..bbbf74c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingConnect.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingConnectImpl.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingConnectImpl.class new file mode 100644 index 0000000..46c0cc5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PendingConnectImpl.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$WhenMappings.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$WhenMappings.class new file mode 100644 index 0000000..9760420 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$WhenMappings.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$getDeniedPermissions$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$getDeniedPermissions$1.class new file mode 100644 index 0000000..312ccdc Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$getDeniedPermissions$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$getGrantedPermissions$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$getGrantedPermissions$1.class new file mode 100644 index 0000000..6fad1ff Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$getGrantedPermissions$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestBluetoothPermissions$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestBluetoothPermissions$1$1.class new file mode 100644 index 0000000..8625027 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestBluetoothPermissions$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestBluetoothPermissions$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestBluetoothPermissions$1.class new file mode 100644 index 0000000..83da9e4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestBluetoothPermissions$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestMultiplePermissions$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestMultiplePermissions$1.class new file mode 100644 index 0000000..4c88fe0 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestMultiplePermissions$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestPermission$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestPermission$1.class new file mode 100644 index 0000000..3263b06 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestPermission$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestPermission$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestPermission$2.class new file mode 100644 index 0000000..73356d5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$requestPermission$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$showPermissionRationale$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$showPermissionRationale$1.class new file mode 100644 index 0000000..f954b1c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion$showPermissionRationale$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion.class new file mode 100644 index 0000000..e20d80d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager$Companion.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager.class new file mode 100644 index 0000000..eabb764 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionManager.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionResult.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionResult.class new file mode 100644 index 0000000..17e6d1f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionResult.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionType.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionType.class new file mode 100644 index 0000000..a1f75ee Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/PermissionType.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$autoConnect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$autoConnect$1.class new file mode 100644 index 0000000..e4be9f9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$autoConnect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$connect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$connect$1.class new file mode 100644 index 0000000..4de69da Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$connect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$disconnect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$disconnect$1.class new file mode 100644 index 0000000..5717230 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$disconnect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$initialize$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$initialize$1.class new file mode 100644 index 0000000..91d6ac1 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$initialize$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$scanDevices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$scanDevices$1.class new file mode 100644 index 0000000..f597ea7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$scanDevices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$sendData$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$sendData$1.class new file mode 100644 index 0000000..d2962f7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$sendData$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testBatteryLevel$1$batChar$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testBatteryLevel$1$batChar$1.class new file mode 100644 index 0000000..f282d11 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testBatteryLevel$1$batChar$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testBatteryLevel$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testBatteryLevel$1.class new file mode 100644 index 0000000..617cacd Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testBatteryLevel$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testVersionInfo$1$target$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testVersionInfo$1$target$1.class new file mode 100644 index 0000000..26974ae Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testVersionInfo$1$target$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testVersionInfo$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testVersionInfo$1.class new file mode 100644 index 0000000..bb786b0 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler$testVersionInfo$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler.class new file mode 100644 index 0000000..c08693d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandler.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$autoConnect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$autoConnect$1.class new file mode 100644 index 0000000..bd925b6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$autoConnect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$connect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$connect$1.class new file mode 100644 index 0000000..c422e01 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$connect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$disconnect$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$disconnect$1.class new file mode 100644 index 0000000..5104bb3 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$disconnect$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$scanDevices$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$scanDevices$1.class new file mode 100644 index 0000000..66cd5ec Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$scanDevices$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$sendData$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$sendData$1.class new file mode 100644 index 0000000..a96fcf2 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper$sendData$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper.class new file mode 100644 index 0000000..d50637e Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ProtocolHandlerWrapper.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/RawProtocolHandler.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/RawProtocolHandler.class new file mode 100644 index 0000000..f322c5d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/RawProtocolHandler.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ScanDevicesOptions.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ScanDevicesOptions.class new file mode 100644 index 0000000..7da7212 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ScanDevicesOptions.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ScanDevicesOptionsReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ScanDevicesOptionsReactiveObject.class new file mode 100644 index 0000000..f59551c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ScanDevicesOptionsReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/SendDataPayload.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/SendDataPayload.class new file mode 100644 index 0000000..06e67e9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/SendDataPayload.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/SendDataPayloadReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/SendDataPayloadReactiveObject.class new file mode 100644 index 0000000..6a148d5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/SendDataPayloadReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$Companion.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$Companion.class new file mode 100644 index 0000000..25127cb Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$Companion.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1$1$1.class new file mode 100644 index 0000000..f5d4561 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1$1.class new file mode 100644 index 0000000..ec6879d Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1.class new file mode 100644 index 0000000..b3f39f9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$autoDiscoverAll$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getCharacteristics$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getCharacteristics$1.class new file mode 100644 index 0000000..7c8403f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getCharacteristics$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1$notifyChar$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1$notifyChar$1.class new file mode 100644 index 0000000..43b358b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1$notifyChar$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1$writeChar$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1$writeChar$1.class new file mode 100644 index 0000000..3db400f Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1$writeChar$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1.class new file mode 100644 index 0000000..12fd6c4 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$2$cb$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$2$cb$1.class new file mode 100644 index 0000000..cbd7a22 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$2$cb$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$2.class new file mode 100644 index 0000000..300f85a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$getServices$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$rejectAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$rejectAdapter$1.class new file mode 100644 index 0000000..c57e098 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$rejectAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$resolveAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$resolveAdapter$1.class new file mode 100644 index 0000000..ef4bdd8 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$resolveAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$timer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$timer$1.class new file mode 100644 index 0000000..d0dc8c7 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1$timer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1.class new file mode 100644 index 0000000..cd974c6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1.class new file mode 100644 index 0000000..ea7fab9 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$readCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$subscribeAllNotifications$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$subscribeAllNotifications$1.class new file mode 100644 index 0000000..2dac892 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$subscribeAllNotifications$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$subscribeCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$subscribeCharacteristic$1.class new file mode 100644 index 0000000..d89f3cf Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$subscribeCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$unsubscribeCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$unsubscribeCharacteristic$1.class new file mode 100644 index 0000000..2156a92 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$unsubscribeCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$1.class new file mode 100644 index 0000000..a02b750 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$2.class new file mode 100644 index 0000000..581f192 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$giveupTimer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$giveupTimer$1.class new file mode 100644 index 0000000..8feb333 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$attemptWrite$giveupTimer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$rejectAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$rejectAdapter$1.class new file mode 100644 index 0000000..77b7f0c Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$rejectAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$resolveAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$resolveAdapter$1.class new file mode 100644 index 0000000..edab5fe Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$resolveAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$timer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$timer$1.class new file mode 100644 index 0000000..9afd0a5 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1$timer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1.class new file mode 100644 index 0000000..e2d8aa1 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$1.class new file mode 100644 index 0000000..cb7510b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$2.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$2.class new file mode 100644 index 0000000..922d67a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$2.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$3.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$3.class new file mode 100644 index 0000000..58c23e8 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$3.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$giveupTimer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$giveupTimer$1.class new file mode 100644 index 0000000..34cc23a Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$attemptWrite$giveupTimer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$rejectAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$rejectAdapter$1.class new file mode 100644 index 0000000..7c3bdf0 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$rejectAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$resolveAdapter$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$resolveAdapter$1.class new file mode 100644 index 0000000..480e210 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$resolveAdapter$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$timer$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$timer$1.class new file mode 100644 index 0000000..0adf650 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1$timer$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1.class new file mode 100644 index 0000000..6af2b08 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1.class new file mode 100644 index 0000000..0d99ff8 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1$executeWrite$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1.class new file mode 100644 index 0000000..490cbf0 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager$writeCharacteristic$1.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager.class new file mode 100644 index 0000000..708161b Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ServiceManager.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ShowingCharacteristicsFor.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ShowingCharacteristicsFor.class new file mode 100644 index 0000000..99ba924 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ShowingCharacteristicsFor.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/ShowingCharacteristicsForReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/ShowingCharacteristicsForReactiveObject.class new file mode 100644 index 0000000..2fcdc16 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/ShowingCharacteristicsForReactiveObject.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/UniAppConfig.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/UniAppConfig.class new file mode 100644 index 0000000..3cdfb64 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/UniAppConfig.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/WriteCharacteristicOptions.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/WriteCharacteristicOptions.class new file mode 100644 index 0000000..e9e26a6 Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/WriteCharacteristicOptions.class differ diff --git a/unpackage/cache/.app-android/class/uni/UNI95B2570/WriteCharacteristicOptionsReactiveObject.class b/unpackage/cache/.app-android/class/uni/UNI95B2570/WriteCharacteristicOptionsReactiveObject.class new file mode 100644 index 0000000..ecbc1ff Binary files /dev/null and b/unpackage/cache/.app-android/class/uni/UNI95B2570/WriteCharacteristicOptionsReactiveObject.class differ diff --git a/unpackage/cache/.app-android/dex/index/classes.dex b/unpackage/cache/.app-android/dex/index/classes.dex new file mode 100644 index 0000000..2469776 Binary files /dev/null and b/unpackage/cache/.app-android/dex/index/classes.dex differ diff --git a/unpackage/cache/.app-android/dex/pages/akbletest/classes.dex b/unpackage/cache/.app-android/dex/pages/akbletest/classes.dex new file mode 100644 index 0000000..0c2da51 Binary files /dev/null and b/unpackage/cache/.app-android/dex/pages/akbletest/classes.dex differ diff --git a/unpackage/cache/.app-android/sourcemap/index.kt.map b/unpackage/cache/.app-android/sourcemap/index.kt.map new file mode 100644 index 0000000..30db756 --- /dev/null +++ b/unpackage/cache/.app-android/sourcemap/index.kt.map @@ -0,0 +1 @@ +{"version":3,"sources":["uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts","uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts","F:/HBuilderX/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/socket.ts","App.uvue","ak/PermissionManager.uts","F:/HBuilderX/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/index.ts","uni_modules/ak-sbsrv/utssdk/interface.uts","uni_modules/ak-sbsrv/utssdk/protocol_handler.uts","uni_modules/ak-sbsrv/utssdk/unierror.uts","uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts","uni_modules/ak-sbsrv/utssdk/app-android/index.uts","uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts","pages/akbletest.uvue","main.uts","uni_modules/uni-getbatteryinfo/utssdk/interface.uts"],"sourcesContent":["import type { BleDevice, BleOptions, BleConnectionState, BleConnectionStateChangeCallback } from '../interface.uts'\r\nimport type { BleConnectOptionsExt } from '../interface.uts'\r\nimport type { ScanDevicesOptions } from '../interface.uts';\r\nimport Context from \"android.content.Context\";\r\nimport BluetoothAdapter from \"android.bluetooth.BluetoothAdapter\";\r\nimport BluetoothManager from \"android.bluetooth.BluetoothManager\";\r\nimport BluetoothDevice from \"android.bluetooth.BluetoothDevice\";\r\nimport BluetoothGatt from \"android.bluetooth.BluetoothGatt\";\r\nimport BluetoothGattCallback from \"android.bluetooth.BluetoothGattCallback\";\r\nimport ScanCallback from \"android.bluetooth.le.ScanCallback\";\r\nimport ScanResult from \"android.bluetooth.le.ScanResult\";\r\nimport ScanSettings from \"android.bluetooth.le.ScanSettings\";\r\nimport Handler from \"android.os.Handler\";\r\nimport Looper from \"android.os.Looper\";\r\nimport ContextCompat from \"androidx.core.content.ContextCompat\";\r\nimport PackageManager from \"android.content.pm.PackageManager\";\r\n// 定义 PendingConnect 类型和实现类\r\ninterface PendingConnect {\r\n resolve: () => void;\r\n reject: (err?: any) => void; // Changed to make err optional\r\n timer?: number;\r\n}\r\n\r\nclass PendingConnectImpl implements PendingConnect {\r\n resolve: () => void;\r\n reject: (err?: any) => void; // Changed to make err optional\r\n timer?: number;\r\n \r\n constructor(resolve: () => void, reject: (err?: any) => void, timer?: number) {\r\n this.resolve = resolve;\r\n this.reject = reject;\r\n this.timer = timer;\r\n }\r\n}\r\n// 引入全局回调管理\r\nimport { gattCallback } from './service_manager.uts'\r\nconst pendingConnects = new Map();\r\n\r\nconst STATE_DISCONNECTED = 0;\r\nconst STATE_CONNECTING = 1;\r\nconst STATE_CONNECTED = 2;\r\nconst STATE_DISCONNECTING = 3;\r\n\r\nexport class DeviceManager {\r\n private static instance: DeviceManager | null = null;\r\n private devices = new Map();\r\n private connectionStates = new Map();\r\n private connectionStateChangeListeners: BleConnectionStateChangeCallback[] = []\r\n private gattMap = new Map();\r\n private scanCallback: ScanCallback | null = null\r\n private isScanning: boolean = false\r\n private constructor() {}\r\n static getInstance(): DeviceManager {\r\n if (DeviceManager.instance == null) {\r\n DeviceManager.instance = new DeviceManager();\r\n }\r\n return DeviceManager.instance!;\r\n }\r\n startScan(options: ScanDevicesOptions): void {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:60','ak startscan now')\r\n const adapter = this.getBluetoothAdapter();\r\n if (adapter == null) {\r\n throw new Error('未找到蓝牙适配器');\r\n }\r\n if (!adapter.isEnabled) {\r\n // 尝试请求用户开启蓝牙\r\n try {\r\n adapter.enable(); // 直接调用,无需可选链和括号\r\n } catch (e) {\r\n // 某些设备可能不支持 enable\r\n }\r\n setTimeout(() => {\r\n if (!adapter.isEnabled) {\r\n throw new Error('蓝牙未开启');\r\n }\r\n }, 1500);\r\n throw new Error('正在开启蓝牙,请重试');\r\n }\r\n const foundDevices = this.devices; // 直接用全局 devices\r\n \r\n class MyScanCallback extends ScanCallback {\r\n private foundDevices: Map;\r\n private onDeviceFound: (device: BleDevice) => void;\r\n constructor(foundDevices: Map, onDeviceFound: (device: BleDevice) => void) {\r\n super();\r\n this.foundDevices = foundDevices;\r\n this.onDeviceFound = onDeviceFound;\r\n }\r\n override onScanResult(callbackType: Int, result: ScanResult): void {\r\n const device = result.getDevice();\r\n if (device != null) {\r\n const deviceId = device.getAddress();\r\n let bleDevice = foundDevices.get(deviceId);\r\n if (bleDevice == null) {\r\n bleDevice = {\r\n deviceId,\r\n name: device.getName() ?? 'Unknown',\r\n rssi: result.getRssi(),\r\n lastSeen: Date.now()\r\n };\r\n foundDevices.set(deviceId, bleDevice);\r\n this.onDeviceFound(bleDevice);\r\n } else {\r\n // 更新属性(已确保 bleDevice 非空)\r\n bleDevice.rssi = result.getRssi();\r\n bleDevice.name = device.getName() ?? bleDevice.name;\r\n bleDevice.lastSeen = Date.now();\r\n }\r\n }\r\n }\r\n \r\n \r\n override onScanFailed(errorCode: Int): void {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:114','ak scan fail')\r\n }\r\n }\r\n this.scanCallback = new MyScanCallback(foundDevices, options.onDeviceFound ?? (() => {}));\r\n const scanner = adapter.getBluetoothLeScanner();\r\n if (scanner == null) {\r\n throw new Error('无法获取扫描器');\r\n }\r\n const scanSettings = new ScanSettings.Builder()\r\n .setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY)\r\n .build();\r\n scanner.startScan(null, scanSettings, this.scanCallback);\r\n this.isScanning = true;\r\n // 默认10秒后停止扫描\r\n new Handler(Looper.getMainLooper()).postDelayed(() => {\r\n if (this.isScanning && this.scanCallback != null) {\r\n scanner.stopScan(this.scanCallback);\r\n this.isScanning = false;\r\n // this.devices = foundDevices;\r\n if (options.onScanFinished != null) options.onScanFinished?.invoke();\r\n }\r\n }, 40000);\r\n }\r\n\r\n async connectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:139','[AKBLE] connectDevice called, deviceId:', deviceId, 'options:', options, 'connectionStates:')\r\n const adapter = this.getBluetoothAdapter();\r\n if (adapter == null) {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:142','[AKBLE] connectDevice failed: 蓝牙适配器不可用')\r\n throw new Error('蓝牙适配器不可用');\r\n }\r\n const device = adapter.getRemoteDevice(deviceId);\r\n if (device == null) {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:147','[AKBLE] connectDevice failed: 未找到设备', deviceId)\r\n throw new Error('未找到设备');\r\n }\r\n this.connectionStates.set(deviceId, STATE_CONNECTING);\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:151','[AKBLE] connectDevice set STATE_CONNECTING, deviceId:', deviceId, 'connectionStates:')\r\n this.emitConnectionStateChange(deviceId, STATE_CONNECTING);\r\n const activity = UTSAndroid.getUniActivity();\r\n const timeout = options?.timeout ?? 15000;\r\n const key = `${deviceId}|connect`;\r\n return new Promise((resolve, reject) => {\r\n const timer = setTimeout(() => {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:158','[AKBLE] connectDevice 超时:', deviceId)\r\n pendingConnects.delete(key);\r\n this.connectionStates.set(deviceId, STATE_DISCONNECTED);\r\n this.gattMap.set(deviceId, null);\r\n this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED);\r\n reject(new Error('连接超时'));\r\n }, timeout);\r\n \r\n // 创建一个适配器函数来匹配类型签名\r\n const resolveAdapter = () => { \r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:168','[AKBLE] connectDevice resolveAdapter:', deviceId)\r\n resolve(); \r\n };\r\n const rejectAdapter = (err?: any) => { \r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:172','[AKBLE] connectDevice rejectAdapter:', deviceId, err)\r\n reject(err); \r\n };\r\n \r\n pendingConnects.set(key, new PendingConnectImpl(resolveAdapter, rejectAdapter, timer));\r\n try {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:178','[AKBLE] connectGatt 调用前:', deviceId)\r\n const gatt = device.connectGatt(activity, false, gattCallback);\r\n this.gattMap.set(deviceId, gatt);\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:181','[AKBLE] connectGatt 调用后:', deviceId, gatt)\r\n } catch (e) {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:183','[AKBLE] connectGatt 异常:', deviceId, e)\r\n clearTimeout(timer);\r\n pendingConnects.delete(key);\r\n this.connectionStates.set(deviceId, STATE_DISCONNECTED);\r\n this.gattMap.set(deviceId, null);\r\n this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED);\r\n reject(e);\r\n }\r\n });\r\n }\r\n\r\n // 统一分发连接回调(应在 gattCallback.onConnectionStateChange 内调用)\r\n static handleConnectionStateChange(deviceId: string, newState: number, error?: any) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:196','[AKBLE] handleConnectionStateChange:', deviceId, 'newState:', newState, 'error:', error, 'pendingConnects:')\r\n const key = `${deviceId}|connect`;\r\n const cb = pendingConnects.get(key);\r\n if (cb != null) {\r\n // 修复 timer 的空安全问题,使用临时变量\r\n const timerValue = cb.timer;\r\n if (timerValue != null) {\r\n clearTimeout(timerValue);\r\n }\r\n \r\n // 修复 error 处理\r\n if (newState === STATE_CONNECTED) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:208','[AKBLE] handleConnectionStateChange: 连接成功', deviceId)\r\n cb.resolve();\r\n } else {\r\n // 正确处理可空值\r\n const errorToUse = error != null ? error : new Error('连接断开');\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:213','[AKBLE] handleConnectionStateChange: 连接失败', deviceId, errorToUse)\r\n cb.reject(errorToUse);\r\n }\r\n pendingConnects.delete(key);\r\n } else {\r\n __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:218','[AKBLE] handleConnectionStateChange: 未找到 pendingConnects', deviceId, newState)\r\n }\r\n }\r\n\r\n async disconnectDevice(deviceId: string, isActive: boolean = true): Promise {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:223','[AKBLE] disconnectDevice called, deviceId:', deviceId, 'isActive:', isActive)\r\n let gatt = this.gattMap.get(deviceId);\r\n if (gatt != null) {\r\n gatt.disconnect();\r\n gatt.close();\r\n // gatt=null;\r\n this.gattMap.set(deviceId, null);\r\n this.connectionStates.set(deviceId, STATE_DISCONNECTED);\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:231','[AKBLE] disconnectDevice set STATE_DISCONNECTED, deviceId:', deviceId, 'connectionStates:')\r\n this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED);\r\n return;\r\n } else {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:235','[AKBLE] disconnectDevice: gatt is null, deviceId:', deviceId)\r\n return;\r\n }\r\n }\r\n\r\n async reconnectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise {\r\n let attempts = 0;\r\n const maxAttempts = options?.maxAttempts ?? 3;\r\n const interval = options?.interval ?? 3000;\r\n while (attempts < maxAttempts) {\r\n try {\r\n await this.disconnectDevice(deviceId, false);\r\n await this.connectDevice(deviceId, options);\r\n return;\r\n } catch (e) {\r\n attempts++;\r\n if (attempts >= maxAttempts) throw new Error('重连失败');\r\n // 修复 setTimeout 问题,使用旧式 Promise + setTimeout 解决\r\n await new Promise((resolve) => {\r\n setTimeout(() => {\r\n resolve();\r\n }, interval);\r\n });\r\n }\r\n }\r\n }\r\n\r\n getConnectedDevices(): BleDevice[] {\r\n // 创建一个空数组来存储结果\r\n const result: BleDevice[] = [];\r\n \r\n // 遍历 devices Map 并检查连接状态\r\n this.devices.forEach((device, deviceId) => {\r\n if (this.connectionStates.get(deviceId) === STATE_CONNECTED) {\r\n result.push(device);\r\n }\r\n });\r\n \r\n return result;\r\n }\r\n\r\n onConnectionStateChange(listener: BleConnectionStateChangeCallback) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:277','[AKBLE][LOG] onConnectionStateChange 注册, 当前监听数:', this.connectionStateChangeListeners.length + 1, listener)\r\n this.connectionStateChangeListeners.push(listener)\r\n }\r\n\r\n protected emitConnectionStateChange(deviceId: string, state: BleConnectionState) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:282','[AKBLE][LOG] emitConnectionStateChange', deviceId, state, 'listeners:', this.connectionStateChangeListeners.length, 'connectionStates:', this.connectionStates)\r\n for (const listener of this.connectionStateChangeListeners) {\r\n try { \r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:285','[AKBLE][LOG] emitConnectionStateChange 调用 listener', listener)\r\n listener(deviceId, state) \r\n } catch (e) { \r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:288','[AKBLE][LOG] emitConnectionStateChange listener error', e) \r\n }\r\n }\r\n }\r\n\r\n getGattInstance(deviceId: string): BluetoothGatt | null {\r\n return this.gattMap.get(deviceId) ?? null;\r\n }\r\n\r\n private getBluetoothAdapter(): BluetoothAdapter | null {\r\n const context = UTSAndroid.getAppContext();\r\n if (context == null) return null;\r\n const manager = context?.getSystemService(Context.BLUETOOTH_SERVICE) as BluetoothManager;\r\n return manager.getAdapter();\r\n }\r\n\r\n /**\r\n * 获取指定ID的设备(如果存在)\r\n */\r\n public getDevice(deviceId: string): BleDevice | null {\r\n\t __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:308',deviceId,this.devices)\r\n return this.devices.get(deviceId) ?? null;\r\n }\r\n}\r\n","import type { BleService, BleCharacteristic, BleDataReceivedCallback, BleCharacteristicProperties, WriteCharacteristicOptions, ByteArray } from '../interface.uts'\r\nimport BluetoothGatt from \"android.bluetooth.BluetoothGatt\";\r\nimport BluetoothGattService from \"android.bluetooth.BluetoothGattService\";\r\nimport BluetoothGattCharacteristic from \"android.bluetooth.BluetoothGattCharacteristic\";\r\nimport BluetoothGattDescriptor from \"android.bluetooth.BluetoothGattDescriptor\";\r\nimport BluetoothGattCallback from \"android.bluetooth.BluetoothGattCallback\";\r\n\r\nimport UUID from \"java.util.UUID\";\r\nimport { DeviceManager } from './device_manager.uts'\r\nimport { AkBleErrorImpl, AkBluetoothErrorCode } from '../unierror.uts'\r\nimport { AutoDiscoverAllResult } from '../interface.uts'\r\n\r\n\r\n\r\n\r\n// 补全UUID格式,将短格式转换为标准格式\r\nfunction getFullUuid(shortUuid : string) : string {\r\n\treturn `0000${shortUuid}-0000-1000-8000-00805f9b34fb`\r\n}\r\n\r\n\r\nconst deviceWriteQueues = new Map>();\r\n\r\nfunction enqueueDeviceWrite(deviceId : string, work : () => Promise) : Promise {\r\n\tconst previous = deviceWriteQueues.get(deviceId) ?? Promise.resolve();\r\n\tconst next = (async () : Promise => {\r\n\t\ttry {\r\n\t\t\tawait previous;\r\n\t\t} catch (e) { /* ignore previous rejection to keep queue alive */ }\r\n\t\treturn await work();\r\n\t})();\r\n\tconst queued = next.then(() => { }, () => { });\r\n\tdeviceWriteQueues.set(deviceId, queued);\r\n\treturn next.finally(() => {\r\n\t\tif (deviceWriteQueues.get(deviceId) == queued) {\r\n\t\t\tdeviceWriteQueues.delete(deviceId);\r\n\t\t}\r\n\t});\r\n}\r\n\r\n\r\n\r\nfunction createCharProperties(props : number) : BleCharacteristicProperties {\r\n\tconst result : BleCharacteristicProperties = {\r\n\t\tread: false,\r\n\t\twrite: false,\r\n\t\tnotify: false,\r\n\t\tindicate: false,\r\n\t\tcanRead: false,\r\n\t\tcanWrite: false,\r\n\t\tcanNotify: false,\r\n\t\twriteWithoutResponse: false\r\n\t};\r\n\tresult.read = (props & BluetoothGattCharacteristic.PROPERTY_READ) !== 0;\r\n\tresult.write = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0;\r\n\tresult.notify = (props & BluetoothGattCharacteristic.PROPERTY_NOTIFY) !== 0;\r\n\tresult.indicate = (props & BluetoothGattCharacteristic.PROPERTY_INDICATE) !== 0;\r\n\tresult.writeWithoutResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0;\r\n\r\n\tresult.canRead = result.read;\r\n\tconst writeWithoutResponse = result.writeWithoutResponse;\r\n\tresult.canWrite = (result.write != null && result.write) || (writeWithoutResponse != null && writeWithoutResponse);\r\n\tresult.canNotify = result.notify;\r\n\treturn result;\r\n}\r\n\r\n// 定义 PendingCallback 类型和实现类\r\ninterface PendingCallback {\r\n\tresolve : (data : any) => void;\r\n\treject : (err ?: any) => void;\r\n\ttimer ?: number; // Changed from any to number\r\n}\r\n\r\nclass PendingCallbackImpl implements PendingCallback {\r\n\tresolve : (data : any) => void;\r\n\treject : (err ?: any) => void;\r\n\ttimer ?: number; // Changed from any to number\r\n\r\n\tconstructor(resolve : (data : any) => void, reject : (err ?: any) => void, timer ?: number) {\r\n\t\tthis.resolve = resolve;\r\n\t\tthis.reject = reject;\r\n\t\tthis.timer = timer;\r\n\t}\r\n}\r\n\r\n// 全局回调管理(必须在类外部声明)\r\nlet pendingCallbacks : Map;\r\nlet notifyCallbacks : Map;\r\n\r\n// 在全局范围内初始化\r\npendingCallbacks = new Map();\r\nnotifyCallbacks = new Map();\r\n\r\n// 服务发现等待队列:deviceId -> 回调数组\r\nconst serviceDiscoveryWaiters = new Map void)[]>();\r\n// 服务发现状态:deviceId -> 是否已发现\r\nconst serviceDiscovered = new Map();\r\n\r\n// 特征发现等待队列:deviceId|serviceId -> 回调数组\r\nconst characteristicDiscoveryWaiters = new Map void)[]>();\r\n\r\nclass GattCallback extends BluetoothGattCallback {\r\n\tconstructor() {\r\n\t\tsuper();\r\n\t}\r\n\r\n\toverride onServicesDiscovered(gatt : BluetoothGatt, status : Int) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:108','ak onServicesDiscovered')\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tif (status == BluetoothGatt.GATT_SUCCESS) {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:111',`服务发现成功: ${deviceId}`);\r\n\t\t\tserviceDiscovered.set(deviceId, true);\r\n\t\t\t// 统一回调所有等待 getServices 的调用\r\n\t\t\tconst waiters = serviceDiscoveryWaiters.get(deviceId);\r\n\t\t\tif (waiters != null && waiters.length > 0) {\r\n\t\t\t\tconst services = gatt.getServices();\r\n\t\t\t\tconst result : BleService[] = [];\r\n\t\t\t\tif (services != null) {\r\n\t\t\t\t\tconst servicesList = services;\r\n\t\t\t\t\tconst size = servicesList.size;\r\n\t\t\t\t\tfor (let i = 0; i < size; i++) {\r\n\t\tconst service = servicesList.get(i as Int);\r\n\t\t\t\t\t\tif (service != null) {\r\n\t\t\t\t\t\t\tconst bleService : BleService = {\r\n\t\t\t\t\t\t\t\tuuid: service.getUuid().toString(),\r\n\t\t\t\t\t\t\t\tisPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY\r\n\t\t\t\t\t\t\t};\r\n\t\t\t\t\t\t\tresult.push(bleService);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\tfor (let i = 0; i < waiters.length; i++) {\r\n\t\t\t\t\tconst cb = waiters[i];\r\n\t\t\t\t\tif (cb != null) { cb(result, null); }\r\n\t\t\t\t}\r\n\t\t\t\tserviceDiscoveryWaiters.delete(deviceId);\r\n\t\t\t}\r\n\t\t} else {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:139',`服务发现失败: ${deviceId}, status: ${status}`);\r\n\t\t\t// 失败时也要通知等待队列\r\n\t\t\tconst waiters = serviceDiscoveryWaiters.get(deviceId);\r\n\t\t\tif (waiters != null && waiters.length > 0) {\r\n\t\t\t\tfor (let i = 0; i < waiters.length; i++) {\r\n\t\t\t\t\tconst cb = waiters[i];\r\n\t\t\t\t\tif (cb != null) { cb(null, new Error('服务发现失败')); }\r\n\t\t\t\t}\r\n\t\t\t\tserviceDiscoveryWaiters.delete(deviceId);\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\toverride onConnectionStateChange(gatt : BluetoothGatt, status : Int, newState : Int) : void {\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\tif (newState == BluetoothGatt.STATE_CONNECTED) {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:154',`设备已连接: ${deviceId}`);\r\n\t\t\tDeviceManager.handleConnectionStateChange(deviceId, 2, null); // 2 = STATE_CONNECTED\r\n\t} else if (newState == BluetoothGatt.STATE_DISCONNECTED) {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:157',`设备已断开: ${deviceId}`);\r\n\t\t\tserviceDiscovered.delete(deviceId);\r\n\t\t\tDeviceManager.handleConnectionStateChange(deviceId, 0, null); // 0 = STATE_DISCONNECTED\r\n\t\t}\r\n\t}\r\n\t\toverride onCharacteristicChanged(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:163','ak onCharacteristicChanged')\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tconst serviceId = characteristic.getService().getUuid().toString();\r\n\t\tconst charId = characteristic.getUuid().toString();\r\n\t\tconst key = `${deviceId}|${serviceId}|${charId}|notify`;\r\n\t\tconst callback = notifyCallbacks.get(key);\r\n\t\tconst value = characteristic.getValue();\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:170','[onCharacteristicChanged]', key, value);\r\n\t\tif (callback != null && value != null) {\r\n\t\t\tconst valueLength = value.size;\r\n\t\t\tconst arr = new Uint8Array(valueLength);\r\n\t\t\tfor (let i = 0 as Int; i < valueLength; i++) {\r\n\t\t\t\tconst v = value[i as Int];\r\n\t\t\t\tarr[i] = v != null ? v : 0;\r\n\t\t\t}\r\n\t\t\t// 保存接收日志\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:179',`\r\n INSERT INTO ble_data_log (device_id, service_id, char_id, direction, data, timestamp)\r\n VALUES ('${deviceId}', '${serviceId}', '${charId}', 'recv', '${Array.from(arr).join(',')}', ${Date.now()})\r\n `)\r\n\r\n\t\t\tcallback(arr);\r\n\t\t}\r\n\t}\r\n\t\toverride onCharacteristicRead(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:188','ak onCharacteristicRead', status)\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tconst serviceId = characteristic.getService().getUuid().toString();\r\n\t\tconst charId = characteristic.getUuid().toString();\r\n\t\tconst key = `${deviceId}|${serviceId}|${charId}|read`;\r\n\t\tconst pending = pendingCallbacks.get(key);\r\n\t\tconst value = characteristic.getValue();\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:195','[onCharacteristicRead]', key, 'status=', status, 'value=', value);\r\n\t\tif (pending != null) {\r\n\t\t\ttry {\r\n\t\t\t\tconst timer = pending.timer;\r\n\t\t\t\tif (timer != null) {\r\n\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t\tpending.timer = null;\r\n\t\t\t\t}\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\tif (status == BluetoothGatt.GATT_SUCCESS && value != null) {\r\n\t\t\t\t\tconst valueLength = value.size\r\n\t\t\t\t\tconst arr = new Uint8Array(valueLength);\r\n\t\t\t\t\tfor (let i = 0 as Int; i < valueLength; i++) {\r\n\t\t\t\t\t\tconst v = value[i as Int];\r\n\t\t\t\t\t\tarr[i] = v != null ? v : 0;\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\t// resolve with ArrayBuffer\r\n\t\t\t\t\tpending.resolve(arr.buffer as ArrayBuffer);\r\n\t\t\t\t} else {\r\n\t\t\t\t\tpending.reject(new Error('Characteristic read failed'));\r\n\t\t\t\t}\r\n\t\t\t} catch (e) {\r\n\t\t\t\ttry { pending.reject(e); } catch (e2) { __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:218',e2); }\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\toverride onCharacteristicWrite(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:224','ak onCharacteristicWrite', status)\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tconst serviceId = characteristic.getService().getUuid().toString();\r\n\t\tconst charId = characteristic.getUuid().toString();\r\n\t\tconst key = `${deviceId}|${serviceId}|${charId}|write`;\r\n\t\tconst pending = pendingCallbacks.get(key);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:230','[onCharacteristicWrite]', key, 'status=', status);\r\n\t\tif (pending != null) {\r\n\t\t\ttry {\r\n\t\t\t\tconst timer = pending.timer;\r\n\t\t\t\tif (timer != null) {\r\n\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t}\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\tif (status == BluetoothGatt.GATT_SUCCESS) {\r\n\t\t\t\t\tpending.resolve('ok');\r\n\t\t\t\t} else {\r\n\t\t\t\t\tpending.reject(new Error('Characteristic write failed'));\r\n\t\t\t\t}\r\n\t\t\t} catch (e) {\r\n\t\t\t\ttry { pending.reject(e); } catch (e2) { __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:244',e2); }\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n}\r\n\r\n// 导出单例实例供外部使用\r\nexport const gattCallback = new GattCallback();\r\n\r\nexport class ServiceManager {\r\n\tprivate static instance : ServiceManager | null = null;\r\n\tprivate services = new Map();\r\n\tprivate characteristics = new Map>();\r\n\tprivate deviceManager = DeviceManager.getInstance();\r\n\tprivate constructor() { }\r\n\tstatic getInstance() : ServiceManager {\r\n\t\tif (ServiceManager.instance == null) {\r\n\t\t\tServiceManager.instance = new ServiceManager();\r\n\t\t}\r\n\t\treturn ServiceManager.instance!;\r\n\t}\r\n\r\n\tgetServices(deviceId : string, callback ?: (services : BleService[] | null, error ?: Error) => void) : any | Promise {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:267','ak start getservice', deviceId);\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) {\r\n\t\t\tif (callback != null) { callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\")); }\r\n\t\t\treturn Promise.reject(new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\"));\r\n\t\t}\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:273','ak serviceDiscovered', gatt)\r\n\t\t// 如果服务已发现,直接返回\r\n\t\tif (serviceDiscovered.get(deviceId) == true) {\r\n\t\t\tconst services = gatt.getServices();\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:277',services)\r\n\t\t\tconst result : BleService[] = [];\r\n\t\t\tif (services != null) {\r\n\t\t\t\tconst servicesList = services;\r\n\t\t\t\tconst size = servicesList.size;\r\n\t\t\t\tif (size > 0) {\r\n\t\t\tfor (let i = 0 as Int; i < size; i++) {\r\n\t\t\t\tconst service = servicesList != null ? servicesList.get(i) : servicesList[i];\r\n\t\t\t\t\t\tif (service != null) {\r\n\t\t\t\t\t\t\tconst bleService : BleService = {\r\n\t\t\t\t\t\t\t\tuuid: service.getUuid().toString(),\r\n\t\t\t\t\t\t\t\tisPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY\r\n\t\t\t\t\t\t\t};\r\n\t\t\t\t\t\t\tresult.push(bleService);\r\n\r\n\t\t\t\t\t\t\tif (bleService.uuid == getFullUuid('0001')) {\r\n\t\t\t\t\t\t\t\tconst device = this.deviceManager.getDevice(deviceId);\r\n\t\t\t\t\t\t\t\tif (device != null) {\r\n\t\t\t\t\t\t\t\t\tdevice.serviceId = bleService.uuid;\r\n\t\t\t\t\t\t\t\t\tthis.getCharacteristics(deviceId, device.serviceId, (chars, err) => {\r\n\t\t\t\t\t\t\t\t\t\tif (err == null && chars != null) {\r\n\t\t\t\t\t\t\t\t\t\t\tconst writeChar = chars.find(c => c.uuid == getFullUuid('0010'));\r\n\t\t\t\t\t\t\t\t\t\t\tconst notifyChar = chars.find(c => c.uuid == getFullUuid('0011'));\r\n\t\t\t\t\t\t\t\t\t\t\tif (writeChar != null) device.writeCharId = writeChar.uuid;\r\n\t\t\t\t\t\t\t\t\t\t\tif (notifyChar != null) device.notifyCharId = notifyChar.uuid;\r\n\t\t\t\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\t\t\t});\r\n\t\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tif (callback != null) { callback(result, null); }\r\n\t\t\treturn Promise.resolve(result);\r\n\t\t}\r\n\t\t// 未发现则发起服务发现并加入等待队列\r\n\t\tif (!serviceDiscoveryWaiters.has(deviceId)) {\r\n\t\t\tserviceDiscoveryWaiters.set(deviceId, []);\r\n\t\t\tgatt.discoverServices();\r\n\t\t}\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\tconst cb = (services : BleService[] | null, error ?: Error) => {\r\n\t\t\t\tif (error != null) reject(error);\r\n\t\t\t\telse resolve(services ?? []);\r\n\t\t\t\tif (callback != null) callback(services, error);\r\n\t\t\t};\r\n\t\t\tconst arr = serviceDiscoveryWaiters.get(deviceId);\r\n\t\t\tif (arr != null) arr.push(cb);\r\n\t\t});\r\n\t}\r\n\tgetCharacteristics(deviceId : string, serviceId : string, callback : (characteristics : BleCharacteristic[] | null, error ?: Error) => void) : void {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\"));\r\n\t\t// 如果服务还没发现,等待服务发现后再查特征\r\n\t\tif (serviceDiscovered.get(deviceId) !== true) {\r\n\t\t\t// 先注册到服务发现等待队列\r\n\t\t\tthis.getServices(deviceId, (services, err) => {\r\n\t\t\t\tif (err != null) {\r\n\t\t\t\t\tcallback(null, err);\r\n\t\t\t\t} else {\r\n\t\t\t\t\tthis.getCharacteristics(deviceId, serviceId, callback);\r\n\t\t\t\t}\r\n\t\t\t});\r\n\t\t\treturn;\r\n\t\t}\r\n\t\t// 服务已发现,正常获取特征\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\"));\r\n\t\tconst chars = service.getCharacteristics();\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:347',chars)\r\n\t\tconst result : BleCharacteristic[] = [];\r\n\t\tif (chars != null) {\r\n\t\t\tconst characteristicsList = chars;\r\n\t\t\tconst size = characteristicsList.size;\r\n\t\t\tconst bleService : BleService = {\r\n\t\t\t\tuuid: serviceId,\r\n\t\t\t\tisPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY\r\n\t\t\t};\r\n\t\t\tfor (let i = 0 as Int; i < size; i++) {\r\n\t\t\t\tconst char = characteristicsList != null ? characteristicsList.get(i as Int) : characteristicsList[i];\r\n\t\t\t\tif (char != null) {\r\n\t\t\t\t\tconst props = char.getProperties();\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tconst charUuid = char.getUuid() != null ? char.getUuid().toString() : '';\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:362','[ServiceManager] characteristic uuid=', charUuid);\r\n\t\t\t\t\t} catch (e) { __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:363','[ServiceManager] failed to read char uuid', e); }\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:364',props);\r\n\t\t\t\t\tconst bleCharacteristic : BleCharacteristic = {\r\n\t\t\t\t\t\tuuid: char.getUuid().toString(),\r\n\t\t\t\t\t\tservice: bleService,\r\n\t\t\t\t\t\tproperties: createCharProperties(props)\r\n\t\t\t\t\t};\r\n\t\t\t\t\tresult.push(bleCharacteristic);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t\tcallback(result, null);\r\n\t}\r\n\r\n\tpublic async readCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|read`;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:385',key)\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\tconst timer = setTimeout(() => {\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\treject(new AkBleErrorImpl(AkBluetoothErrorCode.ConnectionTimeout, \"Connection timeout\", \"\"));\r\n\t\t\t}, 5000);\r\n\t\t\tconst resolveAdapter = (data : any) => { __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:391','read resolve:', data); resolve(data as ArrayBuffer); };\r\n\t\t\tconst rejectAdapter = (err ?: any) => { reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Unknown error occurred\", \"\")); };\r\n\t\t\tpendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer));\r\n\t\t\tif (gatt.readCharacteristic(char) == false) {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\treject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Unknown error occurred\", \"\"));\r\n\t\t\t}\r\n\t\t\telse {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:400','read should be succeed', key)\r\n\t\t\t}\r\n\t\t});\r\n\t}\r\n\r\n\tpublic async writeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, data : Uint8Array, options ?: WriteCharacteristicOptions) : Promise {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:406','[writeCharacteristic] deviceId:', deviceId, 'serviceId:', serviceId, 'characteristicId:', characteristicId, 'data:', data);\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) {\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:409','[writeCharacteristic] gatt is null');\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\t}\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) {\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:414','[writeCharacteristic] service is null');\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\t}\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) {\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:419','[writeCharacteristic] characteristic is null');\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\t}\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|write`;\r\n\t\tconst wantsNoResponse = options != null && options.waitForResponse == false;\r\n\t\tlet retryMaxAttempts = 20;\r\n\t\tlet retryDelay = 100;\r\n\t\tlet giveupTimeout = 20000;\r\n\t\tif (options != null) {\r\n\t\t\ttry {\r\n\t\t\t\tif (options.maxAttempts != null) {\r\n\t\t\t\t\tconst parsedAttempts = Math.floor(options.maxAttempts as number);\r\n\t\t\t\t\tif (!isNaN(parsedAttempts) && parsedAttempts > 0) retryMaxAttempts = parsedAttempts;\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t\ttry {\r\n\t\t\t\tif (options.retryDelayMs != null) {\r\n\t\t\t\t\tconst parsedDelay = Math.floor(options.retryDelayMs as number);\r\n\t\t\t\t\tif (!isNaN(parsedDelay) && parsedDelay >= 0) retryDelay = parsedDelay;\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t\ttry {\r\n\t\t\t\tif (options.giveupTimeoutMs != null) {\r\n\t\t\t\t\tconst parsedGiveup = Math.floor(options.giveupTimeoutMs as number);\r\n\t\t\t\t\tif (!isNaN(parsedGiveup) && parsedGiveup > 0) giveupTimeout = parsedGiveup;\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t}\r\n\t\tconst gattInstance = gatt;\r\n\t\tconst executeWrite = () : Promise => {\r\n\r\n\t\t\treturn new Promise((resolve) => {\r\n\t\t\t\tconst initialTimeout = Math.max(giveupTimeout + 5000, 10000);\r\n\t\t\t\tlet timer = setTimeout(() => {\r\n\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:454','[writeCharacteristic] timeout');\r\n\t\t\t\t\tresolve(false);\r\n\t\t\t\t}, initialTimeout);\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:457','[writeCharacteristic] initial timeout set to', initialTimeout, 'ms for', key);\r\n\t\t\t\tconst resolveAdapter = (data : any) => {\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:459','[writeCharacteristic] resolveAdapter called');\r\n\t\t\t\t\tresolve(true);\r\n\t\t\t\t};\r\n\t\t\t\tconst rejectAdapter = (err ?: any) => {\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:463','[writeCharacteristic] rejectAdapter called', err);\r\n\t\t\t\t\tresolve(false);\r\n\t\t\t\t};\r\n\t\t\t\tpendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer));\r\n\t\t\t\tconst byteArray = new ByteArray(data.length as Int);\r\n\t\t\t\tfor (let i = 0 as Int; i < data.length; i++) {\r\n\t\t\t\t\tbyteArray[i] = data[i].toByte();\r\n\t\t\t\t}\r\n\t\t\t\tconst forceWriteTypeNoResponse = options != null && options.forceWriteTypeNoResponse == true;\r\n\t\t\t\tlet usesNoResponse = forceWriteTypeNoResponse || wantsNoResponse;\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst props = char.getProperties();\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:475','[writeCharacteristic] characteristic properties mask=', props);\r\n\t\t\t\t\tif (usesNoResponse == false) {\r\n\t\t\t\t\t\tconst supportsWriteWithResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0;\r\n\t\t\t\t\t\tconst supportsWriteNoResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0;\r\n\t\t\t\t\t\tif (supportsWriteWithResponse == false && supportsWriteNoResponse == true) {\r\n\t\t\t\t\t\t\tusesNoResponse = true;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (usesNoResponse) {\r\n\t\t\t\t\t\ttry { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_NO_RESPONSE); } catch (e) { }\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:485','[writeCharacteristic] using WRITE_TYPE_NO_RESPONSE');\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\ttry { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT); } catch (e) { }\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:488','[writeCharacteristic] using WRITE_TYPE_DEFAULT');\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:491','[writeCharacteristic] failed to inspect/set write type', e);\r\n\t\t\t\t}\r\n\t\t\t\tconst maxAttempts = retryMaxAttempts;\r\n\t\t\t\tfunction attemptWrite(att : Int) : void {\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tlet setOk = true;\r\n\t\t\t\t\t\ttry {\r\n\t\t\t\t\t\t\tconst setRes = char.setValue(byteArray);\r\n\t\t\t\t\t\t\tif (typeof setRes == 'boolean' && setRes == false) {\r\n\t\t\t\t\t\t\t\tsetOk = false;\r\n\t\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:501','[writeCharacteristic] setValue returned false for', key, 'attempt', att);\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\t\tsetOk = false;\r\n\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:505','[writeCharacteristic] setValue threw for', key, 'attempt', att, e);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (setOk == false) {\r\n\t\t\t\t\t\t\tif (att >= maxAttempts) {\r\n\t\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\tsetTimeout(() => { attemptWrite((att + 1) as Int); }, retryDelay);\r\n\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\ttry {\r\n\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:518','[writeCharacteristic] attempt', att, 'calling gatt.writeCharacteristic');\r\n\t\t\t\t\t\t\tconst r = gattInstance.writeCharacteristic(char);\r\n\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:520','[writeCharacteristic] attempt', att, 'result=', r);\r\n\t\t\t\t\t\t\tif (r == true) {\r\n\t\t\t\t\t\t\t\tif (usesNoResponse) {\r\n\t\t\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:523','[writeCharacteristic] WRITE_TYPE_NO_RESPONSE success for', key);\r\n\t\t\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t\t\tresolve(true);\r\n\t\t\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\t\tconst extra = 20000;\r\n\t\t\t\t\t\t\t\ttimer = setTimeout(() => {\r\n\t\t\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:533','[writeCharacteristic] timeout after write initiated');\r\n\t\t\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t\t\t}, extra);\r\n\t\t\t\t\t\t\t\tconst pendingEntry = pendingCallbacks.get(key);\r\n\t\t\t\t\t\t\t\tif (pendingEntry != null) pendingEntry.timer = timer;\r\n\t\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:541','[writeCharacteristic] attempt', att, 'exception when calling writeCharacteristic', e);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (att < maxAttempts) {\r\n\t\t\t\t\t\t\tconst nextAtt = (att + 1) as Int;\r\n\t\t\t\t\t\t\tsetTimeout(() => { attemptWrite(nextAtt); }, retryDelay);\r\n\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (usesNoResponse) {\r\n\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:551','[writeCharacteristic] all attempts failed with WRITE_NO_RESPONSE for', key);\r\n\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\tconst giveupTimeoutLocal = giveupTimeout;\r\n\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:557','[writeCharacteristic] all attempts failed; waiting for late callback up to', giveupTimeoutLocal, 'ms for', key);\r\n\t\t\t\t\t\tconst giveupTimer = setTimeout(() => {\r\n\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:560','[writeCharacteristic] giveup timeout expired for', key);\r\n\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t}, giveupTimeoutLocal);\r\n\t\t\t\t\t\tconst pendingEntryAfter = pendingCallbacks.get(key);\r\n\t\t\t\t\t\tif (pendingEntryAfter != null) pendingEntryAfter.timer = giveupTimer;\r\n\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:568','[writeCharacteristic] Exception in attemptWrite', e);\r\n\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\r\n\t\t\t\ttry {\r\n\t\t\t\t\tattemptWrite(1 as Int);\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:578','[writeCharacteristic] Exception before attempting write', e);\r\n\t\t\t\t\tresolve(false);\r\n\t\t\t\t}\r\n\t\t\t});\r\n\t\t};\r\n\t\treturn enqueueDeviceWrite(deviceId, executeWrite);\r\n\t}\r\n\r\n\tpublic async subscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, onData : BleDataReceivedCallback) : Promise {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|notify`;\r\n\t\tnotifyCallbacks.set(key, onData);\r\n\t\tif (gatt.setCharacteristicNotification(char, true) == false) {\r\n\t\t\tnotifyCallbacks.delete(key);\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Failed to unsubscribe characteristic\", \"\");\r\n\t\t} else {\r\n\t\t\t// 写入 CCCD 描述符,启用 notify\r\n\t\t\tconst descriptor = char.getDescriptor(UUID.fromString(\"00002902-0000-1000-8000-00805f9b34fb\"));\r\n\t\t\tif (descriptor != null) {\r\n\t\t\t\t// 设置描述符值\r\n\t\t\t\tconst value =\r\n\t\t\t\t\tBluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE;\r\n\r\n\t\t\t\tdescriptor.setValue(value);\r\n\t\t\t\tconst writedescript = gatt.writeDescriptor(descriptor);\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:608','subscribeCharacteristic: CCCD written for notify', writedescript);\r\n\t\t\t} else {\r\n\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:610','subscribeCharacteristic: CCCD descriptor not found!');\r\n\t\t\t}\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:612','subscribeCharacteristic ok!!');\r\n\t\t}\r\n\t}\r\n\r\n\tpublic async unsubscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|notify`;\r\n\t\tnotifyCallbacks.delete(key);\r\n\t\tif (gatt.setCharacteristicNotification(char, false) == false) {\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Failed to unsubscribe characteristic\", \"\");\r\n\t\t}\r\n\t}\r\n\r\n\r\n\t// 自动发现所有服务和特征\r\n\tpublic async autoDiscoverAll(deviceId : string) : Promise {\r\n\t\tconst services = await this.getServices(deviceId, null) as BleService[];\r\n\t\tconst allCharacteristics : BleCharacteristic[] = [];\r\n\t\tfor (const service of services) {\r\n\t\t\tawait new Promise((resolve, reject) => {\r\n\t\t\t\tthis.getCharacteristics(deviceId, service.uuid, (chars, err) => {\r\n\t\t\t\t\tif (err != null) reject(err);\r\n\t\t\t\t\telse {\r\n\t\t\t\t\t\tif (chars != null) allCharacteristics.push(...chars);\r\n\t\t\t\t\t\tresolve();\r\n\t\t\t\t\t}\r\n\t\t\t\t});\r\n\t\t\t});\r\n\t\t}\r\n\t\treturn { services, characteristics: allCharacteristics };\r\n\t}\r\n\r\n\t// 自动订阅所有支持 notify/indicate 的特征\r\n\tpublic async subscribeAllNotifications(deviceId : string, onData : BleDataReceivedCallback) : Promise {\r\n\t\tconst { services, characteristics } = await this.autoDiscoverAll(deviceId);\r\n\t\tfor (const char of characteristics) {\r\n\t\t\tif (char.properties.notify || char.properties.indicate) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tawait this.subscribeCharacteristic(deviceId, char.service.uuid, char.uuid, onData);\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t// 可以选择忽略单个特征订阅失败\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:658',`订阅特征 ${char.uuid} 失败:`, e);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n}","/// \n// 之所以又写了一份,是因为外层的socket,connectSocket的时候必须传入multiple:true\n// 但是android又不能传入,目前代码里又不能写条件编译之类的。\nexport function initRuntimeSocket(\n hosts: string,\n port: string,\n id: string\n): Promise {\n if (hosts == '' || port == '' || id == '') return Promise.resolve(null)\n return hosts\n .split(',')\n .reduce>(\n (\n promise: Promise,\n host: string\n ): Promise => {\n return promise.then((socket): Promise => {\n if (socket != null) return Promise.resolve(socket)\n return tryConnectSocket(host, port, id)\n })\n },\n Promise.resolve(null)\n )\n}\n\nconst SOCKET_TIMEOUT = 500\nfunction tryConnectSocket(\n host: string,\n port: string,\n id: string\n): Promise {\n return new Promise((resolve, reject) => {\n const socket = uni.connectSocket({\n url: `ws://${host}:${port}/${id}`,\n fail() {\n resolve(null)\n },\n })\n const timer = setTimeout(() => {\n // @ts-expect-error\n socket.close({\n code: 1006,\n reason: 'connect timeout',\n } as CloseSocketOptions)\n resolve(null)\n }, SOCKET_TIMEOUT)\n\n socket.onOpen((e) => {\n clearTimeout(timer)\n resolve(socket)\n })\n socket.onClose((e) => {\n clearTimeout(timer)\n resolve(null)\n })\n socket.onError((e) => {\n clearTimeout(timer)\n resolve(null)\n })\n })\n}\n","\r\n\r\n","/**\r\n * PermissionManager.uts\r\n * \r\n * Utility class for managing Android permissions throughout the app\r\n * Handles requesting permissions, checking status, and directing users to settings\r\n */\r\n\r\n/**\r\n * Common permission types that can be requested\r\n */\r\nexport enum PermissionType {\r\n BLUETOOTH = 'bluetooth',\r\n LOCATION = 'location',\r\n STORAGE = 'storage',\r\n CAMERA = 'camera',\r\n MICROPHONE = 'microphone',\r\n NOTIFICATIONS = 'notifications',\r\n CALENDAR = 'calendar',\r\n CONTACTS = 'contacts',\r\n SENSORS = 'sensors'\r\n}\r\n\r\n/**\r\n * Result of a permission request\r\n */\r\ntype PermissionResult = {\r\n granted: boolean;\r\n grantedPermissions: string[];\r\n deniedPermissions: string[];\r\n}\r\n\r\n/**\r\n * Manages permission requests and checks throughout the app\r\n */\r\nexport class PermissionManager {\r\n /**\r\n * Maps permission types to the actual Android permission strings\r\n */\r\n private static getPermissionsForType(type: PermissionType): string[] {\r\n switch (type) {\r\n case PermissionType.BLUETOOTH:\r\n return [\r\n 'android.permission.BLUETOOTH_SCAN',\r\n 'android.permission.BLUETOOTH_CONNECT',\r\n 'android.permission.BLUETOOTH_ADVERTISE'\r\n ];\r\n case PermissionType.LOCATION:\r\n return [\r\n 'android.permission.ACCESS_FINE_LOCATION',\r\n 'android.permission.ACCESS_COARSE_LOCATION'\r\n ];\r\n case PermissionType.STORAGE:\r\n return [\r\n 'android.permission.READ_EXTERNAL_STORAGE',\r\n 'android.permission.WRITE_EXTERNAL_STORAGE'\r\n ];\r\n case PermissionType.CAMERA:\r\n return ['android.permission.CAMERA'];\r\n case PermissionType.MICROPHONE:\r\n return ['android.permission.RECORD_AUDIO'];\r\n case PermissionType.NOTIFICATIONS:\r\n return ['android.permission.POST_NOTIFICATIONS'];\r\n case PermissionType.CALENDAR:\r\n return [\r\n 'android.permission.READ_CALENDAR',\r\n 'android.permission.WRITE_CALENDAR'\r\n ];\r\n case PermissionType.CONTACTS:\r\n return [\r\n 'android.permission.READ_CONTACTS',\r\n 'android.permission.WRITE_CONTACTS'\r\n ];\r\n case PermissionType.SENSORS:\r\n return ['android.permission.BODY_SENSORS'];\r\n default:\r\n return [];\r\n }\r\n }\r\n \r\n /**\r\n * Get appropriate display name for a permission type\r\n */\r\n private static getPermissionDisplayName(type: PermissionType): string {\r\n switch (type) {\r\n case PermissionType.BLUETOOTH:\r\n return '蓝牙';\r\n case PermissionType.LOCATION:\r\n return '位置';\r\n case PermissionType.STORAGE:\r\n return '存储';\r\n case PermissionType.CAMERA:\r\n return '相机';\r\n case PermissionType.MICROPHONE:\r\n return '麦克风';\r\n case PermissionType.NOTIFICATIONS:\r\n return '通知';\r\n case PermissionType.CALENDAR:\r\n return '日历';\r\n case PermissionType.CONTACTS:\r\n return '联系人';\r\n case PermissionType.SENSORS:\r\n return '身体传感器';\r\n default:\r\n return '未知权限';\r\n }\r\n }\r\n \r\n /**\r\n * Check if a permission is granted\r\n * @param type The permission type to check\r\n * @returns True if the permission is granted, false otherwise\r\n */\r\n static isPermissionGranted(type: PermissionType): boolean {\r\n\r\n try {\r\n const permissions = this.getPermissionsForType(type);\r\n const activity = UTSAndroid.getUniActivity();\r\n \r\n if (activity == null || permissions.length === 0) {\r\n return false;\r\n }\r\n \r\n // Check each permission in the group\r\n for (const permission of permissions) {\r\n if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) {\r\n return false;\r\n }\r\n }\r\n \r\n return true;\r\n } catch (e) {\r\n __f__('error','at ak/PermissionManager.uts:132',`Error checking ${type} permission:`, e);\r\n return false;\r\n }\r\n\r\n \r\n\r\n\r\n\r\n }\r\n \r\n /**\r\n * Request a permission from the user\r\n * @param type The permission type to request\r\n * @param callback Function to call with the result of the permission request\r\n * @param showRationale Whether to show a rationale dialog if permission was previously denied\r\n */\r\n static requestPermission(\r\n type: PermissionType,\r\n callback: (result: PermissionResult) => void,\r\n showRationale: boolean = true\r\n ): void {\r\n\r\n try {\r\n const permissions = this.getPermissionsForType(type);\r\n const activity = UTSAndroid.getUniActivity();\r\n \r\n if (activity == null || permissions.length === 0) {\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: permissions\r\n });\r\n return;\r\n }\r\n \r\n // Check if already granted\r\n let allGranted = true;\r\n for (const permission of permissions) {\r\n if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) {\r\n allGranted = false;\r\n break;\r\n }\r\n }\r\n \r\n if (allGranted) {\r\n callback({\r\n granted: true,\r\n grantedPermissions: permissions,\r\n deniedPermissions: []\r\n });\r\n return;\r\n }\r\n \r\n // Request the permissions\r\n UTSAndroid.requestSystemPermission(\r\n activity,\r\n permissions,\r\n (granted: boolean, grantedPermissions: string[]) => {\r\n if (granted) {\r\n callback({\r\n granted: true,\r\n grantedPermissions: grantedPermissions,\r\n deniedPermissions: []\r\n });\r\n } else if (showRationale) {\r\n // Show rationale dialog\r\n this.showPermissionRationale(type, callback);\r\n } else {\r\n // Just report the denial\r\n callback({\r\n granted: false,\r\n grantedPermissions: grantedPermissions,\r\n deniedPermissions: this.getDeniedPermissions(permissions, grantedPermissions)\r\n });\r\n }\r\n },\r\n (denied: boolean, deniedPermissions: string[]) => {\r\n callback({\r\n granted: false,\r\n grantedPermissions: this.getGrantedPermissions(permissions, deniedPermissions),\r\n deniedPermissions: deniedPermissions\r\n });\r\n }\r\n );\r\n } catch (e) {\r\n __f__('error','at ak/PermissionManager.uts:217',`Error requesting ${type} permission:`, e);\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: this.getPermissionsForType(type)\r\n });\r\n }\r\n\r\n \r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n }\r\n \r\n /**\r\n * Show a rationale dialog explaining why the permission is needed\r\n */\r\n private static showPermissionRationale(\r\n type: PermissionType,\r\n callback: (result: PermissionResult) => void\r\n ): void {\r\n const permissionName = this.getPermissionDisplayName(type);\r\n \r\n uni.showModal({\r\n title: '权限申请',\r\n content: `需要${permissionName}权限才能使用相关功能`,\r\n confirmText: '去设置',\r\n cancelText: '取消',\r\n success: (result) => {\r\n if (result.confirm) {\r\n this.openAppSettings();\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: this.getPermissionsForType(type)\r\n });\r\n } else {\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: this.getPermissionsForType(type)\r\n });\r\n }\r\n }\r\n });\r\n }\r\n \r\n /**\r\n * Open the app settings page\r\n */\r\n static openAppSettings(): void {\r\n\r\n try {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const intent = new android.content.Intent();\r\n intent.setAction(\"android.settings.APPLICATION_DETAILS_SETTINGS\");\r\n const uri = android.net.Uri.fromParts(\"package\", context.getPackageName(), null);\r\n intent.setData(uri);\r\n intent.addFlags(android.content.Intent.FLAG_ACTIVITY_NEW_TASK);\r\n context.startActivity(intent);\r\n }\r\n } catch (e) {\r\n __f__('error','at ak/PermissionManager.uts:285','Failed to open app settings', e);\r\n uni.showToast({\r\n title: '请手动前往系统设置修改应用权限',\r\n icon: 'none',\r\n duration: 3000\r\n });\r\n }\r\n\r\n \r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n }\r\n \r\n /**\r\n * Helper to get the list of granted permissions\r\n */\r\n private static getGrantedPermissions(allPermissions: string[], deniedPermissions: string[]): string[] {\r\n return allPermissions.filter(p => !deniedPermissions.includes(p));\r\n }\r\n \r\n /**\r\n * Helper to get the list of denied permissions\r\n */\r\n private static getDeniedPermissions(allPermissions: string[], grantedPermissions: string[]): string[] {\r\n return allPermissions.filter(p => !grantedPermissions.includes(p));\r\n }\r\n \r\n /**\r\n * Request multiple permission types at once\r\n * @param types Array of permission types to request\r\n * @param callback Function to call when all permissions have been processed\r\n */\r\n static requestMultiplePermissions(\r\n types: PermissionType[],\r\n callback: (results: Map) => void\r\n ): void {\r\n if (types.length === 0) {\r\n callback(new Map());\r\n return;\r\n }\r\n \r\n const results = new Map();\r\n let remaining = types.length;\r\n \r\n for (const type of types) {\r\n this.requestPermission(\r\n type,\r\n (result) => {\r\n results.set(type, result);\r\n remaining--;\r\n \r\n if (remaining === 0) {\r\n callback(results);\r\n }\r\n },\r\n true\r\n );\r\n }\r\n }\r\n \r\n /**\r\n * Convenience method to request Bluetooth permissions\r\n * @param callback Function to call after the permission request\r\n */\r\n static requestBluetoothPermissions(callback: (granted: boolean) => void): void {\r\n this.requestPermission(PermissionType.BLUETOOTH, (result) => {\r\n // For Bluetooth, we also need location permissions on Android\r\n if (result.granted) {\r\n this.requestPermission(PermissionType.LOCATION, (locationResult) => {\r\n callback(locationResult.granted);\r\n });\r\n } else {\r\n callback(false);\r\n }\r\n });\r\n }\r\n}","import { initRuntimeSocket } from './socket'\n\nexport function initRuntimeSocketService(): Promise {\n const hosts: string = process.env.UNI_SOCKET_HOSTS\n const port: string = process.env.UNI_SOCKET_PORT\n const id: string = process.env.UNI_SOCKET_ID\n if (hosts == '' || port == '' || id == '') return Promise.resolve(false)\n let socketTask: SocketTask | null = null\n __registerWebViewUniConsole(\n (): string => {\n return process.env.UNI_CONSOLE_WEBVIEW_EVAL_JS_CODE\n },\n (data: string) => {\n socketTask?.send({\n data,\n } as SendSocketMessageOptions)\n }\n )\n return Promise.resolve()\n .then((): Promise => {\n return initRuntimeSocket(hosts, port, id).then((socket): boolean => {\n if (socket == null) {\n return false\n }\n socketTask = socket\n return true\n })\n })\n .catch((): boolean => {\n return false\n })\n}\n\ninitRuntimeSocketService()\n","// 蓝牙相关接口和类型定义\r\n\r\n// 基础设备信息类型\r\nexport type BleDeviceInfo = {\r\n\tdeviceId : string;\r\n\tname : string;\r\n\tRSSI ?: number;\r\n\tconnected ?: boolean;\r\n\t// 新增\r\n\tserviceId ?: string;\r\n\twriteCharId ?: string;\r\n\tnotifyCharId ?: string;\r\n}\r\nexport type AutoDiscoverAllResult = {\r\n\tservices : BleService[];\r\n\tcharacteristics : BleCharacteristic[];\r\n}\r\n\r\n// 服务信息类型\r\nexport type BleServiceInfo = {\r\n\tuuid : string;\r\n\tisPrimary : boolean;\r\n}\r\n\r\n// 特征值属性类型\r\nexport type BleCharacteristicProperties = {\r\n\tread : boolean;\r\n\twrite : boolean;\r\n\tnotify : boolean;\r\n\tindicate : boolean;\r\n\twriteWithoutResponse ?: boolean;\r\n\tcanRead ?: boolean;\r\n\tcanWrite ?: boolean;\r\n\tcanNotify ?: boolean;\r\n}\r\n\r\n// 特征值信息类型\r\nexport type BleCharacteristicInfo = {\r\n\tuuid : string;\r\n\tserviceId : string;\r\n\tproperties : BleCharacteristicProperties;\r\n}\r\n\r\n// 错误状态码\r\nexport enum BleErrorCode {\r\n\tUNKNOWN_ERROR = 0,\r\n\tBLUETOOTH_UNAVAILABLE = 1,\r\n\tPERMISSION_DENIED = 2,\r\n\tDEVICE_NOT_CONNECTED = 3,\r\n\tSERVICE_NOT_FOUND = 4,\r\n\tCHARACTERISTIC_NOT_FOUND = 5,\r\n\tOPERATION_TIMEOUT = 6\r\n}\r\n\r\n// 命令类型\r\nexport enum CommandType {\r\n\tBATTERY = 1,\r\n\tDEVICE_INFO = 2,\r\n\tCUSTOM = 99,\r\n\tTestBatteryLevel = 0x01\r\n}\r\n\r\n// 错误接口\r\nexport type BleError {\r\n\terrCode : number;\r\n\terrMsg : string;\r\n\terrSubject ?: string;\r\n}\r\n\r\n\r\n// 连接选项\r\nexport type BleConnectOptions = {\r\n\tdeviceId : string;\r\n\ttimeout ?: number;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 断开连接选项\r\nexport type BleDisconnectOptions = {\r\n\tdeviceId : string;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 获取特征值选项\r\nexport type BleCharacteristicOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tcharacteristicId : string;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 写入特征值选项\r\nexport type BleWriteOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tcharacteristicId : string;\r\n\tvalue : Uint8Array;\r\n\twriteType ?: number;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// Options for writeCharacteristic helper\r\nexport type WriteCharacteristicOptions = {\r\n\twaitForResponse ?: boolean;\r\n\tmaxAttempts ?: number;\r\n\tretryDelayMs ?: number;\r\n\tgiveupTimeoutMs ?: number;\r\n\tforceWriteTypeNoResponse ?: boolean;\r\n}\r\n\r\n// 通知特征值回调函数\r\nexport type BleNotifyCallback = (data : Uint8Array) => void;\r\n\r\n// 通知特征值选项\r\nexport type BleNotifyOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tcharacteristicId : string;\r\n\tstate ?: boolean; // true: 启用通知,false: 禁用通知\r\n\tonCharacteristicValueChange : BleNotifyCallback;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 获取服务选项\r\nexport type BleDeviceServicesOptions = {\r\n\tdeviceId : string;\r\n\tsuccess ?: (result : BleServicesResult) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 获取特征值选项\r\nexport type BleDeviceCharacteristicsOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tsuccess ?: (result : BleCharacteristicsResult) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 蓝牙扫描选项\r\nexport type BluetoothScanOptions = {\r\n\tservices ?: string[];\r\n\ttimeout ?: number;\r\n\tonDeviceFound ?: (device : BleDeviceInfo) => void;\r\n\tsuccess ?: (result : BleScanResult) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 扫描结果\r\n\r\n// 服务结果\r\nexport type BleServicesResult = {\r\n\tservices : BleServiceInfo[];\r\n\terrMsg ?: string;\r\n}\r\n\r\n// 特征值结果\r\nexport type BleCharacteristicsResult = {\r\n\tcharacteristics : BleCharacteristicInfo[];\r\n\terrMsg ?: string;\r\n}\r\n\r\n// 定义连接状态枚举\r\nexport enum BLE_CONNECTION_STATE {\r\n\tDISCONNECTED = 0,\r\n\tCONNECTING = 1,\r\n\tCONNECTED = 2,\r\n\tDISCONNECTING = 3\r\n}\r\n\r\n// 电池状态类型定义\r\nexport type BatteryStatus = {\r\n\tbatteryLevel : number; // 电量百分比\r\n\tisCharging : boolean; // 充电状态\r\n}\r\n\r\n// 蓝牙服务接口类型定义 - 转换为type类型\r\nexport type BleService = {\r\n\tuuid : string;\r\n\tisPrimary : boolean;\r\n}\r\n\r\n// 蓝牙特征值接口定义 - 转换为type类型\r\nexport type BleCharacteristic = {\r\n\tuuid : string;\r\n\tservice : BleService;\r\n\tproperties : BleCharacteristicProperties;\r\n}\r\n\r\n// PendingPromise接口定义\r\nexport interface PendingCallback {\r\n\tresolve : (data : any) => void;\r\n\treject : (err ?: any) => void;\r\n\ttimer ?: number;\r\n}\r\n\r\n// 蓝牙相关接口和类型定义\r\nexport type BleDevice = {\r\n\tdeviceId : string;\r\n\tname : string;\r\n\trssi ?: number;\r\n\tlastSeen ?: number; // 新增\r\n\t// 新增\r\n\tserviceId ?: string;\r\n\twriteCharId ?: string;\r\n\tnotifyCharId ?: string;\r\n}\r\n\r\n// BLE常规选项\r\nexport type BleOptions = {\r\n\ttimeout ?: number;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : any) => void;\r\n\tcomplete ?: () => void;\r\n}\r\n\r\nexport type BleConnectionState = number; // 0: DISCONNECTED, 1: CONNECTING, 2: CONNECTED, 3: DISCONNECTING\r\n\r\nexport type BleConnectOptionsExt = {\r\n\ttimeout ?: number;\r\n\tservices ?: string[];\r\n\trequireResponse ?: boolean;\r\n\tautoReconnect ?: boolean;\r\n\tmaxAttempts ?: number;\r\n\tinterval ?: number;\r\n};\r\n\r\n// 回调函数类型\r\nexport type BleDeviceFoundCallback = (device : BleDevice) => void;\r\nexport type BleConnectionStateChangeCallback = (deviceId : string, state : BleConnectionState) => void;\r\n\r\nexport type BleDataPayload = {\r\n\tdeviceId : string;\r\n\tserviceId ?: string;\r\n\tcharacteristicId ?: string;\r\n\tdata : string | ArrayBuffer;\r\n\tformat ?: number; // 0: JSON, 1: XML, 2: RAW\r\n}\r\n\r\nexport type BleDataSentCallback = (payload : BleDataPayload, success : boolean, error ?: BleError) => void;\r\nexport type BleErrorCallback = (error : BleError) => void;\r\n\r\n// 健康数据类型定义\r\nexport enum HealthDataType {\r\n\tHEART_RATE = 1,\r\n\tBLOOD_OXYGEN = 2,\r\n\tTEMPERATURE = 3,\r\n\tSTEP_COUNT = 4,\r\n\tSLEEP_DATA = 5,\r\n\tHEALTH_DATA = 6\r\n}\r\n\r\n// Platform-specific services should be imported from per-platform entrypoints\r\n// (e.g. './app-android/index.uts' or './web/index.uts').\r\n// Avoid re-exporting platform modules at the SDK root to prevent bundlers\r\n// Platform-specific services should be imported from per-platform entrypoints\r\n// (e.g. './app-android/index.uts' or './web/index.uts').\r\n// Avoid re-exporting platform modules at the SDK root to prevent bundlers\r\n// from pulling android.* symbols into web bundles.\r\n// If a typed ambient reference is required, declare the shape here instead of importing implementation.\r\n// Example lightweight typed placeholder (do not import platform code here):\r\n// export type BluetoothService = any; // platform-specific implementation exported from platform index files\r\n\r\n\r\n\r\n// ====== 新增多协议、统一事件、协议适配、状态管理支持 ======\r\nexport type BleProtocolType =\r\n\t| 'standard'\r\n\t| 'custom'\r\n\t| 'health'\r\n\t| 'ibeacon'\r\n\t| 'mesh';\r\n\r\nexport type BleEvent =\r\n\t| 'deviceFound'\r\n\t| 'scanFinished'\r\n\t| 'connectionStateChanged'\r\n\t| 'dataReceived'\r\n\t| 'dataSent'\r\n\t| 'error'\r\n\t| 'servicesDiscovered'\r\n\t| 'connected' // 新增\r\n\t| 'disconnected'; // 新增\r\n\r\n// 事件回调参数\r\nexport type BleEventPayload = {\r\n\tevent : BleEvent;\r\n\tdevice ?: BleDevice;\r\n\tprotocol ?: BleProtocolType;\r\n\tstate ?: BleConnectionState;\r\n\tdata ?: ArrayBuffer | string | object;\r\n\tformat ?: string;\r\n\terror ?: BleError;\r\n\textra ?: any;\r\n}\r\n\r\n// 事件回调函数\r\nexport type BleEventCallback = (payload : BleEventPayload) => void;\r\n\r\n// 多协议设备信息(去除交叉类型,直接展开字段)\r\nexport type MultiProtocolDevice = {\r\n\tdeviceId : string;\r\n\tname : string;\r\n\trssi ?: number;\r\n\tprotocol : BleProtocolType;\r\n};\r\n\r\nexport type ScanDevicesOptions = {\r\n\tprotocols ?: BleProtocolType[];\r\n\toptionalServices ?: string[];\r\n\ttimeout ?: number;\r\n\tonDeviceFound ?: (device : BleDevice) => void;\r\n\tonScanFinished ?: () => void;\r\n};\r\n// Named payload type used by sendData\r\nexport type SendDataPayload = {\r\n\tdeviceId : string;\r\n\tserviceId ?: string;\r\n\tcharacteristicId ?: string;\r\n\tdata : string | ArrayBuffer;\r\n\tformat ?: number;\r\n\tprotocol : BleProtocolType;\r\n}\r\n// 协议处理器接口(为 protocol-handler 适配器预留)\r\nexport type ScanHandler = {\r\n\tprotocol : BleProtocolType;\r\n\tscanDevices ?: (options : ScanDevicesOptions) => Promise;\r\n\tconnect : (device : BleDevice, options ?: BleConnectOptionsExt) => Promise;\r\n\tdisconnect : (device : BleDevice) => Promise;\r\n\t// Optional: send arbitrary data via the protocol's write characteristic\r\n\tsendData ?: (device : BleDevice, payload : SendDataPayload, options ?: BleOptions) => Promise;\r\n\t// Optional: try to connect and discover service/characteristic ids for this device\r\n\tautoConnect ?: (device : BleDevice, options ?: BleConnectOptionsExt) => Promise;\r\n\r\n}\r\n\r\n\r\n// 自动发现服务和特征返回类型\r\nexport type AutoBleInterfaces = {\r\n\tserviceId : string;\r\n\twriteCharId : string;\r\n\tnotifyCharId : string;\r\n}\r\nexport type ResponseCallbackEntry = {\r\n\tcb : (data : Uint8Array) => boolean | void;\r\n\tmulti : boolean;\r\n};\r\n\r\n// Result returned by a DFU control parser. Use a plain string `type` to keep\r\n// the generated Kotlin simple and avoid inline union types which the generator\r\n// does not handle well.\r\nexport type ControlParserResult = {\r\n\ttype : string; // e.g. 'progress', 'success', 'error', 'info'\r\n\tprogress ?: number;\r\n\terror ?: any;\r\n}\r\n\r\n// DFU types\r\nexport type DfuOptions = {\r\n\tmtu ?: number;\r\n\tuseNordic ?: boolean;\r\n\t// If true, the DFU upload will await a write response per-packet. Set false to use\r\n\t// WRITE_NO_RESPONSE (fire-and-forget) for higher throughput. Default: false.\r\n\twaitForResponse ?: boolean;\r\n\t// Maximum number of outstanding NO_RESPONSE writes to allow before throttling.\r\n\t// This implements a simple sliding window. Default: 32.\r\n\tmaxOutstanding ?: number;\r\n\t// Per-chunk sleep (ms) to yield to event loop / Android BLE stack. Default: 2.\r\n\twriteSleepMs ?: number;\r\n\t// Retry delay (ms) used by the Android write helper when gatt.writeCharacteristic\r\n\t// returns false. Smaller values can improve throughput on congested stacks.\r\n\twriteRetryDelayMs ?: number;\r\n\t// Maximum number of immediate write attempts before falling back to the give-up timeout.\r\n\twriteMaxAttempts ?: number;\r\n\t// Timeout (ms) to wait for a late onCharacteristicWrite callback after all retries fail.\r\n\twriteGiveupTimeoutMs ?: number;\r\n\t// Packet Receipt Notification (PRN) window size in packets. If set, DFU\r\n\t// manager will send a Set PRN command to the device and wait for PRN\r\n\t// notifications after this many packets. Default: 12.\r\n\tprn ?: number;\r\n\t// Timeout (ms) to wait for a PRN notification once the window is reached.\r\n\t// Default: 10000 (10s).\r\n\tprnTimeoutMs ?: number;\r\n\t// When true, disable PRN waits automatically after the first timeout to prevent\r\n\t// repeated long stalls on devices that do not send PRNs. Default: true.\r\n\tdisablePrnOnTimeout ?: boolean;\r\n\t// Time (ms) to wait for outstanding fire-and-forget writes to drain before issuing\r\n\t// the activate/validate control command. Default: 3000.\r\n\tdrainOutstandingTimeoutMs ?: number;\r\n\tcontrolTimeout ?: number;\r\n\tonProgress ?: (percent : number) => void;\r\n\tonLog ?: (message : string) => void;\r\n\tcontrolParser ?: (data : Uint8Array) => ControlParserResult | null;\r\n}\r\n\r\nexport type DfuManagerType = {\r\n\tstartDfu : (deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) => Promise;\r\n}\r\n\r\n// Lightweight runtime / UTS shims and missing types\r\n// These are conservative placeholders to satisfy typings used across platform files.\r\n// UTSJSONObject: bundler environments used by the build may not support\r\n// TypeScript-style index signatures in this .uts context. Use a conservative\r\n// 'any' alias so generated code doesn't rely on unsupported syntax while\r\n// preserving a usable type at the source level.\r\nexport type UTSJSONObject = any;\r\n\r\n// ByteArray / Int are used in the Android platform code to interop with Java APIs.\r\n// Define minimal aliases so source can compile. Runtime uses Uint8Array and number.\r\nexport type ByteArray = any; // runtime will use Java byte[] via UTS bridge; keep as any here\r\n\r\n// Callback types used by service_manager and index wrappers\r\nexport type BleDataReceivedCallback = (data: Uint8Array) => void;\r\nexport type BleScanResult = {\r\n\tdeviceId: string;\r\n\tname?: string;\r\n\trssi?: number;\r\n\tadvertising?: any;\r\n};\r\n\r\n// Minimal UI / framework placeholders (some files reference these in types only)\r\nexport type ComponentPublicInstance = any;\r\nexport type UniElement = any;\r\nexport type UniPage = any;\r\n\r\n// Platform service placeholder (actual implementation exported from platform index files)\r\n// Provide a lightweight, strongly-shaped class skeleton so source-level code\r\n// (and the code generator) can rely on concrete method names and signatures.\r\n// Implementations are platform-specific and exported from per-platform index\r\n// files (e.g. './app-android/index.uts' or './web/index.uts'). This class is\r\n// intentionally thin — it declares method signatures used across pages and\r\n// platform shims so the generator emits resolvable Kotlin symbols.\r\nexport class BluetoothService {\r\n\t// Event emitter style\r\n\ton(event: BleEvent | string, callback: BleEventCallback): void {}\r\n\toff(event: BleEvent | string, callback?: BleEventCallback): void {}\r\n\r\n\t// Scanning / discovery\r\n\tscanDevices(options?: ScanDevicesOptions): Promise { return Promise.resolve(); }\r\n\r\n\t// Connection management\r\n\tconnectDevice(deviceId: string, protocol?: string, options?: BleConnectOptionsExt): Promise { return Promise.resolve(); }\r\n\tdisconnectDevice(deviceId: string, protocol?: string): Promise { return Promise.resolve(); }\r\n\tgetConnectedDevices(): MultiProtocolDevice[] { return []; }\r\n\r\n\t// Services / characteristics\r\n\tgetServices(deviceId: string): Promise { return Promise.resolve([]); }\r\n\tgetCharacteristics(deviceId: string, serviceId: string): Promise { return Promise.resolve([]); }\r\n\r\n\t// Read / write / notify\r\n\treadCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(new ArrayBuffer(0)); }\r\n\twriteCharacteristic(deviceId: string, serviceId: string, characteristicId: string, value: Uint8Array | ArrayBuffer, options?: WriteCharacteristicOptions): Promise { return Promise.resolve(true); }\r\n\tsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, callback: BleNotifyCallback): Promise { return Promise.resolve(); }\r\n\tunsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(); }\r\n\r\n\t\t// Convenience helpers\r\n\t\tgetAutoBleInterfaces(deviceId: string): Promise {\r\n\t\t\tconst res: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' };\r\n\t\t\treturn Promise.resolve(res);\r\n\t\t}\r\n}\r\n\r\n// Runtime protocol handler base class. Exporting a concrete class ensures the\r\n// generator emits a resolvable runtime type that platform handlers can extend.\r\n// Source-level code can still use the ScanHandler type for typing.\r\n// Runtime ProtocolHandler is implemented in `protocol_handler.uts`.\r\n// Keep the public typing in this file minimal to avoid duplicate runtime\r\n// declarations. Consumers that need the runtime class should import it from\r\n// './protocol_handler.uts'.","// Minimal ProtocolHandler runtime class used by pages and components.\r\n// This class adapts the platform `BluetoothService` to a small protocol API\r\n// expected by pages: setConnectionParameters, initialize, testBatteryLevel,\r\n// testVersionInfo. Implemented conservatively to avoid heavy dependencies.\r\n\r\nimport type { BluetoothService, AutoBleInterfaces, AutoDiscoverAllResult, BleService, BleCharacteristic, BleProtocolType, BleDevice, ScanDevicesOptions, BleConnectOptionsExt, SendDataPayload, BleOptions } from './interface.uts'\r\n\r\nexport class ProtocolHandler {\r\n\t// bluetoothService may be omitted for lightweight wrappers; allow null\r\n\tbluetoothService: BluetoothService | null = null\r\n\tprotocol: BleProtocolType = 'standard'\r\n\tdeviceId: string | null = null\r\n\tserviceId: string | null = null\r\n\twriteCharId: string | null = null\r\n\tnotifyCharId: string | null = null\r\n\tinitialized: boolean = false\r\n\r\n\t// Accept an optional BluetoothService so wrapper subclasses can call\r\n\t// `super()` without forcing a runtime instance.\r\n\tconstructor(bluetoothService?: BluetoothService) {\r\n\t\tif (bluetoothService != null) this.bluetoothService = bluetoothService\r\n\t}\r\n\r\n\tsetConnectionParameters(deviceId: string, serviceId: string, writeCharId: string, notifyCharId: string) {\r\n\t\tthis.deviceId = deviceId\r\n\t\tthis.serviceId = serviceId\r\n\t\tthis.writeCharId = writeCharId\r\n\t\tthis.notifyCharId = notifyCharId\r\n\t}\r\n\r\n\t// initialize: optional setup, returns a Promise that resolves when ready\r\n\tasync initialize(): Promise {\r\n\t\t// Simple async initializer — keep implementation minimal and generator-friendly.\r\n\t\ttry {\r\n\t\t\t// If bluetoothService exposes any protocol-specific setup, call it here.\r\n\t\t\tthis.initialized = true\r\n\t\t\treturn\r\n\t\t} catch (e) {\r\n\t\t\tthrow e\r\n\t\t}\r\n\t}\r\n\r\n\t// Protocol lifecycle / operations — default no-ops so generated code has\r\n\t// concrete member references and platform-specific handlers can override.\r\n\tasync scanDevices(options?: ScanDevicesOptions): Promise { return; }\r\n\tasync connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return; }\r\n\tasync disconnect(device: BleDevice): Promise { return; }\r\n\tasync sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { return; }\r\n\tasync autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return { serviceId: '', writeCharId: '', notifyCharId: '' }; }\r\n\r\n\t// Example: testBatteryLevel will attempt to read the battery characteristic\r\n\t// if write/notify-based protocol is not available. Returns number percentage.\r\n\tasync testBatteryLevel(): Promise {\r\n\t\tif (this.deviceId == null) throw new Error('deviceId not set')\r\n\t\t// copy to local so Kotlin generator can smart-cast the value across awaits\r\n\t\tconst deviceId = this.deviceId\r\n\t\t// try reading standard Battery characteristic (180F -> 2A19)\r\n\t\tif (this.bluetoothService == null) throw new Error('bluetoothService not set')\r\n\t\tconst services = await this.bluetoothService.getServices(deviceId)\r\n\r\n\t\r\n\tlet found: BleService | null = null\r\n\t\tfor (let i = 0; i < services.length; i++) {\r\n\t\t\tconst s = services[i]\r\n\t\t\tconst uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null)\r\n\t\t\tconst uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : ''\r\n\t\t\tif (uuid.indexOf('180f') !== -1) { found = s; break }\r\n\t\t}\r\n\t\tif (found == null) {\r\n\t\t\t// fallback: if writeCharId exists and notify available use protocol (not implemented)\r\n\t\t\treturn 0\r\n\t\t}\r\n\tconst foundUuid = found!.uuid\r\n\tconst charsRaw = await this.bluetoothService.getCharacteristics(deviceId, foundUuid)\r\n\tconst chars: BleCharacteristic[] = charsRaw\r\n\tconst batChar = chars.find((c: BleCharacteristic) => ((c.properties != null && c.properties.read) || (c.uuid != null && ('' + c.uuid).toLowerCase().includes('2a19'))))\r\n\t\tif (batChar == null) return 0\r\n\tconst buf = await this.bluetoothService.readCharacteristic(deviceId, foundUuid, batChar.uuid)\r\n\t\tconst arr = new Uint8Array(buf)\r\n\t\tif (arr.length > 0) {\r\n\t\t\treturn arr[0]\r\n\t\t}\r\n\t\treturn 0\r\n\t}\r\n\r\n\t// testVersionInfo: try to read Device Information characteristics or return empty\r\n\tasync testVersionInfo(hw: boolean): Promise {\r\n\t\t// copy to local so Kotlin generator can smart-cast the value across awaits\r\n\t\tconst deviceId = this.deviceId\r\n\t\tif (deviceId == null) return ''\r\n\t\t// Device Information service 180A, characteristics: 2A26 (SW), 2A27 (HW) sometimes\r\n\t\tif (this.bluetoothService == null) return ''\r\n\t\tconst _services = await this.bluetoothService.getServices(deviceId)\r\n\t\tconst services2: BleService[] = _services \r\n\t\tlet found2: BleService | null = null\r\n\t\tfor (let i = 0; i < services2.length; i++) {\r\n\t\t\tconst s = services2[i]\r\n\t\t\tconst uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null)\r\n\t\t\tconst uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : ''\r\n\t\t\tif (uuid.indexOf('180a') !== -1) { found2 = s; break }\r\n\t\t}\r\n\t\tif (found2 == null) return ''\r\n\t\tconst _found2 = found2\r\n\t\tconst found2Uuid = _found2!.uuid\r\n\t\tconst chars = await this.bluetoothService.getCharacteristics(deviceId, found2Uuid)\r\n\t\tconst target = chars.find((c) => {\r\n\t\t\tconst id = ('' + c.uuid).toLowerCase()\r\n\t\t\tif (hw) return id.includes('2a27') || id.includes('hardware')\r\n\t\t\treturn id.includes('2a26') || id.includes('software')\r\n\t\t})\r\n\t\tif (target == null) return ''\r\n\tconst buf = await this.bluetoothService.readCharacteristic(deviceId, found2Uuid, target.uuid)\r\n\ttry { return new TextDecoder().decode(new Uint8Array(buf)) } catch (e) { return '' }\r\n\t}\r\n}\r\n","// Minimal error definitions used across the BLE module.\r\n// Keep this file small and avoid runtime dependencies; it's mainly for typing and\r\n// simple runtime error construction used by native platform code.\r\n\r\nexport enum AkBluetoothErrorCode {\r\n\tUnknownError = 0,\r\n\tDeviceNotFound = 1,\r\n\tServiceNotFound = 2,\r\n\tCharacteristicNotFound = 3,\r\n\tConnectionTimeout = 4,\r\n\tUnspecified = 99\r\n}\r\n\r\nexport class AkBleErrorImpl extends Error {\r\n\tpublic code: AkBluetoothErrorCode;\r\n\tpublic detail: any|null;\n\tconstructor(code: AkBluetoothErrorCode, message?: string, detail: any|null = null) {\r\n\t\tsuper(message ?? AkBleErrorImpl.defaultMessage(code));\r\n\t\tthis.name = 'AkBleError';\r\n\t\tthis.code = code;\r\n\t\tthis.detail = detail;\r\n\t}\r\n\tstatic defaultMessage(code: AkBluetoothErrorCode) {\r\n\t\tswitch (code) {\r\n\t\t\tcase AkBluetoothErrorCode.DeviceNotFound: return 'Device not found';\r\n\t\t\tcase AkBluetoothErrorCode.ServiceNotFound: return 'Service not found';\r\n\t\t\tcase AkBluetoothErrorCode.CharacteristicNotFound: return 'Characteristic not found';\r\n\t\t\tcase AkBluetoothErrorCode.ConnectionTimeout: return 'Connection timed out';\r\n\t\t\tcase AkBluetoothErrorCode.UnknownError: default: return 'Unknown Bluetooth error';\r\n\t\t}\r\n\t}\r\n}\r\n\r\nexport default AkBleErrorImpl;\r\n","import type {\r\n\tBleDevice,\r\n\tBleConnectionState,\r\n\tBleEvent,\r\n\tBleEventCallback,\r\n\tBleEventPayload,\r\n\tBleScanResult,\r\n\tBleConnectOptionsExt,\r\n\tAutoBleInterfaces,\r\n\tBleDataPayload,\r\n\tSendDataPayload,\r\n\tBleOptions,\r\n\tMultiProtocolDevice,\r\n\tScanHandler,\r\n\tBleProtocolType,\r\n\tScanDevicesOptions\r\n} from '../interface.uts';\r\nimport { ProtocolHandler } from '../protocol_handler.uts';\r\nimport { BluetoothService } from '../interface.uts';\r\nimport { DeviceManager } from './device_manager.uts';\r\n\r\n// Shape used when callers register plain objects as handlers. Using a named\r\n// type keeps member access explicit so the code generator emits valid Kotlin\r\n// member references instead of trying to access properties on Any.\r\ntype RawProtocolHandler = {\r\n\tprotocol?: BleProtocolType;\r\n\tscanDevices?: (options?: ScanDevicesOptions) => Promise;\r\n\tconnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise;\r\n\tdisconnect?: (device: BleDevice) => Promise;\r\n\tsendData?: (device: BleDevice, payload?: SendDataPayload, options?: BleOptions) => Promise;\r\n\tautoConnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise;\r\n}\r\n\r\n// 设备上下文\r\nclass DeviceContext {\r\n\tdevice : BleDevice;\r\n\tprotocol : BleProtocolType;\r\n\tstate : BleConnectionState;\r\n\thandler : ProtocolHandler;\r\n\tconstructor(device : BleDevice, protocol : BleProtocolType, handler : ProtocolHandler) {\r\n\t\tthis.device = device;\r\n\t\tthis.protocol = protocol;\r\n\t\tthis.state = 0; // DISCONNECTED\r\n\t\tthis.handler = handler;\r\n\t}\r\n}\r\n\r\nconst deviceMap = new Map(); // key: deviceId|protocol\r\n// Single active protocol handler (no multi-protocol registration)\r\nlet activeProtocol: BleProtocolType = 'standard';\r\nlet activeHandler: ProtocolHandler | null = null;\r\n// 事件监听注册表\r\nconst eventListeners = new Map>();\r\n\r\nfunction emit(event : BleEvent, payload : BleEventPayload) {\r\n\tif (event === 'connectionStateChanged') {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:57','[AKBLE][LOG] bluetooth_manager.uts emit connectionStateChanged', payload)\r\n\t}\r\n\tconst listeners = eventListeners.get(event);\r\n\tif (listeners != null) {\r\n\t\tlisteners.forEach(cb => {\r\n\t\t\ttry { cb(payload); } catch (e) { }\r\n\t\t});\r\n\t}\r\n}\r\nclass ProtocolHandlerWrapper extends ProtocolHandler {\r\n\tprivate _raw: RawProtocolHandler | null;\r\n\tconstructor(raw?: RawProtocolHandler) {\r\n\t\t// pass a lightweight BluetoothService instance to satisfy generators\r\n\t\tsuper(new BluetoothService());\r\n\t\tthis._raw = (raw != null) ? raw : null;\r\n\t}\r\n\toverride async scanDevices(options?: ScanDevicesOptions): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.scanDevices === 'function') {\r\n\t\t\tawait rawTyped.scanDevices(options);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.connect === 'function') {\r\n\t\t\tawait rawTyped.connect(device, options);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async disconnect(device: BleDevice): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.disconnect === 'function') {\r\n\t\t\tawait rawTyped.disconnect(device);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.sendData === 'function') {\r\n\t\t\tawait rawTyped.sendData(device, payload, options);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.autoConnect === 'function') {\r\n\t\t\treturn await rawTyped.autoConnect(device, options);\r\n\t\t}\r\n\t\treturn { serviceId: '', writeCharId: '', notifyCharId: '' };\r\n\t}\r\n}\r\n\r\n// Strong runtime detector for plain object handlers (no Type Predicate)\r\n// Note: the UTS bundler doesn't support TypeScript type predicates (x is T),\r\n// and it doesn't accept the 'unknown' type. This returns a boolean and\r\n// callers must cast the value to RawProtocolHandler after the function\r\n// returns true.\r\nfunction isRawProtocolHandler(x: any): boolean {\r\n\tif (x == null || typeof x !== 'object') return false;\r\n\tconst r = x as Record;\r\n\tif (typeof r['scanDevices'] === 'function') return true;\r\n\tif (typeof r['connect'] === 'function') return true;\r\n\tif (typeof r['disconnect'] === 'function') return true;\r\n\tif (typeof r['sendData'] === 'function') return true;\r\n\tif (typeof r['autoConnect'] === 'function') return true;\r\n\tif (typeof r['protocol'] === 'string') return true;\r\n\treturn false;\r\n}\r\n\r\nexport const registerProtocolHandler = (handler : any) => {\r\n\tif (handler == null) return;\r\n\t// Determine protocol value defensively. Default to 'standard' when unknown.\r\n\tlet proto: BleProtocolType = 'standard';\r\n\tif (handler instanceof ProtocolHandler) {\r\n\t\ttry { proto = (handler as ProtocolHandler).protocol as BleProtocolType; } catch (e) { }\r\n\t\tactiveHandler = handler as ProtocolHandler;\r\n\t} else if (isRawProtocolHandler(handler)) {\r\n\t\ttry { proto = (handler as RawProtocolHandler).protocol as BleProtocolType; } catch (e) { }\r\n\t\tactiveHandler = new ProtocolHandlerWrapper(handler as RawProtocolHandler);\r\n\t\t(activeHandler as ProtocolHandler).protocol = proto;\r\n\t} else {\r\n\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:139','[AKBLE] registerProtocolHandler: unsupported handler type, ignoring', handler);\r\n\t\treturn;\r\n\t}\r\n\tactiveProtocol = proto;\r\n}\r\n\r\n\r\nexport const scanDevices = async (options ?: ScanDevicesOptions) : Promise => {\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:147','[AKBLE] start scan', options)\r\n\t// Determine which protocols to run: either user-specified or all registered\r\n\t// Single active handler flow\r\n\tif (activeHandler == null) {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:151','[AKBLE] no active scan handler registered')\r\n\t\treturn\r\n\t}\r\n\tconst handler = activeHandler as ProtocolHandler;\r\n\tconst scanOptions : ScanDevicesOptions = {\r\n\t\tonDeviceFound: (device : BleDevice) => emit('deviceFound', { event: 'deviceFound', device }),\r\n\t\tonScanFinished: () => emit('scanFinished', { event: 'scanFinished' })\r\n\t}\r\n\ttry {\r\n\t\tawait handler.scanDevices(scanOptions)\r\n\t} catch (e) {\r\n\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:162','[AKBLE] scanDevices handler error', e)\r\n\t}\r\n}\r\n\r\n\r\nexport const connectDevice = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => {\r\n\tconst handler = activeHandler;\r\n\tif (handler == null) throw new Error('No protocol handler');\r\n\tconst device : BleDevice = { deviceId, name: '', rssi: 0 }; // 可扩展\r\n\tawait handler.connect(device, options);\r\n\tconst ctx = new DeviceContext(device, protocol, handler);\r\n\tctx.state = 2; // CONNECTED\r\n\tdeviceMap.set(getDeviceKey(deviceId, protocol), ctx);\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:175',deviceMap)\r\n\temit('connectionStateChanged', { event: 'connectionStateChanged', device, protocol, state: 2 });\r\n}\r\n\r\nexport const disconnectDevice = async (deviceId : string, protocol : BleProtocolType) : Promise => {\r\n\tconst ctx = deviceMap.get(getDeviceKey(deviceId, protocol));\r\n\tif (ctx == null || ctx.handler == null) return;\r\n\tawait ctx.handler.disconnect(ctx.device);\r\n\tctx.state = 0;\r\n\temit('connectionStateChanged', { event: 'connectionStateChanged', device: ctx.device, protocol, state: 0 });\r\n\tdeviceMap.delete(getDeviceKey(deviceId, protocol));\r\n}\r\nexport const sendData = async (payload : SendDataPayload, options ?: BleOptions) : Promise => {\r\n\tconst ctx = deviceMap.get(getDeviceKey(payload.deviceId, payload.protocol));\r\n\tif (ctx == null) throw new Error('Device not connected');\r\n\t// copy to local non-null variable so generator can smart-cast across awaits\r\n\tconst deviceCtx = ctx as DeviceContext;\r\n\tif (deviceCtx.handler == null) throw new Error('sendData not supported for this protocol');\r\n\tawait deviceCtx.handler.sendData(deviceCtx.device, payload, options);\r\n\temit('dataSent', { event: 'dataSent', device: deviceCtx.device, protocol: payload.protocol, data: payload.data });\r\n}\r\n\r\nexport const getConnectedDevices = () : MultiProtocolDevice[] => {\r\n\tconst result : MultiProtocolDevice[] = [];\r\n\tdeviceMap.forEach((ctx : DeviceContext) => {\r\n\t\tconst dev : MultiProtocolDevice = {\r\n\t\t\tdeviceId: ctx.device.deviceId,\r\n\t\t\tname: ctx.device.name,\r\n\t\t\trssi: ctx.device.rssi,\r\n\t\t\tprotocol: ctx.protocol\r\n\t\t};\r\n\t\tresult.push(dev);\r\n\t});\r\n\treturn result;\r\n}\r\n\r\nexport const getConnectionState = (deviceId : string, protocol : BleProtocolType) : BleConnectionState => {\r\n\tconst ctx = deviceMap.get(getDeviceKey(deviceId, protocol));\r\n\tif (ctx == null) return 0;\r\n\treturn ctx.state;\r\n}\r\n\r\nexport const on = (event : BleEvent, callback : BleEventCallback) => {\r\n\tif (!eventListeners.has(event)) eventListeners.set(event, new Set());\r\n\teventListeners.get(event)!.add(callback);\r\n}\r\n\r\nexport const off = (event : BleEvent, callback ?: BleEventCallback) => {\r\n\tif (callback == null) {\r\n\t\teventListeners.delete(event);\r\n\t} else {\r\n\t\teventListeners.get(event)?.delete(callback as BleEventCallback);\r\n\t}\r\n}\r\n\r\nfunction getDeviceKey(deviceId : string, protocol : BleProtocolType) : string {\r\n\treturn `${deviceId}|${protocol}`;\r\n}\r\n\r\nexport const autoConnect = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => {\r\n\tconst handler = activeHandler;\r\n\tif (handler == null) throw new Error('autoConnect not supported for this protocol');\r\n\tconst device : BleDevice = { deviceId, name: '', rssi: 0 };\r\n\t// safe call - handler.autoConnect exists on ProtocolHandler\r\n\treturn await handler.autoConnect(device, options) as AutoBleInterfaces;\r\n}\r\n\r\n// Ensure there is at least one handler registered so callers can scan/connect\r\n// without needing to import a registry module. This creates a minimal default\r\n// ProtocolHandler backed by a BluetoothService instance.\r\ntry {\r\n\tif (activeHandler == null) {\r\n\t\t// Create a DeviceManager-backed raw handler that delegates to native code\r\n\t\tconst _dm = DeviceManager.getInstance();\r\n\t\tconst _raw: RawProtocolHandler = {\r\n\t\t\tprotocol: 'standard',\r\n\t\t\tscanDevices: (options?: ScanDevicesOptions) => {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst scanOptions = options != null ? options : {} as ScanDevicesOptions;\r\n\t\t\t\t\t_dm.startScan(scanOptions);\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:256','[AKBLE] DeviceManager.startScan failed', e);\r\n\t\t\t\t}\r\n\t\t\t\treturn Promise.resolve();\r\n\t\t\t},\r\n\t\t\tconnect: (device, options?: BleConnectOptionsExt) => {\r\n\t\t\t\treturn _dm.connectDevice(device.deviceId, options);\r\n\t\t\t},\r\n\t\t\tdisconnect: (device) => {\r\n\t\t\t\treturn _dm.disconnectDevice(device.deviceId);\r\n\t\t\t},\r\n\t\t\tautoConnect: (device, options?: any) => {\r\n\t\t\t\t// DeviceManager does not provide an autoConnect helper; return default\r\n\t\t\t\tconst result: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' };\r\n\t\t\t\treturn Promise.resolve(result);\r\n\t\t\t}\r\n\t\t};\r\n\t\tconst _wrapper = new ProtocolHandlerWrapper(_raw);\r\n\t\tactiveHandler = _wrapper;\r\n\t\tactiveProtocol = _raw.protocol as BleProtocolType;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:275','[AKBLE] default protocol handler (BluetoothService-backed) registered', activeProtocol);\r\n\t}\r\n} catch (e) {\r\n\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:278','[AKBLE] failed to register default protocol handler', e);\r\n}","import * as BluetoothManager from './bluetooth_manager.uts';\r\nimport { ServiceManager } from './service_manager.uts';\r\nimport type { ScanDevicesOptions, BleConnectOptionsExt, MultiProtocolDevice, BleEvent, BleEventCallback, BleService, BleCharacteristic, WriteCharacteristicOptions, AutoBleInterfaces, BleDataReceivedCallback } from '../interface.uts';\r\nimport { DeviceManager } from './device_manager.uts';\r\n\r\nconst serviceManager = ServiceManager.getInstance();\r\n\r\nexport class BluetoothService {\r\n scanDevices(options?: ScanDevicesOptions) { return BluetoothManager.scanDevices(options); }\r\n connectDevice(deviceId: string, protocol: string, options?: BleConnectOptionsExt) { return BluetoothManager.connectDevice(deviceId, protocol, options); }\r\n disconnectDevice(deviceId: string, protocol: string) { return BluetoothManager.disconnectDevice(deviceId, protocol); }\r\n getConnectedDevices(): MultiProtocolDevice[] { return BluetoothManager.getConnectedDevices(); }\r\n on(event: BleEvent, callback: BleEventCallback) { return BluetoothManager.on(event, callback); }\r\n off(event: BleEvent, callback?: BleEventCallback) { return BluetoothManager.off(event, callback); }\r\n getServices(deviceId: string): Promise {\r\n return new Promise((resolve, reject) => {\r\n serviceManager.getServices(deviceId, (list, err) => {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:18','getServices:', list, err); // 新增日志\r\n if (err != null) reject(err);\r\n else resolve((list as BleService[]) ?? []);\r\n });\r\n });\r\n }\r\n getCharacteristics(deviceId: string, serviceId: string): Promise {\r\n return new Promise((resolve, reject) => {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:26',deviceId,serviceId)\r\n serviceManager.getCharacteristics(deviceId, serviceId, (list, err) => {\r\n if (err != null) reject(err);\r\n else resolve((list as BleCharacteristic[]) ?? []);\r\n });\r\n });\r\n }\r\n /**\r\n * 自动发现服务和特征,返回可用的写入和通知特征ID\r\n * @param deviceId 设备ID\r\n * @returns {Promise}\r\n */\r\n async getAutoBleInterfaces(deviceId: string): Promise {\r\n // 1. 获取服务列表\r\n const services = await this.getServices(deviceId);\r\n if (services == null || services.length == 0) throw new Error('未发现服务');\r\n\r\n // 2. 选择目标服务(优先bae前缀,可根据需要调整)\r\n let serviceId = '';\r\n for (let i = 0; i < services.length; i++) {\r\n const s = services[i];\r\n const uuidCandidate: string | null = (s.uuid != null ? s.uuid : null)\r\n const uuid: string = uuidCandidate != null ? uuidCandidate : ''\r\n // prefer regex test to avoid nullable receiver calls in generated Kotlin\r\n if (/^bae/i.test(uuid)) {\r\n serviceId = uuid\r\n break;\r\n }\r\n }\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:55',serviceId)\r\n if (serviceId == null || serviceId == '') serviceId = services[0].uuid;\r\n\r\n // 3. 获取特征列表\r\n const characteristics = await this.getCharacteristics(deviceId, serviceId);\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:60',characteristics)\r\n if (characteristics == null || characteristics.length == 0) throw new Error('未发现特征值');\r\n\r\n // 4. 筛选write和notify特征\r\n let writeCharId = '';\r\n let notifyCharId = '';\r\n for (let i = 0; i < characteristics.length; i++) {\r\n\t\t\r\n const c = characteristics[i];\r\n\t __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:69',c)\r\n if ((writeCharId == null || writeCharId == '') && c.properties != null && (c.properties.write || c.properties.writeWithoutResponse==true)) writeCharId = c.uuid;\r\n if ((notifyCharId == null || notifyCharId == '') && c.properties != null && (c.properties.notify || c.properties.indicate)) notifyCharId = c.uuid;\r\n }\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:73',serviceId, writeCharId, notifyCharId);\r\n if ((writeCharId == null || writeCharId == '') || (notifyCharId == null || notifyCharId == '')) throw new Error('未找到合适的写入或通知特征');\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:75',serviceId, writeCharId, notifyCharId);\r\n // // 发现服务和特征后\r\n\tconst deviceManager = DeviceManager.getInstance();\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:78',deviceManager);\r\n const device = deviceManager.getDevice(deviceId);\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:80',deviceId,device)\r\n device!.serviceId = serviceId;\r\n device!.writeCharId = writeCharId;\r\n device!.notifyCharId = notifyCharId;\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:84',device);\r\n return { serviceId, writeCharId, notifyCharId };\r\n }\r\n async subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, onData: BleDataReceivedCallback): Promise {\r\n return serviceManager.subscribeCharacteristic(deviceId, serviceId, characteristicId, onData);\r\n }\r\n async readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise {\r\n return serviceManager.readCharacteristic(deviceId, serviceId, characteristicId);\r\n }\r\n async writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, data: Uint8Array, options?: WriteCharacteristicOptions): Promise {\r\n return serviceManager.writeCharacteristic(deviceId, serviceId, characteristicId, data, options);\r\n }\r\n async unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise {\r\n return serviceManager.unsubscribeCharacteristic(deviceId, serviceId, characteristicId);\r\n }\r\n async autoDiscoverAll(deviceId: string): Promise {\r\n return serviceManager.autoDiscoverAll(deviceId);\r\n }\r\n async subscribeAllNotifications(deviceId: string, onData: BleDataReceivedCallback): Promise {\r\n return serviceManager.subscribeAllNotifications(deviceId, onData);\r\n }\r\n}\r\n\r\nexport const bluetoothService = new BluetoothService();\r\n\r\n// Ensure protocol handlers are registered when this module is imported.\r\n // import './protocol_registry.uts';\r\n","import { BleService } from '../interface.uts'\r\nimport type { WriteCharacteristicOptions, DfuOptions, ControlParserResult } from '../interface.uts'\r\nimport { DeviceManager } from './device_manager.uts'\r\nimport { ServiceManager } from './service_manager.uts'\r\nimport BluetoothGatt from 'android.bluetooth.BluetoothGatt'\r\nimport BluetoothGattCharacteristic from 'android.bluetooth.BluetoothGattCharacteristic'\r\nimport BluetoothGattDescriptor from 'android.bluetooth.BluetoothGattDescriptor'\r\nimport UUID from 'java.util.UUID'\r\n\r\n// 通用 Nordic DFU UUIDs (常见设备可能使用这些;如厂商自定义请替换)\r\nconst DFU_SERVICE_UUID = '0000fe59-0000-1000-8000-00805f9b34fb'\r\nconst DFU_CONTROL_POINT_UUID = '8ec90001-f315-4f60-9fb8-838830daea50'\r\nconst DFU_PACKET_UUID = '8ec90002-f315-4f60-9fb8-838830daea50'\r\n\r\ntype DfuSession = {\r\n\tresolve : () => void;\r\n\treject : (err ?: any) => void;\r\n\tonProgress ?: (p : number) => void;\r\n\tonLog ?: (s : string) => void;\r\n\tcontrolParser ?: (data : Uint8Array) => ControlParserResult | null;\r\n\t// Nordic 专用字段\r\n\tbytesSent ?: number;\r\n\ttotalBytes ?: number;\r\n\tuseNordic ?: boolean;\r\n\t// PRN (packet receipt notification) support\r\n\tprn ?: number;\r\n\tpacketsSincePrn ?: number;\r\n\tprnResolve ?: () => void;\r\n\tprnReject ?: (err ?: any) => void;\r\n}\r\n\r\n\r\n\r\nexport class DfuManager {\r\n\t// 会话表,用于把 control-point 通知路由到当前 DFU 流程\r\n\tprivate sessions : Map = new Map();\r\n\r\n\t// 简化:只实现最基本的 GATT-based DFU 上传逻辑,需按设备协议调整 control point 的命令/解析\r\n\r\n\t// Emit a DFU lifecycle event for a session. name should follow Nordic listener names\r\n\tprivate _emitDfuEvent(deviceId : string, name : string, payload ?: any) {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:42','[DFU][Event]', name, deviceId, payload ?? '');\r\n\t\tconst s = this.sessions.get(deviceId);\r\n\t\tif (s == null) return;\r\n\t\tif (typeof s.onLog == 'function') {\r\n\t\t\ttry {\r\n\t\t\t\tconst logFn = s.onLog as (msg : string) => void;\r\n\t\t\t\tlogFn(`[${name}] ${payload != null ? JSON.stringify(payload) : ''}`);\r\n\t\t\t} catch (e) { }\r\n\t\t}\r\n\t\tif (name == 'onProgress' && typeof s.onProgress == 'function' && typeof payload == 'number') {\r\n\t\t\ttry { s.onProgress(payload); } catch (e) { }\r\n\t\t}\r\n\t}\r\n\r\n\tasync startDfu(deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) : Promise {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:57','startDfu 0')\r\n\t\tconst deviceManager = DeviceManager.getInstance();\r\n\t\tconst serviceManager = ServiceManager.getInstance();\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:60','startDfu 1')\r\n\t\tconst gatt : BluetoothGatt | null = deviceManager.getGattInstance(deviceId);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:62','startDfu 2')\r\n\t\tif (gatt == null) throw new Error('Device not connected');\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:64','[DFU] startDfu start deviceId=', deviceId, 'firmwareBytes=', firmwareBytes != null ? firmwareBytes.length : 0, 'options=', options);\r\n\t\ttry {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:66','[DFU] requesting high connection priority for', deviceId);\r\n\t\t\tgatt.requestConnectionPriority(BluetoothGatt.CONNECTION_PRIORITY_HIGH);\r\n\t\t} catch (e) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:69','[DFU] requestConnectionPriority failed', e);\r\n\t\t}\r\n\r\n\t\t// 发现服务并特征\r\n\t\t// ensure services discovered before accessing GATT; serviceManager exposes Promise-based API\r\n\t\tawait serviceManager.getServices(deviceId, null);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:75','[DFU] services ensured for', deviceId);\r\n\t\tconst dfuService = gatt.getService(UUID.fromString(DFU_SERVICE_UUID));\r\n\t\tif (dfuService == null) throw new Error('DFU service not found');\r\n\t\tconst controlChar = dfuService.getCharacteristic(UUID.fromString(DFU_CONTROL_POINT_UUID));\r\n\t\tconst packetChar = dfuService.getCharacteristic(UUID.fromString(DFU_PACKET_UUID));\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:80','[DFU] dfuService=', dfuService != null ? dfuService.getUuid().toString() : null, 'controlChar=', controlChar != null ? controlChar.getUuid().toString() : null, 'packetChar=', packetChar != null ? packetChar.getUuid().toString() : null);\r\n\t\tif (controlChar == null || packetChar == null) throw new Error('DFU characteristics missing');\r\n\t\tconst packetProps = packetChar.getProperties();\r\n\t\tconst supportsWriteWithResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE) != 0;\r\n\t\tconst supportsWriteNoResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) != 0;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:85','[DFU] packet characteristic props mask=', packetProps, 'supportsWithResponse=', supportsWriteWithResponse, 'supportsNoResponse=', supportsWriteNoResponse);\r\n\r\n\t// Allow caller to request a desired MTU via options for higher throughput\r\n\tconst desiredMtu = (options != null && typeof options.mtu == 'number') ? options.mtu : 247;\r\n\t\ttry {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:90','[DFU] requesting MTU=', desiredMtu, 'for', deviceId);\r\n\t\t\tawait this._requestMtu(gatt, desiredMtu, 8000);\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:92','[DFU] requestMtu completed for', deviceId);\r\n\t\t} catch (e) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:94','[DFU] requestMtu failed or timed out, continue with default.', e);\r\n\t\t}\r\n\t\tconst mtu = desiredMtu; // 假定成功或使用期望值\r\n\tconst chunkSize = Math.max(20, mtu - 3);\r\n\r\n\t\t// small helper to convert a byte (possibly signed) to a two-digit hex string\r\n\t\tconst byteToHex = (b : number) => {\r\n\t\t\tconst v = (b < 0) ? (b + 256) : b;\r\n\t\t\tlet s = v.toString(16);\r\n\t\t\tif (s.length < 2) s = '0' + s;\r\n\t\t\treturn s;\r\n\t\t};\r\n\r\n\t// Parameterize PRN window and timeout via options early so they are available\r\n\t\t// for session logging. Defaults: prn = 12 packets, prnTimeoutMs = 10000 ms\r\n\t\tlet prnWindow = 0;\r\n\t\tif (options != null && typeof options.prn == 'number') {\r\n\t\t\tprnWindow = Math.max(0, Math.floor(options.prn));\r\n\t\t}\r\n\t\tconst prnTimeoutMs = (options != null && typeof options.prnTimeoutMs == 'number') ? Math.max(1000, Math.floor(options.prnTimeoutMs)) : 8000;\r\n\t\tconst disablePrnOnTimeout = !(options != null && options.disablePrnOnTimeout == false);\r\n\r\n\t\t// 订阅 control point 通知并将通知路由到会话处理器\r\n\t\tconst controlHandler = (data : Uint8Array) => {\r\n\t\t\t// 交给会话处理器解析并触发事件\r\n\t\t\ttry {\r\n\t\t\t\tconst hexParts: string[] = [];\r\n\t\t\t\tfor (let i = 0; i < data.length; i++) {\r\n\t\t\t\t\tconst v = data[i] as number;\r\n\t\t\t\t\thexParts.push(byteToHex(v));\r\n\t\t\t\t}\r\n\t\t\t\tconst hex = hexParts.join(' ');\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:126','[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data), 'hex=', hex);\r\n\t\t\t} catch (e) {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:128','[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data));\r\n\t\t\t}\r\n\t\t\tthis._handleControlNotification(deviceId, data);\r\n\t\t};\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:132','[DFU] subscribing control point for', deviceId);\r\n\t\tawait serviceManager.subscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, controlHandler);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:134','[DFU] subscribeCharacteristic returned for', deviceId);\r\n\r\n\t\t// 保存会话回调(用于 waitForControlEvent); 支持 Nordic 模式追踪已发送字节\r\n\t\tthis.sessions.set(deviceId, {\r\n\t\t\tresolve: () => { },\r\n\t\t\treject: (err ?: any) => {__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:139',err) },\r\n\t\t\tonProgress: null,\r\n\t\t\tonLog: null,\r\n\t\t\tcontrolParser: (data : Uint8Array) => this._defaultControlParser(data),\r\n\t\t\tbytesSent: 0,\r\n\t\t\ttotalBytes: firmwareBytes.length,\r\n\t\t\tuseNordic: options != null && options.useNordic == true,\r\n\t\t\tprn: null,\r\n\t\t\tpacketsSincePrn: 0,\r\n\t\t\tprnResolve: null,\r\n\t\t\tprnReject: null\r\n\t\t});\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:151','[DFU] session created for', deviceId, 'totalBytes=', firmwareBytes.length);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:152','[DFU] DFU session details:', { deviceId: deviceId, totalBytes: firmwareBytes.length, chunkSize: chunkSize, prnWindow: prnWindow, prnTimeoutMs: prnTimeoutMs });\r\n\r\n\t\t// wire options callbacks into the session (if provided)\r\n\t\tconst sessRef = this.sessions.get(deviceId);\r\n\t\tif (sessRef != null) {\r\n\t\t\tsessRef.onProgress = (options != null && typeof options.onProgress == 'function') ? options.onProgress : null;\r\n\t\t\tsessRef.onLog = (options != null && typeof options.onLog == 'function') ? options.onLog : null;\r\n\t\t}\r\n\r\n\t\t// emit initial lifecycle events (Nordic-like)\r\n\tthis._emitDfuEvent(deviceId, 'onDeviceConnecting', null);\r\n\r\n\t\t// 写入固件数据(非常保守的实现:逐包写入并等待短延迟)\r\n\t\t// --- PRN setup (optional, Nordic-style flow) ---\r\n\t\t// Parameterize PRN window and timeout via options: options.prn, options.prnTimeoutMs\r\n\t\t// Defaults were set earlier; build PRN payload using arithmetic to avoid\r\n\t\t// bitwise operators which don't map cleanly to generated Kotlin.\r\n\t\tif (prnWindow > 0) {\r\n\t\t\ttry {\r\n\t\t\t\t// send Set PRN to device (format: [OP_CODE_SET_PRN, prn LSB, prn MSB])\r\n\t\t\t\t// WARNING: Ensure your device uses the same opcode/format; change if needed.\r\n\t\t\t\tconst prnLsb = prnWindow % 256;\r\n\t\t\t\tconst prnMsb = Math.floor(prnWindow / 256) % 256;\r\n\t\t\t\tconst prnPayload = new Uint8Array([0x02, prnLsb, prnMsb]);\r\n\t\t\t\tawait serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, prnPayload, null);\r\n\t\t\t\tconst sess0 = this.sessions.get(deviceId);\r\n\t\t\t\tif (sess0 != null) {\r\n\t\t\t\t\tsess0.useNordic = true;\r\n\t\t\t\t\tsess0.prn = prnWindow;\r\n\t\t\t\t\tsess0.packetsSincePrn = 0;\r\n\t\t\t\t\tsess0.controlParser = (data : Uint8Array) => this._nordicControlParser(data);\r\n\t\t\t\t}\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:184','[DFU] Set PRN sent (prn=', prnWindow, ') for', deviceId);\r\n\t\t\t} catch (e) {\r\n\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:186','[DFU] Set PRN failed (continuing without PRN):', e);\r\n\t\t\t\tconst sessFallback = this.sessions.get(deviceId);\r\n\t\t\t\tif (sessFallback != null) sessFallback.prn = 0;\r\n\t\t\t}\r\n\t\t} else {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:191','[DFU] PRN disabled (prnWindow=', prnWindow, ') for', deviceId);\r\n\t\t}\r\n\r\n\t// 写入固件数据(逐包写入并根据 options.waitForResponse 选择是否等待响应)\r\n\t\tlet offset = 0;\r\n\t\tconst total = firmwareBytes.length;\r\n\tthis._emitDfuEvent(deviceId, 'onDfuProcessStarted', null);\r\n\tthis._emitDfuEvent(deviceId, 'onUploadingStarted', null);\r\n\t\t// Track outstanding write operations when using fire-and-forget mode so we can\r\n\t\t// log and throttle if the Android stack becomes overwhelmed.\r\n\t\tlet outstandingWrites = 0;\r\n\t\t// read tuning parameters from options in a safe, generator-friendly way\r\n\t\tlet configuredMaxOutstanding = 2;\r\n\t\tlet writeSleepMs = 0;\r\n\t\tlet writeRetryDelay = 100;\r\n\t\tlet writeMaxAttempts = 12;\r\n\t\tlet writeGiveupTimeout = 60000;\r\n\t\tlet drainOutstandingTimeout = 3000;\r\n\t\tlet failureBackoffMs = 0;\r\n\r\n\t\t// throughput measurement\r\n\t\tlet throughputWindowBytes = 0;\r\n\t\tlet lastThroughputTime = Date.now();\r\n\t\tfunction _logThroughputIfNeeded(force ?: boolean) {\r\n\t\t\ttry {\r\n\t\t\t\tconst now = Date.now();\r\n\t\t\t\tconst elapsed = now - lastThroughputTime;\r\n\t\t\t\tif (force == true || elapsed >= 1000) {\r\n\t\t\t\t\tconst bytes = throughputWindowBytes;\r\n\t\t\t\t\tconst bps = Math.floor((bytes * 1000) / Math.max(1, elapsed));\r\n\t\t\t\t\t// reset window\r\n\t\t\t\t\tthroughputWindowBytes = 0;\r\n\t\t\t\t\tlastThroughputTime = now;\r\n\t\t\t\t\tconst human = `${bps} B/s`;\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:225','[DFU] throughput:', human, 'elapsedMs=', elapsed);\r\n\t\t\t\t\tconst s = this.sessions.get(deviceId);\r\n\t\t\t\t\tif (s != null && typeof s.onLog == 'function') {\r\n\t\t\t\t\t\ttry { s.onLog?.invoke('[DFU] throughput: ' + human); } catch (e) { }\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t}\r\n\r\n\t\tfunction _safeErr(e ?: any) {\r\n\t\t\ttry {\r\n\t\t\t\tif (e == null) return '';\r\n\t\t\t\tif (typeof e == 'string') return e;\r\n\t\t\t\ttry { return JSON.stringify(e); } catch (e2) { }\r\n\t\t\t\ttry { return (e as any).toString(); } catch (e3) { }\r\n\t\t\t\treturn '';\r\n\t\t\t} catch (e4) { return ''; }\r\n\t\t}\r\n\t\ttry {\r\n\t\t\tif (options != null) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.maxOutstanding != null) {\r\n\t\t\t\t\t\tconst parsed = Math.floor(options.maxOutstanding as number);\r\n\t\t\t\t\t\tif (!isNaN(parsed) && parsed > 0) configuredMaxOutstanding = parsed;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeSleepMs != null) {\r\n\t\t\t\t\t\tconst parsedWs = Math.floor(options.writeSleepMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedWs) && parsedWs >= 0) writeSleepMs = parsedWs;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeRetryDelayMs != null) {\r\n\t\t\t\t\t\tconst parsedRetry = Math.floor(options.writeRetryDelayMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedRetry) && parsedRetry >= 0) writeRetryDelay = parsedRetry;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeMaxAttempts != null) {\r\n\t\t\t\t\t\tconst parsedAttempts = Math.floor(options.writeMaxAttempts as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedAttempts) && parsedAttempts > 0) writeMaxAttempts = parsedAttempts;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeGiveupTimeoutMs != null) {\r\n\t\t\t\t\t\tconst parsedGiveupTimeout = Math.floor(options.writeGiveupTimeoutMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedGiveupTimeout) && parsedGiveupTimeout > 0) writeGiveupTimeout = parsedGiveupTimeout;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.drainOutstandingTimeoutMs != null) {\r\n\t\t\t\t\t\tconst parsedDrain = Math.floor(options.drainOutstandingTimeoutMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedDrain) && parsedDrain >= 0) drainOutstandingTimeout = parsedDrain;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t}\r\n\t\t\tif (configuredMaxOutstanding < 1) configuredMaxOutstanding = 1;\r\n\t\t\tif (writeSleepMs < 0) writeSleepMs = 0;\r\n\t\t} catch (e) { }\r\n\t\t\tif (supportsWriteWithResponse == false && supportsWriteNoResponse == true) {\r\n\t\t\t\tif (configuredMaxOutstanding > 1) configuredMaxOutstanding = 1;\r\n\t\t\t\tif (writeSleepMs < 15) writeSleepMs = 15;\r\n\t\t\t\tif (writeRetryDelay < 150) writeRetryDelay = 150;\r\n\t\t\t\tif (writeMaxAttempts < 40) writeMaxAttempts = 40;\r\n\t\t\t\tif (writeGiveupTimeout < 120000) writeGiveupTimeout = 120000;\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:291','[DFU] packet char only supports WRITE_NO_RESPONSE; serializing writes with conservative pacing');\r\n\t\t\t}\r\n\t\tconst maxOutstandingCeiling = configuredMaxOutstanding;\r\n\t\tlet adaptiveMaxOutstanding = configuredMaxOutstanding;\r\n\t\tconst minOutstandingWindow = 1;\r\n\r\n\t\twhile (offset < total) {\r\n\t\t\tconst end = Math.min(offset + chunkSize, total);\r\n\t\t\tconst slice = firmwareBytes.subarray(offset, end);\r\n\t\t\t// Decide whether to wait for response per-chunk. Honor characteristic support.\r\n\t\t\t// Generator-friendly: avoid 'undefined' and use explicit boolean check.\r\n\t\t\tlet finalWaitForResponse = true;\r\n\t\t\tif (options != null) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst maybe = options.waitForResponse;\r\n\t\t\t\t\tif (maybe == true && supportsWriteWithResponse == false && supportsWriteNoResponse == true) {\r\n\t\t\t\t\t\t// caller requested response but characteristic cannot provide it; keep true to ensure we await the write promise.\r\n\t\t\t\t\t\tfinalWaitForResponse = true;\r\n\t\t\t\t\t} else if (maybe == false) {\r\n\t\t\t\t\t\tfinalWaitForResponse = false;\r\n\t\t\t\t\t} else if (maybe == true) {\r\n\t\t\t\t\t\tfinalWaitForResponse = true;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { finalWaitForResponse = true; }\r\n\t\t\t}\r\n\r\n\t\t\tconst writeOpts: WriteCharacteristicOptions = {\r\n\t\t\t\twaitForResponse: finalWaitForResponse,\r\n\t\t\t\tretryDelayMs: writeRetryDelay,\r\n\t\t\t\tmaxAttempts: writeMaxAttempts,\r\n\t\t\t\tgiveupTimeoutMs: writeGiveupTimeout,\r\n\t\t\t\tforceWriteTypeNoResponse: finalWaitForResponse == false\r\n\t\t\t};\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:324','[DFU] writing packet chunk offset=', offset, 'len=', slice.length, 'waitForResponse=', finalWaitForResponse, 'outstanding=', outstandingWrites);\r\n\r\n\t\t\t// Fire-and-forget path: do not await the write if waitForResponse == false.\r\n\t\t\tif (finalWaitForResponse == false) {\r\n\t\t\t\tif (failureBackoffMs > 0) {\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:329','[DFU] applying failure backoff', failureBackoffMs, 'ms before next write for', deviceId);\r\n\t\t\t\t\tawait this._sleep(failureBackoffMs);\r\n\t\t\t\t\tfailureBackoffMs = Math.floor(failureBackoffMs / 2);\r\n\t\t\t\t}\r\n\t\t\t\twhile (outstandingWrites >= adaptiveMaxOutstanding) {\r\n\t\t\t\t\tawait this._sleep(Math.max(1, writeSleepMs));\r\n\t\t\t\t}\r\n\t\t\t\t// increment outstanding counter and kick the write without awaiting.\r\n\t\t\t\toutstandingWrites = outstandingWrites + 1;\r\n\t\t\t\t// fire-and-forget: start the write but don't await its Promise\r\n\t\t\t\tconst writeOffset = offset;\r\n\t\t\t\tserviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts).then((res) => {\r\n\t\t\t\t\toutstandingWrites = Math.max(0, outstandingWrites - 1);\r\n\t\t\t\t\tif (res == true) {\r\n\t\t\t\t\t\tif (adaptiveMaxOutstanding < maxOutstandingCeiling) {\r\n\t\t\t\t\t\t\tadaptiveMaxOutstanding = Math.min(maxOutstandingCeiling, adaptiveMaxOutstanding + 1);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (failureBackoffMs > 0) failureBackoffMs = Math.floor(failureBackoffMs / 2);\r\n\t\t\t\t\t}\r\n\t\t\t\t\t// log occasional completions\r\n\t\t\t\t\tif ((outstandingWrites & 0x1f) == 0) {\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:350','[DFU] write completion callback, outstandingWrites=', outstandingWrites, 'adaptiveWindow=', adaptiveMaxOutstanding, 'device=', deviceId);\r\n\t\t\t\t\t}\r\n\t\t\t\t\t// detect write failure signaled by service manager\r\n\t\t\t\t\tif (res !== true) {\r\n\t\t\t\t\t\tadaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2));\r\n\t\t\t\t\t\tfailureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay)));\r\n\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:356','[DFU] writeCharacteristic returned false for device=', deviceId, 'offset=', writeOffset, 'adaptiveWindow now=', adaptiveMaxOutstanding);\r\n\t\t\t\t\t\ttry { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: 'write returned false' }); } catch (e) { }\r\n\t\t\t\t\t}\r\n\t\t\t\t}).catch((e) => {\r\n\t\t\t\t\toutstandingWrites = Math.max(0, outstandingWrites - 1);\r\n\t\t\t\t\tadaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2));\r\n\t\t\t\t\tfailureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay)));\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:363','[DFU] fire-and-forget write failed for device=', deviceId, e, 'adaptiveWindow now=', adaptiveMaxOutstanding);\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tconst errMsg ='[DFU] fire-and-forget write failed for device=';\r\n\t\t\t\t\t\tthis._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: errMsg });\r\n\t\t\t\t\t} catch (e2) { }\r\n\t\t\t\t});\r\n\t\t\t\t// account bytes for throughput\r\n\t\t\t\tthroughputWindowBytes += slice.length;\r\n\t\t\t\t_logThroughputIfNeeded(false);\r\n\t\t\t} else {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:373','[DFU] awaiting write for chunk offset=', offset);\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst writeResult = await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts);\r\n\t\t\t\t\tif (writeResult !== true) {\r\n\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:377','[DFU] writeCharacteristic(await) returned false at offset=', offset, 'device=', deviceId);\r\n\t\t\t\t\t\ttry { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: 'write returned false' }); } catch (e) { }\r\n\t\t\t\t\t\t// abort DFU by throwing\r\n\t\t\t\t\t\tthrow new Error('write failed');\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:383','[DFU] awaiting write failed at offset=', offset, 'device=', deviceId, e);\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tconst errMsg = '[DFU] awaiting write failed ';\r\n\t\t\t\t\t\tthis._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: errMsg });\r\n\t\t\t\t\t} catch (e2) { }\r\n\t\t\t\t\tthrow e;\r\n\t\t\t\t}\r\n\t\t\t\t// account bytes for throughput\r\n\t\t\t\tthroughputWindowBytes += slice.length;\r\n\t\t\t\t_logThroughputIfNeeded(false);\r\n\t\t\t}\r\n\t\t\t// update PRN counters and wait when window reached\r\n\t\t\tconst sessAfter = this.sessions.get(deviceId);\r\n\t\t\tif (sessAfter != null && sessAfter.useNordic == true && typeof sessAfter.prn == 'number' && (sessAfter.prn ?? 0) > 0) {\r\n\t\t\t\tsessAfter.packetsSincePrn = (sessAfter.packetsSincePrn ?? 0) + 1;\r\n\t\t\t\tif ((sessAfter.packetsSincePrn ?? 0) >= (sessAfter.prn ?? 0) && (sessAfter.prn ?? 0) > 0) {\r\n\t\t\t\t\t// wait for PRN (device notification) before continuing\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:401','[DFU] reached PRN window, waiting for PRN for', deviceId, 'packetsSincePrn=', sessAfter.packetsSincePrn, 'prn=', sessAfter.prn);\r\n\t\t\t\t\t\tawait this._waitForPrn(deviceId, prnTimeoutMs);\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:403','[DFU] PRN received, resuming transfer for', deviceId);\r\n\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:405','[DFU] PRN wait failed/timed out, continuing anyway for', deviceId, e);\r\n\t\t\t\t\t\tif (disablePrnOnTimeout) {\r\n\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:407','[DFU] disabling PRN waits after timeout for', deviceId);\r\n\t\t\t\t\t\t\tsessAfter.prn = 0;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t\t// reset counter\r\n\t\t\t\t\tsessAfter.packetsSincePrn = 0;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\toffset = end;\r\n\t\t\t// 如果启用 nordic 模式,统计已发送字节\r\n\t\t\tconst sess = this.sessions.get(deviceId);\r\n\t\t\tif (sess != null && typeof sess.bytesSent == 'number') {\r\n\t\t\t\tsess.bytesSent = (sess.bytesSent ?? 0) + slice.length;\r\n\t\t\t}\r\n\t\t\t// 简单节流与日志,避免过快。默认睡眠非常短以提高吞吐量; 可在设备上调节\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:422','[DFU] wrote chunk for', deviceId, 'offset=', offset, '/', total, 'chunkSize=', slice.length, 'bytesSent=', sess != null ? sess.bytesSent : null, 'outstanding=', outstandingWrites);\r\n\t\t\t// emit upload progress event (percent) if available\r\n\t\t\tif (sess != null && typeof sess.bytesSent == 'number' && typeof sess.totalBytes == 'number') {\r\n\t\t\t\tconst p = Math.floor((sess.bytesSent / sess.totalBytes) * 100);\r\n\t\t\t\tthis._emitDfuEvent(deviceId, 'onProgress', p);\r\n\t\t\t}\r\n\t\t\t// yield to event loop and avoid starving the Android BLE stack\r\n\t\t\tawait this._sleep(Math.max(0, writeSleepMs));\r\n\t\t}\r\n\t// wait for outstanding writes to drain before continuing with control commands\r\n\tif (outstandingWrites > 0) {\r\n\t\tconst drainStart = Date.now();\r\n\t\twhile (outstandingWrites > 0 && (Date.now() - drainStart) < drainOutstandingTimeout) {\r\n\t\t\tawait this._sleep(Math.max(0, writeSleepMs));\r\n\t\t}\r\n\t\tif (outstandingWrites > 0) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:438','[DFU] outstandingWrites remain after drain timeout, continuing with', outstandingWrites);\r\n\t\t} else {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:440','[DFU] outstandingWrites drained before control phase');\r\n\t\t}\r\n\t}\r\n\tthis._emitDfuEvent(deviceId, 'onUploadingCompleted', null);\r\n\r\n\t\t\t// force final throughput log before activate/validate\r\n\t\t\t_logThroughputIfNeeded(true);\r\n\r\n\t\t// 发送 activate/validate 命令到 control point(需根据设备协议实现)\r\n\t\t// 下面为占位:请替换为实际的 opcode\r\n\t\t// 在写入前先启动控制结果等待,防止设备快速响应导致丢失通知\r\n\t\tconst controlTimeout = 20000;\r\n\t\tconst controlResultPromise = this._waitForControlResult(deviceId, controlTimeout);\r\n\t\ttry {\r\n\t\t\t// control writes: pass undefined options explicitly to satisfy the generator/typechecker\r\n\t\t\tconst activatePayload = new Uint8Array([0x04]);\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:456','[DFU] sending activate/validate payload=', Array.from(activatePayload));\r\n\t\t\tawait serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, activatePayload, null);\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:458','[DFU] activate/validate write returned for', deviceId);\r\n\t\t} catch (e) {\r\n\t\t\t// 写入失败时取消控制等待,避免悬挂定时器\r\n\t\t\ttry {\r\n\t\t\t\tconst sessOnWriteFail = this.sessions.get(deviceId);\r\n\t\t\t\tif (sessOnWriteFail != null && typeof sessOnWriteFail.reject == 'function') {\r\n\t\t\t\t\tsessOnWriteFail.reject(e);\r\n\t\t\t\t}\r\n\t\t\t} catch (rejectErr) { }\r\n\t\t\tawait controlResultPromise.catch(() => { });\r\n\t\t\ttry { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e2) { }\r\n\t\t\tthis.sessions.delete(deviceId);\r\n\t\t\tthrow e;\r\n\t\t}\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:472','[DFU] sent control activate/validate command to control point for', deviceId);\r\n\t\tthis._emitDfuEvent(deviceId, 'onValidating', null);\r\n\r\n\t// 等待 control-point 返回最终结果(成功或失败),超时可配置\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:476','[DFU] waiting for control result (timeout=', controlTimeout, ') for', deviceId);\r\n\ttry {\r\n\t\tawait controlResultPromise;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:479','[DFU] control result resolved for', deviceId);\r\n\t} catch (err) {\r\n\t\t// 清理订阅后抛出\r\n\t\ttry { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e) { }\r\n\t\tthis.sessions.delete(deviceId);\r\n\t\tthrow err;\r\n\t}\r\n\r\n\t\t// 取消订阅\r\n\t\ttry {\r\n\t\t\tawait serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID);\r\n\t\t} catch (e) { }\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:491','[DFU] unsubscribed control point for', deviceId);\r\n\r\n\t\t// 清理会话\r\n\t\tthis.sessions.delete(deviceId);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:495','[DFU] session cleared for', deviceId);\r\n\r\n\t\treturn;\r\n\t}\r\n\r\n\tasync _requestMtu(gatt : BluetoothGatt, mtu : number, timeoutMs : number) : Promise {\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\t// 在当前项目,BluetoothGattCallback.onMtuChanged 未被封装;简单发起请求并等待短超时\r\n\t\t\ttry {\r\n\t\t\t\tconst ok = gatt.requestMtu(Math.floor(mtu) as Int);\r\n\t\t\t\tif (!ok) {\r\n\t\t\t\t\treturn reject(new Error('requestMtu failed'));\r\n\t\t\t\t}\r\n\t\t\t} catch (e) {\r\n\t\t\t\treturn reject(e);\r\n\t\t\t}\r\n\t\t\t// 无 callback 监听时退回,等待一小段时间以便成功\r\n\t\t\tsetTimeout(() => resolve(), Math.min(2000, timeoutMs));\r\n\t\t});\r\n\t}\r\n\r\n\t_sleep(ms : number) {\r\n\t\treturn new Promise((r) => { setTimeout(() => { r() }, ms); });\r\n\t}\r\n\r\n\t_waitForPrn(deviceId : string, timeoutMs : number) : Promise {\r\n\t\tconst session = this.sessions.get(deviceId);\r\n\t\tif (session == null) return Promise.reject(new Error('no dfu session'));\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\tconst timer = setTimeout(() => {\r\n\t\t\t\t// timeout waiting for PRN\r\n\t\t\t\t// clear pending handlers\r\n\t\t\t\tsession.prnResolve = null;\r\n\t\t\t\tsession.prnReject = null;\r\n\t\t\t\treject(new Error('PRN timeout'));\r\n\t\t\t}, timeoutMs);\r\n\t\t\tconst prnResolve = () => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\tresolve();\r\n\t\t\t};\r\n\t\t\tconst prnReject = (err ?: any) => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\treject(err);\r\n\t\t\t};\r\n\t\t\tsession.prnResolve = prnResolve;\r\n\t\t\tsession.prnReject = prnReject;\r\n\t\t});\r\n\t}\r\n\r\n\t// 默认 control point 解析器(非常通用的尝试解析:如果设备发送 progress byte 或成功码)\r\n\t_defaultControlParser(data : Uint8Array) : ControlParserResult | null {\r\n\t\t// 假设协议:第一个字节为 opcode, 第二字节可为状态或进度\r\n\t\tif (data == null || data.length === 0) return null;\r\n\t\tconst op = data[0];\r\n\t\t// Nordic-style response: [0x10, requestOp, resultCode]\r\n\t\tif (op === 0x10 && data.length >= 3) {\r\n\t\t\tconst requestOp = data[1];\r\n\t\t\tconst resultCode = data[2];\r\n\t\t\tif (resultCode === 0x01) {\r\n\t\t\t\treturn { type: 'success' };\r\n\t\t\t}\r\n\t\t\treturn { type: 'error', error: { requestOp: requestOp, resultCode: resultCode, raw: Array.from(data) } };\r\n\t\t}\r\n\t\t// Nordic PRN notification: [0x11, LSB, MSB] -> return as progress (bytes received)\r\n\t\tif (op === 0x11 && data.length >= 3) {\r\n\t\t\tconst lsb = data[1];\r\n\t\t\tconst msb = data[2];\r\n\t\t\tconst received = (msb << 8) | lsb;\r\n\t\t\treturn { type: 'progress', progress: received };\r\n\t\t}\r\n\t\t// vendor-specific opcode example: 0x60 may mean 'response/progress' for some firmwares\r\n\t\tif (op === 0x60) {\r\n\t\t\tif (data.length >= 3) {\r\n\t\t\t\tconst requestOp = data[1];\r\n\t\t\t\tconst status = data[2];\r\n\t\t\t\t// Known success/status codes observed in field devices\r\n\t\t\t\tif (status === 0x00 || status === 0x01 || status === 0x0A) {\r\n\t\t\t\t\treturn { type: 'success' };\r\n\t\t\t\t}\r\n\t\t\t\treturn { type: 'error', error: { requestOp: requestOp, resultCode: status, raw: Array.from(data) } };\r\n\t\t\t}\r\n\t\t\tif (data.length >= 2) {\r\n\t\t\t\treturn { type: 'progress', progress: data[1] };\r\n\t\t\t}\r\n\t\t}\r\n\t\t// 通用进度回退:若第二字节位于 0-100 之间,当作百分比\r\n\t\tif (data.length >= 2) {\r\n\t\t\tconst maybeProgress = data[1];\r\n\t\t\tif (maybeProgress >= 0 && maybeProgress <= 100) {\r\n\t\t\t\treturn { type: 'progress', progress: maybeProgress };\r\n\t\t\t}\r\n\t\t}\r\n\t\t// 若找到明显的 success opcode (示例 0x01) 或 error 0xFF\r\n\t\tif (op === 0x01) return { type: 'success' };\r\n\t\tif (op === 0xFF) return { type: 'error', error: data };\r\n\t\treturn { type: 'info' };\r\n\t}\r\n\r\n\t// Nordic DFU control-parser(支持 Response and Packet Receipt Notification)\r\n\t_nordicControlParser(data : Uint8Array) : ControlParserResult | null {\r\n\t\t// Nordic opcodes (简化):\r\n\t\t// - 0x10 : Response (opcode, requestOp, resultCode)\r\n\t\t// - 0x11 : Packet Receipt Notification (opcode, value LSB, value MSB)\r\n\t\tif (data == null || data.length == 0) return null;\r\n\t\tconst op = data[0];\r\n\t\tif (op == 0x11 && data.length >= 3) {\r\n\t\t\t// packet receipt notif: bytes received (little endian)\r\n\t\t\tconst lsb = data[1];\r\n\t\t\tconst msb = data[2];\r\n\t\t\tconst received = (msb << 8) | lsb;\r\n\t\t\t// Return received bytes as progress value; parser does not resolve device-specific session here.\r\n\t\t\treturn { type: 'progress', progress: received };\r\n\t\t}\r\n\t\t// Nordic vendor-specific progress/response opcode (example 0x60)\r\n\t\tif (op == 0x60) {\r\n\t\t\tif (data.length >= 3) {\r\n\t\t\t\tconst requestOp = data[1];\r\n\t\t\t\tconst status = data[2];\r\n\t\t\t\tif (status == 0x00 || status == 0x01 || status == 0x0A) {\r\n\t\t\t\t\treturn { type: 'success' };\r\n\t\t\t\t}\r\n\t\t\t\treturn { type: 'error', error: { requestOp, resultCode: status, raw: Array.from(data) } };\r\n\t\t\t}\r\n\t\t\tif (data.length >= 2) {\r\n\t\t\t\treturn { type: 'progress', progress: data[1] };\r\n\t\t\t}\r\n\t\t}\r\n\t\t// Response: check result code for success (0x01 may indicate success in some stacks)\r\n\t\tif (op == 0x10 && data.length >= 3) {\r\n\t\t\tconst requestOp = data[1];\r\n\t\t\tconst resultCode = data[2];\r\n\t\t\t// Nordic resultCode 0x01 = SUCCESS typically\r\n\t\t\tif (resultCode == 0x01) return { type: 'success' };\r\n\t\t\telse return { type: 'error', error: { requestOp, resultCode } };\r\n\t\t}\r\n\t\treturn null;\r\n\t}\r\n\r\n\t_handleControlNotification(deviceId : string, data : Uint8Array) {\r\n\t\tconst session = this.sessions.get(deviceId);\r\n\t\tif (session == null) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:636','[DFU] control notification received but no session for', deviceId, 'data=', Array.from(data));\r\n\t\t\treturn;\r\n\t\t}\r\n\t\ttry {\r\n\t\t\t// human readable opcode mapping\r\n\t\t\tlet opcodeName = 'unknown';\r\n\t\t\tswitch (data[0]) {\r\n\t\t\t\tcase 0x10: opcodeName = 'Response'; break;\r\n\t\t\t\tcase 0x11: opcodeName = 'PRN'; break;\r\n\t\t\t\tcase 0x60: opcodeName = 'VendorProgress'; break;\r\n\t\t\t\tcase 0x01: opcodeName = 'SuccessOpcode'; break;\r\n\t\t\t\tcase 0xFF: opcodeName = 'ErrorOpcode'; break;\r\n\t\t\t}\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:649','[DFU] _handleControlNotification deviceId=', deviceId, 'opcode=0x' + data[0].toString(16), 'name=', opcodeName, 'raw=', Array.from(data));\r\n\t\t\tconst parsed = session.controlParser != null ? session.controlParser(data) : null;\r\n\t\t\tif (session.onLog != null) session.onLog('DFU control notify: ' + Array.from(data).join(','));\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:652','[DFU] parsed control result=', parsed);\r\n\t\t\tif (parsed == null) return;\r\n\t\t\tif (parsed.type == 'progress' && parsed.progress != null) {\r\n\t\t\t\t// 如果在 nordic 模式 parsed.progress 可能是已接收字节数,则转换为百分比\r\n\t\t\t\tif (session.useNordic == true && session.totalBytes != null && session.totalBytes > 0) {\r\n\t\t\t\t\t\tconst percent = Math.floor((parsed.progress / session.totalBytes) * 100);\r\n\t\t\t\t\tsession.onProgress?.(percent);\r\n\t\t\t\t\t\t// If we have written all bytes locally, log that event\r\n\t\t\t\t\t\tif (session.bytesSent != null && session.totalBytes != null && session.bytesSent >= session.totalBytes) {\r\n\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:661','[DFU] all bytes written locally for', deviceId, 'bytesSent=', session.bytesSent, 'total=', session.totalBytes);\r\n\t\t\t\t\t\t\t// emit uploading completed once\r\n\t\t\t\t\t\t\tthis._emitDfuEvent(deviceId, 'onUploadingCompleted', null);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t// If a PRN wait is pending, resolve it (PRN indicates device received packets)\r\n\t\t\t\t\tif (typeof session.prnResolve == 'function') {\r\n\t\t\t\t\t\ttry { session.prnResolve(); } catch (e) { }\r\n\t\t\t\t\t\tsession.prnResolve = null;\r\n\t\t\t\t\t\tsession.prnReject = null;\r\n\t\t\t\t\t\tsession.packetsSincePrn = 0;\r\n\t\t\t\t\t}\r\n\t\t\t\t} else {\r\n\t\t\t\t\tconst progress = parsed.progress\r\n\t\t\t\t\tif (progress != null) {\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:675','[DFU] progress for', deviceId, 'progress=', progress);\r\n\t\t\t\t\t\tsession.onProgress?.(progress);\r\n\t\t\t\t\t\t// also resolve PRN if was waiting (in case device reports numeric progress)\r\n\t\t\t\t\t\tif (typeof session.prnResolve == 'function') {\r\n\t\t\t\t\t\t\ttry { session.prnResolve(); } catch (e) { }\r\n\t\t\t\t\t\t\tsession.prnResolve = null;\r\n\t\t\t\t\t\t\tsession.prnReject = null;\r\n\t\t\t\t\t\t\tsession.packetsSincePrn = 0;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t} else if (parsed.type == 'success') {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:687','[DFU] parsed success for', deviceId, 'resolving session');\r\n\t\t\t\tsession.resolve();\r\n\t\t\t\t// Log final device-acknowledged success\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:690','[DFU] device reported DFU success for', deviceId);\r\n\t\t\t\tthis._emitDfuEvent(deviceId, 'onDfuCompleted', null);\r\n\t\t\t} else if (parsed.type == 'error') {\r\n\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:693','[DFU] parsed error for', deviceId, parsed.error);\r\n\t\t\t\tsession.reject(parsed.error ?? new Error('DFU device error'));\r\n\t\t\t\tthis._emitDfuEvent(deviceId, 'onError', parsed.error ?? {});\r\n\t\t\t} else {\r\n\t\t\t\t// info - just log\r\n\t\t\t}\r\n\t\t} catch (e) {\r\n\t\t\tsession.onLog?.('control parse error: ' + e);\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:701','[DFU] control parse exception for', deviceId, e);\r\n\t\t}\r\n\t}\r\n\r\n\t_waitForControlResult(deviceId : string, timeoutMs : number) : Promise {\r\n\t\tconst session = this.sessions.get(deviceId);\r\n\t\tif (session == null) return Promise.reject(new Error('no dfu session'));\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\t// wrap resolve/reject to clear timer\r\n\t\t\tconst timer = setTimeout(() => {\r\n\t\t\t\t// 超时\r\n\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:712','[DFU] _waitForControlResult timeout for', deviceId);\r\n\t\t\t\treject(new Error('DFU control timeout'));\r\n\t\t\t}, timeoutMs);\r\n\t\t\tconst origResolve = () => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:717','[DFU] _waitForControlResult resolved for', deviceId);\r\n\t\t\t\tresolve();\r\n\t\t\t};\r\n\t\t\tconst origReject = (err ?: any) => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:722','[DFU] _waitForControlResult rejected for', deviceId, 'err=', err);\r\n\t\t\t\treject(err);\r\n\t\t\t};\r\n\t\t\t// replace session handlers temporarily (guard nullable)\r\n\t\t\tif (session != null) {\r\n\t\t\t\tsession.resolve = origResolve;\r\n\t\t\t\tsession.reject = origReject;\r\n\t\t\t}\r\n\t\t});\r\n\t}\r\n}\r\n\r\nexport const dfuManager = new DfuManager();","\r\n\r\n\r\n\r\n","import 'F:/HBuilderX/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/index.ts';import App from './App.uvue'\r\n\r\nimport { createSSRApp } from 'vue'\r\nexport function createApp() {\r\n\tconst app = createSSRApp(App)\r\n\treturn {\r\n\t\tapp\r\n\t}\r\n}\nexport function main(app: IApp) {\n definePageRoutes();\n defineAppConfig();\n (createApp()['app'] as VueApp).mount(app, GenUniApp());\n}\n\nexport class UniAppConfig extends io.dcloud.uniapp.appframe.AppConfig {\n override name: string = \"akbleserver\"\n override appid: string = \"__UNI__95B2570\"\n override versionName: string = \"1.0.1\"\n override versionCode: string = \"101\"\n override uniCompilerVersion: string = \"4.76\"\n \n constructor() { super() }\n}\n\nimport GenPagesAkbletestClass from './pages/akbletest.uvue'\nfunction definePageRoutes() {\n__uniRoutes.push({ path: \"pages/akbletest\", component: GenPagesAkbletestClass, meta: { isQuit: true } as UniPageMeta, style: _uM([[\"navigationBarTitleText\",\"akble\"]]) } as UniPageRoute)\n}\nconst __uniTabBar: Map | null = null\nconst __uniLaunchPage: Map = _uM([[\"url\",\"pages/akbletest\"],[\"style\",_uM([[\"navigationBarTitleText\",\"akble\"]])]])\nfunction defineAppConfig(){\n __uniConfig.entryPagePath = '/pages/akbletest'\n __uniConfig.globalStyle = _uM([[\"navigationBarTextStyle\",\"black\"],[\"navigationBarTitleText\",\"体测训练\"],[\"navigationBarBackgroundColor\",\"#F8F8F8\"],[\"backgroundColor\",\"#F8F8F8\"]])\n __uniConfig.getTabBarConfig = ():Map | null => null\n __uniConfig.tabBar = __uniConfig.getTabBarConfig()\n __uniConfig.conditionUrl = ''\n __uniConfig.uniIdRouter = _uM()\n \n __uniConfig.ready = true\n}\n","export type GetBatteryInfoSuccess = {\n\terrMsg : string,\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\nexport type GetBatteryInfoOptions = {\n\t/**\n\t\t* 接口调用结束的回调函数(调用成功、失败都会执行)\n\t\t*/\n\tsuccess ?: (res : GetBatteryInfoSuccess) => void\n\t/**\n\t\t* 接口调用失败的回调函数\n\t\t*/\n\tfail ?: (res : UniError) => void\n\t/**\n\t\t* 接口调用成功的回调\n\t\t*/\n\tcomplete ?: (res : any) => void\n}\n\nexport type GetBatteryInfoResult = {\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\n/**\n * 错误码\n * - 1001 getAppContext is null\n */\nexport type GetBatteryInfoErrorCode = 1001 ;\n/**\n * GetBatteryInfo 的错误回调参数\n */\nexport interface GetBatteryInfoFail extends IUniError {\n errCode : GetBatteryInfoErrorCode\n};\n\n/**\n* 获取电量信息\n* @param {GetBatteryInfoOptions} options\n*\n*\n* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html\n* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22\n* @since 3.6.11\n*\n* @assert () => success({errCode: 0, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:ok\", level: 60, isCharging: false })\n* @assert () => fail({errCode: 1001, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:fail getAppContext is null\" })\n*/\nexport type GetBatteryInfo = (options : GetBatteryInfoOptions) => void\n\n\nexport type GetBatteryInfoSync = () => GetBatteryInfoResult\n\ninterface Uni {\n\n\t/**\n\t * 获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @param {GetBatteryInfoOptions} options\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo({\n\t *\t\tsuccess(res) {\n\t *\t\t\tconsole.log(res);\n\t *\t\t}\n\t * })\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfo (options : GetBatteryInfoOptions) : void,\n\t/**\n\t * 同步获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo()\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfoSync():GetBatteryInfoResult\n\n}\n"],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/unpackage/cache/.app-android/sourcemap/pages/akbletest.kt.map b/unpackage/cache/.app-android/sourcemap/pages/akbletest.kt.map new file mode 100644 index 0000000..ad889c3 --- /dev/null +++ b/unpackage/cache/.app-android/sourcemap/pages/akbletest.kt.map @@ -0,0 +1 @@ +{"version":3,"sources":["pages/akbletest.uvue","App.uvue","uni_modules/uni-getbatteryinfo/utssdk/interface.uts"],"sourcesContent":["\r\n\r\n\r\n\r\n",null,null],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/unpackage/cache/.app-android/src/.manifest.json b/unpackage/cache/.app-android/src/.manifest.json new file mode 100644 index 0000000..68b4a5f --- /dev/null +++ b/unpackage/cache/.app-android/src/.manifest.json @@ -0,0 +1,16 @@ +{ + "version": "1", + "env": { + "compiler_version": "4.76" + }, + "files": { + "pages/akbletest.kt": { + "class": "GenPagesAkbletest", + "md5": "790db77693349047eeb9766a2c853a981e51afac" + }, + "index.kt": { + "class": "", + "md5": "4e5276a84276eacc108178c185bd1334b128767c" + } + } +} \ No newline at end of file diff --git a/unpackage/cache/.app-android/src/index.kt b/unpackage/cache/.app-android/src/index.kt new file mode 100644 index 0000000..fc71a96 --- /dev/null +++ b/unpackage/cache/.app-android/src/index.kt @@ -0,0 +1,3969 @@ +@file:Suppress("UNCHECKED_CAST", "USELESS_CAST", "INAPPLICABLE_JVM_NAME", "UNUSED_ANONYMOUS_PARAMETER", "NAME_SHADOWING", "UNNECESSARY_NOT_NULL_ASSERTION") +package uni.UNI95B2570 +import android.bluetooth.BluetoothAdapter +import android.bluetooth.BluetoothGatt +import android.bluetooth.BluetoothGattCallback +import android.bluetooth.BluetoothGattCharacteristic +import android.bluetooth.BluetoothGattDescriptor +import android.bluetooth.BluetoothGattService +import android.bluetooth.BluetoothManager +import android.bluetooth.le.ScanCallback +import android.bluetooth.le.ScanResult +import android.bluetooth.le.ScanSettings +import android.content.Context +import android.os.Handler +import android.os.Looper +import io.dcloud.uniapp.* +import io.dcloud.uniapp.extapi.* +import io.dcloud.uniapp.framework.* +import io.dcloud.uniapp.runtime.* +import io.dcloud.uniapp.vue.* +import io.dcloud.uniapp.vue.shared.* +import io.dcloud.unicloud.* +import io.dcloud.uts.* +import io.dcloud.uts.Map +import io.dcloud.uts.Set +import io.dcloud.uts.UTSAndroid +import java.util.UUID +import io.dcloud.uniapp.extapi.connectSocket as uni_connectSocket +import io.dcloud.uniapp.extapi.exit as uni_exit +import io.dcloud.uniapp.extapi.showModal as uni_showModal +import io.dcloud.uniapp.extapi.showToast as uni_showToast +val runBlock1 = run { + __uniConfig.getAppStyles = fun(): Map>> { + return GenApp.styles + } +} +fun initRuntimeSocket(hosts: String, port: String, id: String): UTSPromise { + if (hosts == "" || port == "" || id == "") { + return UTSPromise.resolve(null) + } + return hosts.split(",").reduce>(fun(promise: UTSPromise, host: String): UTSPromise { + return promise.then(fun(socket): UTSPromise { + if (socket != null) { + return UTSPromise.resolve(socket) + } + return tryConnectSocket(host, port, id) + } + ) + } + , UTSPromise.resolve(null)) +} +val SOCKET_TIMEOUT: Number = 500 +fun tryConnectSocket(host: String, port: String, id: String): UTSPromise { + return UTSPromise(fun(resolve, reject){ + val socket = uni_connectSocket(ConnectSocketOptions(url = "ws://" + host + ":" + port + "/" + id, fail = fun(_) { + resolve(null) + } + )) + val timer = setTimeout(fun(){ + socket.close(CloseSocketOptions(code = 1006, reason = "connect timeout")) + resolve(null) + } + , SOCKET_TIMEOUT) + socket.onOpen(fun(e){ + clearTimeout(timer) + resolve(socket) + } + ) + socket.onClose(fun(e){ + clearTimeout(timer) + resolve(null) + } + ) + socket.onError(fun(e){ + clearTimeout(timer) + resolve(null) + } + ) + } + ) +} +fun initRuntimeSocketService(): UTSPromise { + val hosts: String = "192.168.56.1,192.168.233.1,192.168.225.1,192.168.0.116,127.0.0.1,172.19.224.1" + val port: String = "8090" + val id: String = "app-android__aho5q" + if (hosts == "" || port == "" || id == "") { + return UTSPromise.resolve(false) + } + var socketTask: SocketTask? = null + __registerWebViewUniConsole(fun(): String { + return "!function(){\"use strict\";\"function\"==typeof SuppressedError&&SuppressedError;var e=[\"log\",\"warn\",\"error\",\"info\",\"debug\"],n=e.reduce((function(e,n){return e[n]=console[n].bind(console),e}),{}),t=null,r=new Set,o={};function i(e){if(null!=t){var n=e.map((function(e){if(\"string\"==typeof e)return e;var n=e&&\"promise\"in e&&\"reason\"in e,t=n?\"UnhandledPromiseRejection: \":\"\";if(n&&(e=e.reason),e instanceof Error&&e.stack)return e.message&&!e.stack.includes(e.message)?\"\".concat(t).concat(e.message,\"\\n\").concat(e.stack):\"\".concat(t).concat(e.stack);if(\"object\"==typeof e&&null!==e)try{return t+JSON.stringify(e)}catch(e){return t+String(e)}return t+String(e)})).filter(Boolean);n.length>0&&t(JSON.stringify(Object.assign({type:\"error\",data:n},o)))}else e.forEach((function(e){r.add(e)}))}function a(e,n){try{return{type:e,args:u(n)}}catch(e){}return{type:e,args:[]}}function u(e){return e.map((function(e){return c(e)}))}function c(e,n){if(void 0===n&&(n=0),n>=7)return{type:\"object\",value:\"[Maximum depth reached]\"};switch(typeof e){case\"string\":return{type:\"string\",value:e};case\"number\":return function(e){return{type:\"number\",value:String(e)}}(e);case\"boolean\":return function(e){return{type:\"boolean\",value:String(e)}}(e);case\"object\":try{return function(e,n){if(null===e)return{type:\"null\"};if(function(e){return e.\$&&s(e.\$)}(e))return function(e,n){return{type:\"object\",className:\"ComponentPublicInstance\",value:{properties:Object.entries(e.\$.type).map((function(e){return f(e[0],e[1],n+1)}))}}}(e,n);if(s(e))return function(e,n){return{type:\"object\",className:\"ComponentInternalInstance\",value:{properties:Object.entries(e.type).map((function(e){return f(e[0],e[1],n+1)}))}}}(e,n);if(function(e){return e.style&&null!=e.tagName&&null!=e.nodeName}(e))return function(e,n){return{type:\"object\",value:{properties:Object.entries(e).filter((function(e){var n=e[0];return[\"id\",\"tagName\",\"nodeName\",\"dataset\",\"offsetTop\",\"offsetLeft\",\"style\"].includes(n)})).map((function(e){return f(e[0],e[1],n+1)}))}}}(e,n);if(function(e){return\"function\"==typeof e.getPropertyValue&&\"function\"==typeof e.setProperty&&e.\$styles}(e))return function(e,n){return{type:\"object\",value:{properties:Object.entries(e.\$styles).map((function(e){return f(e[0],e[1],n+1)}))}}}(e,n);if(Array.isArray(e))return{type:\"object\",subType:\"array\",value:{properties:e.map((function(e,t){return function(e,n,t){var r=c(e,t);return r.name=\"\".concat(n),r}(e,t,n+1)}))}};if(e instanceof Set)return{type:\"object\",subType:\"set\",className:\"Set\",description:\"Set(\".concat(e.size,\")\"),value:{entries:Array.from(e).map((function(e){return function(e,n){return{value:c(e,n)}}(e,n+1)}))}};if(e instanceof Map)return{type:\"object\",subType:\"map\",className:\"Map\",description:\"Map(\".concat(e.size,\")\"),value:{entries:Array.from(e.entries()).map((function(e){return function(e,n){return{key:c(e[0],n),value:c(e[1],n)}}(e,n+1)}))}};if(e instanceof Promise)return{type:\"object\",subType:\"promise\",value:{properties:[]}};if(e instanceof RegExp)return{type:\"object\",subType:\"regexp\",value:String(e),className:\"Regexp\"};if(e instanceof Date)return{type:\"object\",subType:\"date\",value:String(e),className:\"Date\"};if(e instanceof Error)return{type:\"object\",subType:\"error\",value:e.message||String(e),className:e.name||\"Error\"};var t=void 0,r=e.constructor;r&&r.get\$UTSMetadata\$&&(t=r.get\$UTSMetadata\$().name);var o=Object.entries(e);(function(e){return e.modifier&&e.modifier._attribute&&e.nodeContent})(e)&&(o=o.filter((function(e){var n=e[0];return\"modifier\"!==n&&\"nodeContent\"!==n})));return{type:\"object\",className:t,value:{properties:o.map((function(e){return f(e[0],e[1],n+1)}))}}}(e,n)}catch(e){return{type:\"object\",value:{properties:[]}}}case\"undefined\":return{type:\"undefined\"};case\"function\":return function(e){return{type:\"function\",value:\"function \".concat(e.name,\"() {}\")}}(e);case\"symbol\":return function(e){return{type:\"symbol\",value:e.description}}(e);case\"bigint\":return function(e){return{type:\"bigint\",value:String(e)}}(e)}}function s(e){return e.type&&null!=e.uid&&e.appContext}function f(e,n,t){var r=c(n,t);return r.name=e,r}var l=null,p=[],y={},g=\"---BEGIN:EXCEPTION---\",d=\"---END:EXCEPTION---\";function v(e){null!=l?l(JSON.stringify(Object.assign({type:\"console\",data:e},y))):p.push.apply(p,e)}var m=/^\\s*at\\s+[\\w/./-]+:\\d+\$/;function b(){function t(e){return function(){for(var t=[],r=0;r0){var t=p.slice();p.length=0,v(t)}}((function(e){_(e)}),{channel:e}),function(e,n){if(void 0===n&&(n={}),t=e,Object.assign(o,n),null!=e&&r.size>0){var a=Array.from(r);r.clear(),i(a)}}((function(e){_(e)}),{channel:e}),window.addEventListener(\"error\",(function(e){i([e.error])})),window.addEventListener(\"unhandledrejection\",(function(e){i([e])}))}}()}();" + } + , fun(data: String){ + socketTask?.send(SendSocketMessageOptions(data = data)) + } + ) + return UTSPromise.resolve().then(fun(): UTSPromise { + return initRuntimeSocket(hosts, port, id).then(fun(socket): Boolean { + if (socket == null) { + return false + } + socketTask = socket + return true + } + ) + } + ).`catch`(fun(): Boolean { + return false + } + ) +} +val runBlock2 = run { + initRuntimeSocketService() +} +var firstBackTime: Number = 0 +open class GenApp : BaseApp { + constructor(__ins: ComponentInternalInstance) : super(__ins) { + onLaunch(fun(_: OnLaunchOptions) { + console.log("App Launch", " at App.uvue:10") + } + , __ins) + onAppShow(fun(_: OnShowOptions) { + console.log("App Show", " at App.uvue:15") + } + , __ins) + onAppHide(fun() { + console.log("App Hide", " at App.uvue:18") + } + , __ins) + onLastPageBackPress(fun() { + console.log("App LastPageBackPress", " at App.uvue:22") + if (firstBackTime == 0) { + uni_showToast(ShowToastOptions(title = "再按一次退出应用", position = "bottom")) + firstBackTime = Date.now() + setTimeout(fun(){ + firstBackTime = 0 + }, 2000) + } else if (Date.now() - firstBackTime < 2000) { + firstBackTime = Date.now() + uni_exit(null) + } + } + , __ins) + onExit(fun() { + console.log("App Exit", " at App.uvue:39") + } + , __ins) + } + companion object { + val styles: Map>> by lazy { + _nCS(_uA( + styles0 + )) + } + val styles0: Map>> + get() { + return _uM("uni-row" to _pS(_uM("flexDirection" to "row")), "uni-column" to _pS(_uM("flexDirection" to "column"))) + } + } +} +val GenAppClass = CreateVueAppComponent(GenApp::class.java, fun(): VueComponentOptions { + return VueComponentOptions(type = "app", name = "", inheritAttrs = true, inject = Map(), props = Map(), propsNeedCastKeys = _uA(), emits = Map(), components = Map(), styles = GenApp.styles) +} +, fun(instance): GenApp { + return GenApp(instance) +} +) +open class AutoDiscoverAllResult ( + @JsonNotNull + open var services: UTSArray, + @JsonNotNull + open var characteristics: UTSArray, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("AutoDiscoverAllResult", "uni_modules/ak-sbsrv/utssdk/interface.uts", 13, 13) + } +} +open class BleCharacteristicProperties ( + @JsonNotNull + open var read: Boolean = false, + @JsonNotNull + open var write: Boolean = false, + @JsonNotNull + open var notify: Boolean = false, + @JsonNotNull + open var indicate: Boolean = false, + open var writeWithoutResponse: Boolean? = null, + open var canRead: Boolean? = null, + open var canWrite: Boolean? = null, + open var canNotify: Boolean? = null, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleCharacteristicProperties", "uni_modules/ak-sbsrv/utssdk/interface.uts", 23, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return BleCharacteristicPropertiesReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class BleCharacteristicPropertiesReactiveObject : BleCharacteristicProperties, IUTSReactive { + override var __v_raw: BleCharacteristicProperties + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: BleCharacteristicProperties, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(read = __v_raw.read, write = __v_raw.write, notify = __v_raw.notify, indicate = __v_raw.indicate, writeWithoutResponse = __v_raw.writeWithoutResponse, canRead = __v_raw.canRead, canWrite = __v_raw.canWrite, canNotify = __v_raw.canNotify) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): BleCharacteristicPropertiesReactiveObject { + return BleCharacteristicPropertiesReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var read: Boolean + get() { + return _tRG(__v_raw, "read", __v_raw.read, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("read")) { + return + } + val oldValue = __v_raw.read + __v_raw.read = value + _tRS(__v_raw, "read", oldValue, value) + } + override var write: Boolean + get() { + return _tRG(__v_raw, "write", __v_raw.write, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("write")) { + return + } + val oldValue = __v_raw.write + __v_raw.write = value + _tRS(__v_raw, "write", oldValue, value) + } + override var notify: Boolean + get() { + return _tRG(__v_raw, "notify", __v_raw.notify, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("notify")) { + return + } + val oldValue = __v_raw.notify + __v_raw.notify = value + _tRS(__v_raw, "notify", oldValue, value) + } + override var indicate: Boolean + get() { + return _tRG(__v_raw, "indicate", __v_raw.indicate, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("indicate")) { + return + } + val oldValue = __v_raw.indicate + __v_raw.indicate = value + _tRS(__v_raw, "indicate", oldValue, value) + } + override var writeWithoutResponse: Boolean? + get() { + return _tRG(__v_raw, "writeWithoutResponse", __v_raw.writeWithoutResponse, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("writeWithoutResponse")) { + return + } + val oldValue = __v_raw.writeWithoutResponse + __v_raw.writeWithoutResponse = value + _tRS(__v_raw, "writeWithoutResponse", oldValue, value) + } + override var canRead: Boolean? + get() { + return _tRG(__v_raw, "canRead", __v_raw.canRead, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("canRead")) { + return + } + val oldValue = __v_raw.canRead + __v_raw.canRead = value + _tRS(__v_raw, "canRead", oldValue, value) + } + override var canWrite: Boolean? + get() { + return _tRG(__v_raw, "canWrite", __v_raw.canWrite, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("canWrite")) { + return + } + val oldValue = __v_raw.canWrite + __v_raw.canWrite = value + _tRS(__v_raw, "canWrite", oldValue, value) + } + override var canNotify: Boolean? + get() { + return _tRG(__v_raw, "canNotify", __v_raw.canNotify, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("canNotify")) { + return + } + val oldValue = __v_raw.canNotify + __v_raw.canNotify = value + _tRS(__v_raw, "canNotify", oldValue, value) + } +} +open class BleError ( + @JsonNotNull + open var errCode: Number, + @JsonNotNull + open var errMsg: String, + open var errSubject: String? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleError", "uni_modules/ak-sbsrv/utssdk/interface.uts", 57, 13) + } +} +open class WriteCharacteristicOptions ( + open var waitForResponse: Boolean? = null, + open var maxAttempts: Number? = null, + open var retryDelayMs: Number? = null, + open var giveupTimeoutMs: Number? = null, + open var forceWriteTypeNoResponse: Boolean? = null, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("WriteCharacteristicOptions", "uni_modules/ak-sbsrv/utssdk/interface.uts", 98, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return WriteCharacteristicOptionsReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class WriteCharacteristicOptionsReactiveObject : WriteCharacteristicOptions, IUTSReactive { + override var __v_raw: WriteCharacteristicOptions + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: WriteCharacteristicOptions, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(waitForResponse = __v_raw.waitForResponse, maxAttempts = __v_raw.maxAttempts, retryDelayMs = __v_raw.retryDelayMs, giveupTimeoutMs = __v_raw.giveupTimeoutMs, forceWriteTypeNoResponse = __v_raw.forceWriteTypeNoResponse) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): WriteCharacteristicOptionsReactiveObject { + return WriteCharacteristicOptionsReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var waitForResponse: Boolean? + get() { + return _tRG(__v_raw, "waitForResponse", __v_raw.waitForResponse, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("waitForResponse")) { + return + } + val oldValue = __v_raw.waitForResponse + __v_raw.waitForResponse = value + _tRS(__v_raw, "waitForResponse", oldValue, value) + } + override var maxAttempts: Number? + get() { + return _tRG(__v_raw, "maxAttempts", __v_raw.maxAttempts, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("maxAttempts")) { + return + } + val oldValue = __v_raw.maxAttempts + __v_raw.maxAttempts = value + _tRS(__v_raw, "maxAttempts", oldValue, value) + } + override var retryDelayMs: Number? + get() { + return _tRG(__v_raw, "retryDelayMs", __v_raw.retryDelayMs, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("retryDelayMs")) { + return + } + val oldValue = __v_raw.retryDelayMs + __v_raw.retryDelayMs = value + _tRS(__v_raw, "retryDelayMs", oldValue, value) + } + override var giveupTimeoutMs: Number? + get() { + return _tRG(__v_raw, "giveupTimeoutMs", __v_raw.giveupTimeoutMs, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("giveupTimeoutMs")) { + return + } + val oldValue = __v_raw.giveupTimeoutMs + __v_raw.giveupTimeoutMs = value + _tRS(__v_raw, "giveupTimeoutMs", oldValue, value) + } + override var forceWriteTypeNoResponse: Boolean? + get() { + return _tRG(__v_raw, "forceWriteTypeNoResponse", __v_raw.forceWriteTypeNoResponse, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("forceWriteTypeNoResponse")) { + return + } + val oldValue = __v_raw.forceWriteTypeNoResponse + __v_raw.forceWriteTypeNoResponse = value + _tRS(__v_raw, "forceWriteTypeNoResponse", oldValue, value) + } +} +typealias BleNotifyCallback = (data: Uint8Array) -> Unit +open class BleService ( + @JsonNotNull + open var uuid: String, + @JsonNotNull + open var isPrimary: Boolean = false, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleService", "uni_modules/ak-sbsrv/utssdk/interface.uts", 166, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return BleServiceReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class BleServiceReactiveObject : BleService, IUTSReactive { + override var __v_raw: BleService + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: BleService, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(uuid = __v_raw.uuid, isPrimary = __v_raw.isPrimary) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): BleServiceReactiveObject { + return BleServiceReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var uuid: String + get() { + return _tRG(__v_raw, "uuid", __v_raw.uuid, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("uuid")) { + return + } + val oldValue = __v_raw.uuid + __v_raw.uuid = value + _tRS(__v_raw, "uuid", oldValue, value) + } + override var isPrimary: Boolean + get() { + return _tRG(__v_raw, "isPrimary", __v_raw.isPrimary, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("isPrimary")) { + return + } + val oldValue = __v_raw.isPrimary + __v_raw.isPrimary = value + _tRS(__v_raw, "isPrimary", oldValue, value) + } +} +open class BleCharacteristic ( + @JsonNotNull + open var uuid: String, + @JsonNotNull + open var service: BleService, + @JsonNotNull + open var properties: BleCharacteristicProperties, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleCharacteristic", "uni_modules/ak-sbsrv/utssdk/interface.uts", 171, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return BleCharacteristicReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class BleCharacteristicReactiveObject : BleCharacteristic, IUTSReactive { + override var __v_raw: BleCharacteristic + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: BleCharacteristic, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(uuid = __v_raw.uuid, service = __v_raw.service, properties = __v_raw.properties) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): BleCharacteristicReactiveObject { + return BleCharacteristicReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var uuid: String + get() { + return _tRG(__v_raw, "uuid", __v_raw.uuid, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("uuid")) { + return + } + val oldValue = __v_raw.uuid + __v_raw.uuid = value + _tRS(__v_raw, "uuid", oldValue, value) + } + override var service: BleService + get() { + return _tRG(__v_raw, "service", __v_raw.service, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("service")) { + return + } + val oldValue = __v_raw.service + __v_raw.service = value + _tRS(__v_raw, "service", oldValue, value) + } + override var properties: BleCharacteristicProperties + get() { + return _tRG(__v_raw, "properties", __v_raw.properties, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("properties")) { + return + } + val oldValue = __v_raw.properties + __v_raw.properties = value + _tRS(__v_raw, "properties", oldValue, value) + } +} +open class BleDevice ( + @JsonNotNull + open var deviceId: String, + @JsonNotNull + open var name: String, + open var rssi: Number? = null, + open var lastSeen: Number? = null, + open var serviceId: String? = null, + open var writeCharId: String? = null, + open var notifyCharId: String? = null, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleDevice", "uni_modules/ak-sbsrv/utssdk/interface.uts", 183, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return BleDeviceReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class BleDeviceReactiveObject : BleDevice, IUTSReactive { + override var __v_raw: BleDevice + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: BleDevice, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(deviceId = __v_raw.deviceId, name = __v_raw.name, rssi = __v_raw.rssi, lastSeen = __v_raw.lastSeen, serviceId = __v_raw.serviceId, writeCharId = __v_raw.writeCharId, notifyCharId = __v_raw.notifyCharId) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): BleDeviceReactiveObject { + return BleDeviceReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var deviceId: String + get() { + return _tRG(__v_raw, "deviceId", __v_raw.deviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("deviceId")) { + return + } + val oldValue = __v_raw.deviceId + __v_raw.deviceId = value + _tRS(__v_raw, "deviceId", oldValue, value) + } + override var name: String + get() { + return _tRG(__v_raw, "name", __v_raw.name, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("name")) { + return + } + val oldValue = __v_raw.name + __v_raw.name = value + _tRS(__v_raw, "name", oldValue, value) + } + override var rssi: Number? + get() { + return _tRG(__v_raw, "rssi", __v_raw.rssi, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("rssi")) { + return + } + val oldValue = __v_raw.rssi + __v_raw.rssi = value + _tRS(__v_raw, "rssi", oldValue, value) + } + override var lastSeen: Number? + get() { + return _tRG(__v_raw, "lastSeen", __v_raw.lastSeen, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("lastSeen")) { + return + } + val oldValue = __v_raw.lastSeen + __v_raw.lastSeen = value + _tRS(__v_raw, "lastSeen", oldValue, value) + } + override var serviceId: String? + get() { + return _tRG(__v_raw, "serviceId", __v_raw.serviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("serviceId")) { + return + } + val oldValue = __v_raw.serviceId + __v_raw.serviceId = value + _tRS(__v_raw, "serviceId", oldValue, value) + } + override var writeCharId: String? + get() { + return _tRG(__v_raw, "writeCharId", __v_raw.writeCharId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("writeCharId")) { + return + } + val oldValue = __v_raw.writeCharId + __v_raw.writeCharId = value + _tRS(__v_raw, "writeCharId", oldValue, value) + } + override var notifyCharId: String? + get() { + return _tRG(__v_raw, "notifyCharId", __v_raw.notifyCharId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("notifyCharId")) { + return + } + val oldValue = __v_raw.notifyCharId + __v_raw.notifyCharId = value + _tRS(__v_raw, "notifyCharId", oldValue, value) + } +} +open class BleOptions ( + open var timeout: Number? = null, + open var success: ((result: Any) -> Unit)? = null, + open var fail: ((error: Any) -> Unit)? = null, + open var complete: (() -> Unit)? = null, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleOptions", "uni_modules/ak-sbsrv/utssdk/interface.uts", 194, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return BleOptionsReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class BleOptionsReactiveObject : BleOptions, IUTSReactive { + override var __v_raw: BleOptions + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: BleOptions, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(timeout = __v_raw.timeout, success = __v_raw.success, fail = __v_raw.fail, complete = __v_raw.complete) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): BleOptionsReactiveObject { + return BleOptionsReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var timeout: Number? + get() { + return _tRG(__v_raw, "timeout", __v_raw.timeout, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("timeout")) { + return + } + val oldValue = __v_raw.timeout + __v_raw.timeout = value + _tRS(__v_raw, "timeout", oldValue, value) + } +} +typealias BleConnectionState = Number +open class BleConnectOptionsExt ( + open var timeout: Number? = null, + open var services: UTSArray? = null, + open var requireResponse: Boolean? = null, + open var autoReconnect: Boolean? = null, + open var maxAttempts: Number? = null, + open var interval: Number? = null, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleConnectOptionsExt", "uni_modules/ak-sbsrv/utssdk/interface.uts", 201, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return BleConnectOptionsExtReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class BleConnectOptionsExtReactiveObject : BleConnectOptionsExt, IUTSReactive { + override var __v_raw: BleConnectOptionsExt + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: BleConnectOptionsExt, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(timeout = __v_raw.timeout, services = __v_raw.services, requireResponse = __v_raw.requireResponse, autoReconnect = __v_raw.autoReconnect, maxAttempts = __v_raw.maxAttempts, interval = __v_raw.interval) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): BleConnectOptionsExtReactiveObject { + return BleConnectOptionsExtReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var timeout: Number? + get() { + return _tRG(__v_raw, "timeout", __v_raw.timeout, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("timeout")) { + return + } + val oldValue = __v_raw.timeout + __v_raw.timeout = value + _tRS(__v_raw, "timeout", oldValue, value) + } + override var services: UTSArray? + get() { + return _tRG(__v_raw, "services", __v_raw.services, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("services")) { + return + } + val oldValue = __v_raw.services + __v_raw.services = value + _tRS(__v_raw, "services", oldValue, value) + } + override var requireResponse: Boolean? + get() { + return _tRG(__v_raw, "requireResponse", __v_raw.requireResponse, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("requireResponse")) { + return + } + val oldValue = __v_raw.requireResponse + __v_raw.requireResponse = value + _tRS(__v_raw, "requireResponse", oldValue, value) + } + override var autoReconnect: Boolean? + get() { + return _tRG(__v_raw, "autoReconnect", __v_raw.autoReconnect, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("autoReconnect")) { + return + } + val oldValue = __v_raw.autoReconnect + __v_raw.autoReconnect = value + _tRS(__v_raw, "autoReconnect", oldValue, value) + } + override var maxAttempts: Number? + get() { + return _tRG(__v_raw, "maxAttempts", __v_raw.maxAttempts, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("maxAttempts")) { + return + } + val oldValue = __v_raw.maxAttempts + __v_raw.maxAttempts = value + _tRS(__v_raw, "maxAttempts", oldValue, value) + } + override var interval: Number? + get() { + return _tRG(__v_raw, "interval", __v_raw.interval, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("interval")) { + return + } + val oldValue = __v_raw.interval + __v_raw.interval = value + _tRS(__v_raw, "interval", oldValue, value) + } +} +typealias BleConnectionStateChangeCallback = (deviceId: String, state: BleConnectionState) -> Unit +typealias BleProtocolType = String +typealias BleEvent = String +open class BleEventPayload ( + @JsonNotNull + open var event: BleEvent, + open var device: BleDevice? = null, + open var protocol: BleProtocolType? = null, + open var state: BleConnectionState? = null, + open var data: Any? = null, + open var format: String? = null, + open var error: BleError? = null, + open var extra: Any? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BleEventPayload", "uni_modules/ak-sbsrv/utssdk/interface.uts", 245, 13) + } +} +typealias BleEventCallback = (payload: BleEventPayload) -> Unit +open class MultiProtocolDevice ( + @JsonNotNull + open var deviceId: String, + @JsonNotNull + open var name: String, + open var rssi: Number? = null, + @JsonNotNull + open var protocol: BleProtocolType, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("MultiProtocolDevice", "uni_modules/ak-sbsrv/utssdk/interface.uts", 258, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return MultiProtocolDeviceReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class MultiProtocolDeviceReactiveObject : MultiProtocolDevice, IUTSReactive { + override var __v_raw: MultiProtocolDevice + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: MultiProtocolDevice, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(deviceId = __v_raw.deviceId, name = __v_raw.name, rssi = __v_raw.rssi, protocol = __v_raw.protocol) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): MultiProtocolDeviceReactiveObject { + return MultiProtocolDeviceReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var deviceId: String + get() { + return _tRG(__v_raw, "deviceId", __v_raw.deviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("deviceId")) { + return + } + val oldValue = __v_raw.deviceId + __v_raw.deviceId = value + _tRS(__v_raw, "deviceId", oldValue, value) + } + override var name: String + get() { + return _tRG(__v_raw, "name", __v_raw.name, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("name")) { + return + } + val oldValue = __v_raw.name + __v_raw.name = value + _tRS(__v_raw, "name", oldValue, value) + } + override var rssi: Number? + get() { + return _tRG(__v_raw, "rssi", __v_raw.rssi, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("rssi")) { + return + } + val oldValue = __v_raw.rssi + __v_raw.rssi = value + _tRS(__v_raw, "rssi", oldValue, value) + } + override var protocol: BleProtocolType + get() { + return _tRG(__v_raw, "protocol", __v_raw.protocol, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("protocol")) { + return + } + val oldValue = __v_raw.protocol + __v_raw.protocol = value + _tRS(__v_raw, "protocol", oldValue, value) + } +} +open class ScanDevicesOptions ( + open var protocols: UTSArray? = null, + open var optionalServices: UTSArray? = null, + open var timeout: Number? = null, + open var onDeviceFound: ((device: BleDevice) -> Unit)? = null, + open var onScanFinished: (() -> Unit)? = null, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("ScanDevicesOptions", "uni_modules/ak-sbsrv/utssdk/interface.uts", 264, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return ScanDevicesOptionsReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class ScanDevicesOptionsReactiveObject : ScanDevicesOptions, IUTSReactive { + override var __v_raw: ScanDevicesOptions + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: ScanDevicesOptions, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(protocols = __v_raw.protocols, optionalServices = __v_raw.optionalServices, timeout = __v_raw.timeout, onDeviceFound = __v_raw.onDeviceFound, onScanFinished = __v_raw.onScanFinished) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): ScanDevicesOptionsReactiveObject { + return ScanDevicesOptionsReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var protocols: UTSArray? + get() { + return _tRG(__v_raw, "protocols", __v_raw.protocols, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("protocols")) { + return + } + val oldValue = __v_raw.protocols + __v_raw.protocols = value + _tRS(__v_raw, "protocols", oldValue, value) + } + override var optionalServices: UTSArray? + get() { + return _tRG(__v_raw, "optionalServices", __v_raw.optionalServices, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("optionalServices")) { + return + } + val oldValue = __v_raw.optionalServices + __v_raw.optionalServices = value + _tRS(__v_raw, "optionalServices", oldValue, value) + } + override var timeout: Number? + get() { + return _tRG(__v_raw, "timeout", __v_raw.timeout, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("timeout")) { + return + } + val oldValue = __v_raw.timeout + __v_raw.timeout = value + _tRS(__v_raw, "timeout", oldValue, value) + } +} +open class SendDataPayload ( + @JsonNotNull + open var deviceId: String, + open var serviceId: String? = null, + open var characteristicId: String? = null, + @JsonNotNull + open var data: Any, + open var format: Number? = null, + @JsonNotNull + open var protocol: BleProtocolType, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("SendDataPayload", "uni_modules/ak-sbsrv/utssdk/interface.uts", 272, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return SendDataPayloadReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class SendDataPayloadReactiveObject : SendDataPayload, IUTSReactive { + override var __v_raw: SendDataPayload + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: SendDataPayload, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(deviceId = __v_raw.deviceId, serviceId = __v_raw.serviceId, characteristicId = __v_raw.characteristicId, data = __v_raw.data, format = __v_raw.format, protocol = __v_raw.protocol) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): SendDataPayloadReactiveObject { + return SendDataPayloadReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var deviceId: String + get() { + return _tRG(__v_raw, "deviceId", __v_raw.deviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("deviceId")) { + return + } + val oldValue = __v_raw.deviceId + __v_raw.deviceId = value + _tRS(__v_raw, "deviceId", oldValue, value) + } + override var serviceId: String? + get() { + return _tRG(__v_raw, "serviceId", __v_raw.serviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("serviceId")) { + return + } + val oldValue = __v_raw.serviceId + __v_raw.serviceId = value + _tRS(__v_raw, "serviceId", oldValue, value) + } + override var characteristicId: String? + get() { + return _tRG(__v_raw, "characteristicId", __v_raw.characteristicId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("characteristicId")) { + return + } + val oldValue = __v_raw.characteristicId + __v_raw.characteristicId = value + _tRS(__v_raw, "characteristicId", oldValue, value) + } + override var data: Any + get() { + return _tRG(__v_raw, "data", __v_raw.data, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("data")) { + return + } + val oldValue = __v_raw.data + __v_raw.data = value + _tRS(__v_raw, "data", oldValue, value) + } + override var format: Number? + get() { + return _tRG(__v_raw, "format", __v_raw.format, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("format")) { + return + } + val oldValue = __v_raw.format + __v_raw.format = value + _tRS(__v_raw, "format", oldValue, value) + } + override var protocol: BleProtocolType + get() { + return _tRG(__v_raw, "protocol", __v_raw.protocol, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("protocol")) { + return + } + val oldValue = __v_raw.protocol + __v_raw.protocol = value + _tRS(__v_raw, "protocol", oldValue, value) + } +} +open class AutoBleInterfaces ( + @JsonNotNull + open var serviceId: String, + @JsonNotNull + open var writeCharId: String, + @JsonNotNull + open var notifyCharId: String, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("AutoBleInterfaces", "uni_modules/ak-sbsrv/utssdk/interface.uts", 292, 13) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return AutoBleInterfacesReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class AutoBleInterfacesReactiveObject : AutoBleInterfaces, IUTSReactive { + override var __v_raw: AutoBleInterfaces + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: AutoBleInterfaces, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(serviceId = __v_raw.serviceId, writeCharId = __v_raw.writeCharId, notifyCharId = __v_raw.notifyCharId) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): AutoBleInterfacesReactiveObject { + return AutoBleInterfacesReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var serviceId: String + get() { + return _tRG(__v_raw, "serviceId", __v_raw.serviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("serviceId")) { + return + } + val oldValue = __v_raw.serviceId + __v_raw.serviceId = value + _tRS(__v_raw, "serviceId", oldValue, value) + } + override var writeCharId: String + get() { + return _tRG(__v_raw, "writeCharId", __v_raw.writeCharId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("writeCharId")) { + return + } + val oldValue = __v_raw.writeCharId + __v_raw.writeCharId = value + _tRS(__v_raw, "writeCharId", oldValue, value) + } + override var notifyCharId: String + get() { + return _tRG(__v_raw, "notifyCharId", __v_raw.notifyCharId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("notifyCharId")) { + return + } + val oldValue = __v_raw.notifyCharId + __v_raw.notifyCharId = value + _tRS(__v_raw, "notifyCharId", oldValue, value) + } +} +open class ControlParserResult ( + @JsonNotNull + open var type: String, + open var progress: Number? = null, + open var error: Any? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("ControlParserResult", "uni_modules/ak-sbsrv/utssdk/interface.uts", 304, 13) + } +} +open class DfuOptions ( + open var mtu: Number? = null, + open var useNordic: Boolean? = null, + open var waitForResponse: Boolean? = null, + open var maxOutstanding: Number? = null, + open var writeSleepMs: Number? = null, + open var writeRetryDelayMs: Number? = null, + open var writeMaxAttempts: Number? = null, + open var writeGiveupTimeoutMs: Number? = null, + open var prn: Number? = null, + open var prnTimeoutMs: Number? = null, + open var disablePrnOnTimeout: Boolean? = null, + open var drainOutstandingTimeoutMs: Number? = null, + open var controlTimeout: Number? = null, + open var onProgress: ((percent: Number) -> Unit)? = null, + open var onLog: ((message: String) -> Unit)? = null, + open var controlParser: ((data: Uint8Array) -> ControlParserResult?)? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("DfuOptions", "uni_modules/ak-sbsrv/utssdk/interface.uts", 310, 13) + } +} +typealias ByteArray = Any +typealias BleDataReceivedCallback = (data: Uint8Array) -> Unit +open class BluetoothService : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BluetoothService", "uni_modules/ak-sbsrv/utssdk/interface.uts", 378, 14) + } + open fun on(event: Any, callback: BleEventCallback): Unit {} + open fun off(event: Any, callback: BleEventCallback?): Unit {} + open fun scanDevices(options: ScanDevicesOptions?): UTSPromise { + return UTSPromise.resolve() + } + open fun connectDevice(deviceId: String, protocol: String?, options: BleConnectOptionsExt?): UTSPromise { + return UTSPromise.resolve() + } + open fun disconnectDevice(deviceId: String, protocol: String?): UTSPromise { + return UTSPromise.resolve() + } + open fun getConnectedDevices(): UTSArray { + return _uA() + } + open fun getServices(deviceId: String): UTSPromise> { + return UTSPromise.resolve(_uA()) + } + open fun getCharacteristics(deviceId: String, serviceId: String): UTSPromise> { + return UTSPromise.resolve(_uA()) + } + open fun readCharacteristic(deviceId: String, serviceId: String, characteristicId: String): UTSPromise { + return UTSPromise.resolve(ArrayBuffer(0)) + } + open fun writeCharacteristic(deviceId: String, serviceId: String, characteristicId: String, value: Any, options: WriteCharacteristicOptions?): UTSPromise { + return UTSPromise.resolve(true) + } + open fun subscribeCharacteristic(deviceId: String, serviceId: String, characteristicId: String, callback: BleNotifyCallback): UTSPromise { + return UTSPromise.resolve() + } + open fun unsubscribeCharacteristic(deviceId: String, serviceId: String, characteristicId: String): UTSPromise { + return UTSPromise.resolve() + } + open fun getAutoBleInterfaces(deviceId: String): UTSPromise { + val res = AutoBleInterfaces(serviceId = "", writeCharId = "", notifyCharId = "") + return UTSPromise.resolve(res) + } +} +open class ProtocolHandler : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("ProtocolHandler", "uni_modules/ak-sbsrv/utssdk/protocol_handler.uts", 6, 14) + } + open var bluetoothService: BluetoothService? = null + open var protocol: BleProtocolType = "standard" + open var deviceId: String? = null + open var serviceId: String? = null + open var writeCharId: String? = null + open var notifyCharId: String? = null + open var initialized: Boolean = false + constructor(bluetoothService: BluetoothService?){ + if (bluetoothService != null) { + this.bluetoothService = bluetoothService + } + } + open fun setConnectionParameters(deviceId: String, serviceId: String, writeCharId: String, notifyCharId: String) { + this.deviceId = deviceId + this.serviceId = serviceId + this.writeCharId = writeCharId + this.notifyCharId = notifyCharId + } + open fun initialize(): UTSPromise { + return wrapUTSPromise(suspend w@{ + try { + this.initialized = true + return@w + } + catch (e: Throwable) { + throw e + } + }) + } + open fun scanDevices(options: ScanDevicesOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w + }) + } + open fun connect(device: BleDevice, options: BleConnectOptionsExt?): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w + }) + } + open fun disconnect(device: BleDevice): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w + }) + } + open fun sendData(device: BleDevice, payload: SendDataPayload?, options: BleOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w + }) + } + open fun autoConnect(device: BleDevice, options: BleConnectOptionsExt?): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w AutoBleInterfaces(serviceId = "", writeCharId = "", notifyCharId = "") + }) + } + open fun testBatteryLevel(): UTSPromise { + return wrapUTSPromise(suspend w@{ + if (this.deviceId == null) { + throw UTSError("deviceId not set") + } + val deviceId = this.deviceId!! + if (this.bluetoothService == null) { + throw UTSError("bluetoothService not set") + } + val services = await(this.bluetoothService!!.getServices(deviceId)) + var found: BleService? = null + run { + var i: Number = 0 + while(i < services.length){ + val s = services[i] + val uuidCandidate: String? = if (s != null && s.uuid != null) { + s.uuid + } else { + null + } + val uuid = if (uuidCandidate != null) { + ("" + uuidCandidate).toLowerCase() + } else { + "" + } + if (uuid.indexOf("180f") !== -1) { + found = s + break + } + i++ + } + } + if (found == null) { + return@w 0 + } + val foundUuid = found!!.uuid + val charsRaw = await(this.bluetoothService!!.getCharacteristics(deviceId, foundUuid)) + val chars: UTSArray = charsRaw + val batChar = chars.find(fun(c: BleCharacteristic): Boolean { + return ((c.properties != null && c.properties.read) || (c.uuid != null && ("" + c.uuid).toLowerCase().includes("2a19"))) + } + ) + if (batChar == null) { + return@w 0 + } + val buf = await(this.bluetoothService!!.readCharacteristic(deviceId, foundUuid, batChar.uuid)) + val arr = Uint8Array(buf) + if (arr.length > 0) { + return@w arr[0] + } + return@w 0 + }) + } + open fun testVersionInfo(hw: Boolean): UTSPromise { + return wrapUTSPromise(suspend w@{ + val deviceId = this.deviceId + if (deviceId == null) { + return@w "" + } + if (this.bluetoothService == null) { + return@w "" + } + val _services = await(this.bluetoothService!!.getServices(deviceId)) + val services2: UTSArray = _services + var found2: BleService? = null + run { + var i: Number = 0 + while(i < services2.length){ + val s = services2[i] + val uuidCandidate: String? = if (s != null && s.uuid != null) { + s.uuid + } else { + null + } + val uuid = if (uuidCandidate != null) { + ("" + uuidCandidate).toLowerCase() + } else { + "" + } + if (uuid.indexOf("180a") !== -1) { + found2 = s + break + } + i++ + } + } + if (found2 == null) { + return@w "" + } + val _found2 = found2 + val found2Uuid = _found2!!.uuid + val chars = await(this.bluetoothService!!.getCharacteristics(deviceId, found2Uuid)) + val target = chars.find(fun(c): Boolean { + val id = ("" + c.uuid).toLowerCase() + if (hw) { + return id.includes("2a27") || id.includes("hardware") + } + return id.includes("2a26") || id.includes("software") + } + ) + if (target == null) { + return@w "" + } + val buf = await(this.bluetoothService!!.readCharacteristic(deviceId, found2Uuid, target.uuid)) + try { + return@w TextDecoder().decode(Uint8Array(buf)) + } + catch (e: Throwable) { + return@w "" + } + }) + } +} +enum class AkBluetoothErrorCode(override val value: Int) : UTSEnumInt { + UnknownError(0), + DeviceNotFound(1), + ServiceNotFound(2), + CharacteristicNotFound(3), + ConnectionTimeout(4), + Unspecified(99) +} +open class AkBleErrorImpl : UTSError, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("AkBleErrorImpl", "uni_modules/ak-sbsrv/utssdk/unierror.uts", 12, 14) + } + open var code: AkBluetoothErrorCode + open var detail: Any? + constructor(code: AkBluetoothErrorCode, message: String?, detail: Any? = null) : super(message ?: AkBleErrorImpl.defaultMessage(code)) { + this.name = "AkBleError" + this.code = code + this.detail = detail + } + companion object { + fun defaultMessage(code: AkBluetoothErrorCode): String { + when (code) { + AkBluetoothErrorCode.DeviceNotFound -> + return "Device not found" + AkBluetoothErrorCode.ServiceNotFound -> + return "Service not found" + AkBluetoothErrorCode.CharacteristicNotFound -> + return "Characteristic not found" + AkBluetoothErrorCode.ConnectionTimeout -> + return "Connection timed out" + AkBluetoothErrorCode.UnknownError -> + return "Unknown Bluetooth error" + else -> + return "Unknown Bluetooth error" + } + } + } +} +interface PendingConnect { + var resolve: () -> Unit + var reject: (err: Any?) -> Unit + var timer: Number? +} +open class PendingConnectImpl : PendingConnect, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("PendingConnectImpl", "uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts", 23, 7) + } + override var resolve: () -> Unit + override var reject: (err: Any?) -> Unit + override var timer: Number? + constructor(resolve: () -> Unit, reject: (err: Any?) -> Unit, timer: Number?){ + this.resolve = resolve + this.reject = reject + this.timer = timer + } +} +val pendingConnects = Map() +val STATE_DISCONNECTED: Number = 0 +val STATE_CONNECTING: Number = 1 +val STATE_CONNECTED: Number = 2 +open class DeviceManager : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("DeviceManager", "uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts", 40, 14) + } + private var devices = Map() + private var connectionStates = Map() + private var connectionStateChangeListeners: UTSArray = _uA() + private var gattMap = Map() + private var scanCallback: ScanCallback? = null + private var isScanning: Boolean = false + private constructor(){} + open fun startScan(options: ScanDevicesOptions): Unit { + console.log("ak startscan now", " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:60") + val adapter = this.getBluetoothAdapter() + if (adapter == null) { + throw UTSError("未找到蓝牙适配器") + } + if (!adapter.isEnabled) { + try { + adapter.enable() + } + catch (e: Throwable) {} + setTimeout(fun(){ + if (!adapter.isEnabled) { + throw UTSError("蓝牙未开启") + } + } + , 1500) + throw UTSError("正在开启蓝牙,请重试") + } + val foundDevices = this.devices + open class MyScanCallback : ScanCallback, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("MyScanCallback", "uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts", 77, 15) + } + private var foundDevices: Map + private var onDeviceFound: (device: BleDevice) -> Unit + constructor(foundDevices: Map, onDeviceFound: (device: BleDevice) -> Unit) : super() { + this.foundDevices = foundDevices + this.onDeviceFound = onDeviceFound + } + override fun onScanResult(callbackType: Int, result: ScanResult): Unit { + val device = result.getDevice() + if (device != null) { + val deviceId = device.getAddress() + var bleDevice = foundDevices.get(deviceId) + if (bleDevice == null) { + bleDevice = BleDevice(deviceId = deviceId, name = device.getName() ?: "Unknown", rssi = result.getRssi(), lastSeen = Date.now()) + foundDevices.set(deviceId, bleDevice) + this.onDeviceFound(bleDevice) + } else { + bleDevice.rssi = result.getRssi() + bleDevice.name = device.getName() ?: bleDevice.name + bleDevice.lastSeen = Date.now() + } + } + } + override fun onScanFailed(errorCode: Int): Unit { + console.log("ak scan fail", " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:114") + } + } + this.scanCallback = MyScanCallback(foundDevices, options.onDeviceFound ?: (fun(_device){})) + val scanner = adapter.getBluetoothLeScanner() + if (scanner == null) { + throw UTSError("无法获取扫描器") + } + val scanSettings = ScanSettings.Builder().setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY).build() + scanner.startScan(null, scanSettings, this.scanCallback) + this.isScanning = true + Handler(Looper.getMainLooper()).postDelayed(fun(){ + if (this.isScanning && this.scanCallback != null) { + scanner.stopScan(this.scanCallback) + this.isScanning = false + if (options.onScanFinished != null) { + options.onScanFinished?.invoke() + } + } + } + , 40000) + } + open fun connectDevice(deviceId: String, options: BleConnectOptionsExt?): UTSPromise { + return wrapUTSPromise(suspend w@{ + console.log("[AKBLE] connectDevice called, deviceId:", deviceId, "options:", options, "connectionStates:", " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:139") + val adapter = this.getBluetoothAdapter() + if (adapter == null) { + console.error("[AKBLE] connectDevice failed: 蓝牙适配器不可用", " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:142") + throw UTSError("蓝牙适配器不可用") + } + val device = adapter.getRemoteDevice(deviceId) + if (device == null) { + console.error("[AKBLE] connectDevice failed: 未找到设备", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:147") + throw UTSError("未找到设备") + } + this.connectionStates.set(deviceId, STATE_CONNECTING) + console.log("[AKBLE] connectDevice set STATE_CONNECTING, deviceId:", deviceId, "connectionStates:", " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:151") + this.emitConnectionStateChange(deviceId, STATE_CONNECTING) + val activity = UTSAndroid.getUniActivity() + val timeout = options?.timeout ?: 15000 + val key = "" + deviceId + "|connect" + return@w UTSPromise(fun(resolve, reject){ + val timer = setTimeout(fun(){ + console.error("[AKBLE] connectDevice 超时:", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:158") + pendingConnects.`delete`(key) + this.connectionStates.set(deviceId, STATE_DISCONNECTED) + this.gattMap.set(deviceId, null) + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED) + reject(UTSError("连接超时")) + } + , timeout) + val resolveAdapter = fun(){ + console.log("[AKBLE] connectDevice resolveAdapter:", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:168") + resolve(Unit) + } + val rejectAdapter = fun(err: Any?){ + console.error("[AKBLE] connectDevice rejectAdapter:", deviceId, err, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:172") + reject(err) + } + pendingConnects.set(key, PendingConnectImpl(resolveAdapter, rejectAdapter, timer)) + try { + console.log("[AKBLE] connectGatt 调用前:", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:178") + val gatt = device.connectGatt(activity, false, gattCallback) + this.gattMap.set(deviceId, gatt) + console.log("[AKBLE] connectGatt 调用后:", deviceId, gatt, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:181") + } + catch (e: Throwable) { + console.error("[AKBLE] connectGatt 异常:", deviceId, e, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:183") + clearTimeout(timer) + pendingConnects.`delete`(key) + this.connectionStates.set(deviceId, STATE_DISCONNECTED) + this.gattMap.set(deviceId, null) + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED) + reject(e) + } + } + ) + }) + } + open fun disconnectDevice(deviceId: String, isActive: Boolean = true): UTSPromise { + return wrapUTSPromise(suspend w@{ + console.log("[AKBLE] disconnectDevice called, deviceId:", deviceId, "isActive:", isActive, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:223") + var gatt = this.gattMap.get(deviceId) + if (gatt != null) { + gatt.disconnect() + gatt.close() + this.gattMap.set(deviceId, null) + this.connectionStates.set(deviceId, STATE_DISCONNECTED) + console.log("[AKBLE] disconnectDevice set STATE_DISCONNECTED, deviceId:", deviceId, "connectionStates:", " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:231") + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED) + return@w + } else { + console.log("[AKBLE] disconnectDevice: gatt is null, deviceId:", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:235") + return@w + } + }) + } + open fun reconnectDevice(deviceId: String, options: BleConnectOptionsExt?): UTSPromise { + return wrapUTSPromise(suspend w@{ + var attempts: Number = 0 + val maxAttempts = options?.maxAttempts ?: 3 + val interval = options?.interval ?: 3000 + while(attempts < maxAttempts){ + try { + await(this.disconnectDevice(deviceId, false)) + await(this.connectDevice(deviceId, options)) + return@w + } + catch (e: Throwable) { + attempts++ + if (attempts >= maxAttempts) { + throw UTSError("重连失败") + } + await(UTSPromise(fun(resolve, _reject){ + setTimeout(fun(){ + resolve(Unit) + } + , interval) + } + )) + } + } + }) + } + open fun getConnectedDevices(): UTSArray { + val result: UTSArray = _uA() + this.devices.forEach(fun(device, deviceId){ + if (this.connectionStates.get(deviceId) === STATE_CONNECTED) { + result.push(device) + } + } + ) + return result + } + open fun onConnectionStateChange(listener: BleConnectionStateChangeCallback) { + console.log("[AKBLE][LOG] onConnectionStateChange 注册, 当前监听数:", this.connectionStateChangeListeners.length + 1, listener, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:277") + this.connectionStateChangeListeners.push(listener) + } + protected open fun emitConnectionStateChange(deviceId: String, state: BleConnectionState) { + console.log("[AKBLE][LOG] emitConnectionStateChange", deviceId, state, "listeners:", this.connectionStateChangeListeners.length, "connectionStates:", this.connectionStates, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:282") + for(listener in resolveUTSValueIterator(this.connectionStateChangeListeners)){ + try { + console.log("[AKBLE][LOG] emitConnectionStateChange 调用 listener", listener, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:285") + listener(deviceId, state) + } + catch (e: Throwable) { + console.error("[AKBLE][LOG] emitConnectionStateChange listener error", e, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:288") + } + } + } + open fun getGattInstance(deviceId: String): BluetoothGatt? { + return this.gattMap.get(deviceId) ?: null + } + private fun getBluetoothAdapter(): BluetoothAdapter? { + val context = UTSAndroid.getAppContext() + if (context == null) { + return null + } + val manager = context?.getSystemService(Context.BLUETOOTH_SERVICE) as BluetoothManager + return manager.getAdapter() + } + public open fun getDevice(deviceId: String): BleDevice? { + console.log(deviceId, this.devices, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:308") + return this.devices.get(deviceId) ?: null + } + companion object { + private var instance: DeviceManager? = null + fun getInstance(): DeviceManager { + if (DeviceManager.instance == null) { + DeviceManager.instance = DeviceManager() + } + return DeviceManager.instance!! + } + fun handleConnectionStateChange(deviceId: String, newState: Number, error: Any?) { + console.log("[AKBLE] handleConnectionStateChange:", deviceId, "newState:", newState, "error:", error, "pendingConnects:", " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:196") + val key = "" + deviceId + "|connect" + val cb = pendingConnects.get(key) + if (cb != null) { + val timerValue = cb.timer + if (timerValue != null) { + clearTimeout(timerValue) + } + if (newState === STATE_CONNECTED) { + console.log("[AKBLE] handleConnectionStateChange: 连接成功", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:208") + cb.resolve() + } else { + val errorToUse = if (error != null) { + error + } else { + UTSError("连接断开") + } + console.error("[AKBLE] handleConnectionStateChange: 连接失败", deviceId, errorToUse, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:213") + cb.reject(errorToUse) + } + pendingConnects.`delete`(key) + } else { + console.warn("[AKBLE] handleConnectionStateChange: 未找到 pendingConnects", deviceId, newState, " at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:218") + } + } + } +} +fun getFullUuid(shortUuid: String): String { + return "0000" + shortUuid + "-0000-1000-8000-00805f9b34fb" +} +val deviceWriteQueues = Map>() +fun enqueueDeviceWrite(deviceId: String, work: () -> UTSPromise): UTSPromise { + val previous = deviceWriteQueues.get(deviceId) ?: UTSPromise.resolve() + val next = (fun(): UTSPromise { + return wrapUTSPromise(suspend w@{ + try { + await(previous) + } + catch (e: Throwable) {} + return@w await(work()) + }) + } + )() + val queued = next.then(fun(){}, fun(){}) + deviceWriteQueues.set(deviceId, queued) + return next.`finally`(fun(){ + if (deviceWriteQueues.get(deviceId) == queued) { + deviceWriteQueues.`delete`(deviceId) + } + } + ) +} +fun createCharProperties(props: Number): BleCharacteristicProperties { + val result = BleCharacteristicProperties(read = false, write = false, notify = false, indicate = false, canRead = false, canWrite = false, canNotify = false, writeWithoutResponse = false) + result.read = (props and BluetoothGattCharacteristic.PROPERTY_READ) !== 0 + result.write = (props and BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0 + result.notify = (props and BluetoothGattCharacteristic.PROPERTY_NOTIFY) !== 0 + result.indicate = (props and BluetoothGattCharacteristic.PROPERTY_INDICATE) !== 0 + result.writeWithoutResponse = (props and BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0 + result.canRead = result.read + val writeWithoutResponse = result.writeWithoutResponse!! + result.canWrite = (result.write != null && result.write) || (writeWithoutResponse != null && writeWithoutResponse) + result.canNotify = result.notify + return result +} +interface PendingCallback { + var resolve: (data: Any) -> Unit + var reject: (err: Any?) -> Unit + var timer: Number? +} +open class PendingCallbackImpl : PendingCallback, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("PendingCallbackImpl", "uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts", 61, 7) + } + override var resolve: (data: Any) -> Unit + override var reject: (err: Any?) -> Unit + override var timer: Number? + constructor(resolve: (data: Any) -> Unit, reject: (err: Any?) -> Unit, timer: Number?){ + this.resolve = resolve + this.reject = reject + this.timer = timer + } +} +var pendingCallbacks: Map +var notifyCallbacks: Map +val runBlock3 = run { + pendingCallbacks = Map() + notifyCallbacks = Map() +} +val serviceDiscoveryWaiters = Map?, error: UTSError?) -> Unit)>>() +val serviceDiscovered = Map() +val characteristicDiscoveryWaiters = Map?, error: UTSError?) -> Unit)>>() +open class GattCallback : BluetoothGattCallback, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GattCallback", "uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts", 83, 7) + } + constructor() : super() {} + override fun onServicesDiscovered(gatt: BluetoothGatt, status: Int): Unit { + console.log("ak onServicesDiscovered", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:108") + val deviceId = gatt.getDevice().getAddress() + if (status == BluetoothGatt.GATT_SUCCESS) { + console.log("\u670D\u52A1\u53D1\u73B0\u6210\u529F: " + deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:111") + serviceDiscovered.set(deviceId, true) + val waiters = serviceDiscoveryWaiters.get(deviceId) + if (waiters != null && waiters.length > 0) { + val services = gatt.getServices() + val result: UTSArray = _uA() + if (services != null) { + val servicesList = services + val size = servicesList.size + run { + var i: Number = 0 + while(i < size){ + val service = servicesList.get(i as Int) + if (service != null) { + val bleService = BleService(uuid = service.getUuid().toString(), isPrimary = service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY) + result.push(bleService) + } + i++ + } + } + } + run { + var i: Number = 0 + while(i < waiters.length){ + val cb = waiters[i] + if (cb != null) { + cb(result, null) + } + i++ + } + } + serviceDiscoveryWaiters.`delete`(deviceId) + } + } else { + console.log("\u670D\u52A1\u53D1\u73B0\u5931\u8D25: " + deviceId + ", status: " + status, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:139") + val waiters = serviceDiscoveryWaiters.get(deviceId) + if (waiters != null && waiters.length > 0) { + run { + var i: Number = 0 + while(i < waiters.length){ + val cb = waiters[i] + if (cb != null) { + cb(null, UTSError("服务发现失败")) + } + i++ + } + } + serviceDiscoveryWaiters.`delete`(deviceId) + } + } + } + override fun onConnectionStateChange(gatt: BluetoothGatt, status: Int, newState: Int): Unit { + val deviceId = gatt.getDevice().getAddress() + if (newState == BluetoothGatt.STATE_CONNECTED) { + console.log("\u8BBE\u5907\u5DF2\u8FDE\u63A5: " + deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:154") + DeviceManager.handleConnectionStateChange(deviceId, 2, null) + } else if (newState == BluetoothGatt.STATE_DISCONNECTED) { + console.log("\u8BBE\u5907\u5DF2\u65AD\u5F00: " + deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:157") + serviceDiscovered.`delete`(deviceId) + DeviceManager.handleConnectionStateChange(deviceId, 0, null) + } + } + override fun onCharacteristicChanged(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic): Unit { + console.log("ak onCharacteristicChanged", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:163") + val deviceId = gatt.getDevice().getAddress() + val serviceId = characteristic.getService().getUuid().toString() + val charId = characteristic.getUuid().toString() + val key = "" + deviceId + "|" + serviceId + "|" + charId + "|notify" + val callback = notifyCallbacks.get(key) + val value = characteristic.getValue() + console.log("[onCharacteristicChanged]", key, value, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:170") + if (callback != null && value != null) { + val valueLength = value.size + val arr = Uint8Array(valueLength) + run { + var i = 0 as Int + while(i < valueLength){ + val v = value[i as Int] + arr[i] = if (v != null) { + v + } else { + 0 + } + i++ + } + } + console.log("\n INSERT INTO ble_data_log (device_id, service_id, char_id, direction, data, timestamp)\n VALUES ('" + deviceId + "', '" + serviceId + "', '" + charId + "', 'recv', '" + UTSArray.from(arr).join(",") + "', " + Date.now() + ")\n ", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:179") + callback(arr) + } + } + override fun onCharacteristicRead(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int): Unit { + console.log("ak onCharacteristicRead", status, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:188") + val deviceId = gatt.getDevice().getAddress() + val serviceId = characteristic.getService().getUuid().toString() + val charId = characteristic.getUuid().toString() + val key = "" + deviceId + "|" + serviceId + "|" + charId + "|read" + val pending = pendingCallbacks.get(key) + val value = characteristic.getValue() + console.log("[onCharacteristicRead]", key, "status=", status, "value=", value, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:195") + if (pending != null) { + try { + val timer = pending.timer + if (timer != null) { + clearTimeout(timer) + pending.timer = null + } + pendingCallbacks.`delete`(key) + if (status == BluetoothGatt.GATT_SUCCESS && value != null) { + val valueLength = value.size + val arr = Uint8Array(valueLength) + run { + var i = 0 as Int + while(i < valueLength){ + val v = value[i as Int] + arr[i] = if (v != null) { + v + } else { + 0 + } + i++ + } + } + pending.resolve(arr.buffer as ArrayBuffer) + } else { + pending.reject(UTSError("Characteristic read failed")) + } + } + catch (e: Throwable) { + try { + pending.reject(e) + } + catch (e2: Throwable) { + console.error(e2, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:218") + } + } + } + } + override fun onCharacteristicWrite(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int): Unit { + console.log("ak onCharacteristicWrite", status, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:224") + val deviceId = gatt.getDevice().getAddress() + val serviceId = characteristic.getService().getUuid().toString() + val charId = characteristic.getUuid().toString() + val key = "" + deviceId + "|" + serviceId + "|" + charId + "|write" + val pending = pendingCallbacks.get(key) + console.log("[onCharacteristicWrite]", key, "status=", status, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:230") + if (pending != null) { + try { + val timer = pending.timer + if (timer != null) { + clearTimeout(timer) + } + pendingCallbacks.`delete`(key) + if (status == BluetoothGatt.GATT_SUCCESS) { + pending.resolve("ok") + } else { + pending.reject(UTSError("Characteristic write failed")) + } + } + catch (e: Throwable) { + try { + pending.reject(e) + } + catch (e2: Throwable) { + console.error(e2, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:244") + } + } + } + } +} +val gattCallback = GattCallback() +open class ServiceManager : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("ServiceManager", "uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts", 248, 14) + } + private var services = Map>() + private var characteristics = Map>>() + private var deviceManager = DeviceManager.getInstance() + private constructor(){} + open fun getServices(deviceId: String, callback: ((services: UTSArray?, error: UTSError?) -> Unit)?): Any { + console.log("ak start getservice", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:267") + val gatt = this.deviceManager.getGattInstance(deviceId) + if (gatt == null) { + if (callback != null) { + callback(null, AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")) + } + return UTSPromise.reject(AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")) + } + console.log("ak serviceDiscovered", gatt, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:273") + if (serviceDiscovered.get(deviceId) == true) { + val services = gatt.getServices() + console.log(services, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:277") + val result: UTSArray = _uA() + if (services != null) { + val servicesList = services + val size = servicesList.size + if (size > 0) { + run { + var i = 0 as Int + while(i < size){ + val service = if (servicesList != null) { + servicesList.get(i) + } else { + servicesList[i] + } + if (service != null) { + val bleService = BleService(uuid = service.getUuid().toString(), isPrimary = service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY) + result.push(bleService) + if (bleService.uuid == getFullUuid("0001")) { + val device = this.deviceManager.getDevice(deviceId) + if (device != null) { + device.serviceId = bleService.uuid + this.getCharacteristics(deviceId, device.serviceId!!, fun(chars, err){ + if (err == null && chars != null) { + val writeChar = chars.find(fun(c): Boolean { + return c.uuid == getFullUuid("0010") + } + ) + val notifyChar = chars.find(fun(c): Boolean { + return c.uuid == getFullUuid("0011") + } + ) + if (writeChar != null) { + device.writeCharId = writeChar.uuid + } + if (notifyChar != null) { + device.notifyCharId = notifyChar.uuid + } + } + } + ) + } + } + } + i++ + } + } + } + } + if (callback != null) { + callback(result, null) + } + return UTSPromise.resolve(result) + } + if (!serviceDiscoveryWaiters.has(deviceId)) { + serviceDiscoveryWaiters.set(deviceId, _uA()) + gatt.discoverServices() + } + return UTSPromise>(fun(resolve, reject){ + val cb = fun(services: UTSArray?, error: UTSError?){ + if (error != null) { + reject(error) + } else { + resolve(services ?: _uA()) + } + if (callback != null) { + callback(services, error) + } + } + val arr = serviceDiscoveryWaiters.get(deviceId) + if (arr != null) { + arr.push(cb) + } + } + ) + } + open fun getCharacteristics(deviceId: String, serviceId: String, callback: (characteristics: UTSArray?, error: UTSError?) -> Unit): Unit { + val gatt = this.deviceManager.getGattInstance(deviceId) + if (gatt == null) { + return callback(null, AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")) + } + if (serviceDiscovered.get(deviceId) !== true) { + this.getServices(deviceId, fun(services, err){ + if (err != null) { + callback(null, err) + } else { + this.getCharacteristics(deviceId, serviceId, callback) + } + } + ) + return + } + val service = gatt.getService(UUID.fromString(serviceId)) + if (service == null) { + return callback(null, AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "")) + } + val chars = service.getCharacteristics() + console.log(chars, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:347") + val result: UTSArray = _uA() + if (chars != null) { + val characteristicsList = chars + val size = characteristicsList.size + val bleService = BleService(uuid = serviceId, isPrimary = service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY) + run { + var i = 0 as Int + while(i < size){ + val char = if (characteristicsList != null) { + characteristicsList.get(i as Int) + } else { + characteristicsList[i] + } + if (char != null) { + val props = char.getProperties() + try { + val charUuid = if (char.getUuid() != null) { + char.getUuid().toString() + } else { + "" + } + console.log("[ServiceManager] characteristic uuid=", charUuid, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:362") + } + catch (e: Throwable) { + console.warn("[ServiceManager] failed to read char uuid", e, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:363") + } + console.log(props, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:364") + val bleCharacteristic = BleCharacteristic(uuid = char.getUuid().toString(), service = bleService, properties = createCharProperties(props)) + result.push(bleCharacteristic) + } + i++ + } + } + } + callback(result, null) + } + public open fun readCharacteristic(deviceId: String, serviceId: String, characteristicId: String): UTSPromise { + return wrapUTSPromise(suspend w@{ + val gatt = this.deviceManager.getGattInstance(deviceId) + if (gatt == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "") + } + val service = gatt.getService(UUID.fromString(serviceId)) + if (service == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "") + } + val char = service.getCharacteristic(UUID.fromString(characteristicId)) + if (char == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", "") + } + val key = "" + deviceId + "|" + serviceId + "|" + characteristicId + "|read" + console.log(key, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:385") + return@w UTSPromise(fun(resolve, reject){ + val timer = setTimeout(fun(){ + pendingCallbacks.`delete`(key) + reject(AkBleErrorImpl(AkBluetoothErrorCode.ConnectionTimeout, "Connection timeout", "")) + } + , 5000) + val resolveAdapter = fun(data: Any){ + console.log("read resolve:", data, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:391") + resolve(data as ArrayBuffer) + } + val rejectAdapter = fun(err: Any?){ + reject(AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")) + } + pendingCallbacks.set(key, PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)) + if (gatt.readCharacteristic(char) == false) { + clearTimeout(timer) + pendingCallbacks.`delete`(key) + reject(AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")) + } else { + console.log("read should be succeed", key, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:400") + } + } + ) + }) + } + public open fun writeCharacteristic(deviceId: String, serviceId: String, characteristicId: String, data: Uint8Array, options: WriteCharacteristicOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + console.log("[writeCharacteristic] deviceId:", deviceId, "serviceId:", serviceId, "characteristicId:", characteristicId, "data:", data, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:406") + val gatt = this.deviceManager.getGattInstance(deviceId) + if (gatt == null) { + console.error("[writeCharacteristic] gatt is null", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:409") + throw AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "") + } + val service = gatt.getService(UUID.fromString(serviceId)) + if (service == null) { + console.error("[writeCharacteristic] service is null", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:414") + throw AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "") + } + val char = service.getCharacteristic(UUID.fromString(characteristicId)) + if (char == null) { + console.error("[writeCharacteristic] characteristic is null", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:419") + throw AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", "") + } + val key = "" + deviceId + "|" + serviceId + "|" + characteristicId + "|write" + val wantsNoResponse = options != null && options.waitForResponse == false + var retryMaxAttempts: Number = 20 + var retryDelay: Number = 100 + var giveupTimeout: Number = 20000 + if (options != null) { + try { + if (options.maxAttempts != null) { + val parsedAttempts = Math.floor(options.maxAttempts as Number) + if (!isNaN(parsedAttempts) && parsedAttempts > 0) { + retryMaxAttempts = parsedAttempts + } + } + } + catch (e: Throwable) {} + try { + if (options.retryDelayMs != null) { + val parsedDelay = Math.floor(options.retryDelayMs as Number) + if (!isNaN(parsedDelay) && parsedDelay >= 0) { + retryDelay = parsedDelay + } + } + } + catch (e: Throwable) {} + try { + if (options.giveupTimeoutMs != null) { + val parsedGiveup = Math.floor(options.giveupTimeoutMs as Number) + if (!isNaN(parsedGiveup) && parsedGiveup > 0) { + giveupTimeout = parsedGiveup + } + } + } + catch (e: Throwable) {} + } + val gattInstance = gatt + val executeWrite = fun(): UTSPromise { + return UTSPromise(fun(resolve, _reject){ + val initialTimeout = Math.max(giveupTimeout + 5000, 10000) + var timer = setTimeout(fun(){ + pendingCallbacks.`delete`(key) + console.error("[writeCharacteristic] timeout", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:454") + resolve(false) + } + , initialTimeout) + console.log("[writeCharacteristic] initial timeout set to", initialTimeout, "ms for", key, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:457") + val resolveAdapter = fun(data: Any){ + console.log("[writeCharacteristic] resolveAdapter called", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:459") + resolve(true) + } + val rejectAdapter = fun(err: Any?){ + console.error("[writeCharacteristic] rejectAdapter called", err, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:463") + resolve(false) + } + pendingCallbacks.set(key, PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)) + val byteArray = ByteArray(data.length as Int) + run { + var i = 0 as Int + while(i < data.length){ + byteArray[i] = data[i].toByte() + i++ + } + } + val forceWriteTypeNoResponse = options != null && options.forceWriteTypeNoResponse == true + var usesNoResponse = forceWriteTypeNoResponse || wantsNoResponse + try { + val props = char.getProperties() + console.log("[writeCharacteristic] characteristic properties mask=", props, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:475") + if (usesNoResponse == false) { + val supportsWriteWithResponse = (props and BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0 + val supportsWriteNoResponse = (props and BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0 + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + usesNoResponse = true + } + } + if (usesNoResponse) { + try { + char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_NO_RESPONSE) + } catch (e: Throwable) {} + console.log("[writeCharacteristic] using WRITE_TYPE_NO_RESPONSE", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:485") + } else { + try { + char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT) + } + catch (e: Throwable) {} + console.log("[writeCharacteristic] using WRITE_TYPE_DEFAULT", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:488") + } + } + catch (e: Throwable) { + console.warn("[writeCharacteristic] failed to inspect/set write type", e, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:491") + } + val maxAttempts = retryMaxAttempts + fun attemptWrite(att: Int): Unit { + try { + var setOk = true + try { + val setRes = char.setValue(byteArray) + if (UTSAndroid.`typeof`(setRes) == "boolean" && setRes == false) { + setOk = false + console.warn("[writeCharacteristic] setValue returned false for", key, "attempt", att, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:501") + } + } + catch (e: Throwable) { + setOk = false + console.warn("[writeCharacteristic] setValue threw for", key, "attempt", att, e, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:505") + } + if (setOk == false) { + if (att >= maxAttempts) { + try { + clearTimeout(timer) + } + catch (e: Throwable) {} + pendingCallbacks.`delete`(key) + resolve(false) + return + } + setTimeout(fun(){ + attemptWrite((att + 1) as Int) + } + , retryDelay) + return + } + try { + console.log("[writeCharacteristic] attempt", att, "calling gatt.writeCharacteristic", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:518") + val r = gattInstance.writeCharacteristic(char) + console.log("[writeCharacteristic] attempt", att, "result=", r, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:520") + if (r == true) { + if (usesNoResponse) { + console.log("[writeCharacteristic] WRITE_TYPE_NO_RESPONSE success for", key, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:523") + try { + clearTimeout(timer) + } + catch (e: Throwable) {} + pendingCallbacks.`delete`(key) + resolve(true) + return + } + try { + clearTimeout(timer) + } + catch (e: Throwable) {} + val extra: Number = 20000 + timer = setTimeout(fun(){ + pendingCallbacks.`delete`(key) + console.error("[writeCharacteristic] timeout after write initiated", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:533") + resolve(false) + } + , extra) + val pendingEntry = pendingCallbacks.get(key) + if (pendingEntry != null) { + pendingEntry.timer = timer + } + return + } + } + catch (e: Throwable) { + console.error("[writeCharacteristic] attempt", att, "exception when calling writeCharacteristic", e, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:541") + } + if (att < maxAttempts) { + val nextAtt = (att + 1) as Int + setTimeout(fun(){ + attemptWrite(nextAtt) + } + , retryDelay) + return + } + if (usesNoResponse) { + try { + clearTimeout(timer) + } + catch (e: Throwable) {} + pendingCallbacks.`delete`(key) + console.warn("[writeCharacteristic] all attempts failed with WRITE_NO_RESPONSE for", key, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:551") + resolve(false) + return + } + try { + clearTimeout(timer) + } + catch (e: Throwable) {} + val giveupTimeoutLocal = giveupTimeout + console.warn("[writeCharacteristic] all attempts failed; waiting for late callback up to", giveupTimeoutLocal, "ms for", key, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:557") + val giveupTimer = setTimeout(fun(){ + pendingCallbacks.`delete`(key) + console.error("[writeCharacteristic] giveup timeout expired for", key, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:560") + resolve(false) + } + , giveupTimeoutLocal) + val pendingEntryAfter = pendingCallbacks.get(key) + if (pendingEntryAfter != null) { + pendingEntryAfter.timer = giveupTimer + } + } + catch (e: Throwable) { + clearTimeout(timer) + pendingCallbacks.`delete`(key) + console.error("[writeCharacteristic] Exception in attemptWrite", e, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:568") + resolve(false) + } + } + try { + attemptWrite(1 as Int) + } + catch (e: Throwable) { + clearTimeout(timer) + pendingCallbacks.`delete`(key) + console.error("[writeCharacteristic] Exception before attempting write", e, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:578") + resolve(false) + } + } + ) + } + return@w enqueueDeviceWrite(deviceId, executeWrite) + }) + } + public open fun subscribeCharacteristic(deviceId: String, serviceId: String, characteristicId: String, onData: BleDataReceivedCallback): UTSPromise { + return wrapUTSPromise(suspend { + val gatt = this.deviceManager.getGattInstance(deviceId) + if (gatt == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "") + } + val service = gatt.getService(UUID.fromString(serviceId)) + if (service == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "") + } + val char = service.getCharacteristic(UUID.fromString(characteristicId)) + if (char == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", "") + } + val key = "" + deviceId + "|" + serviceId + "|" + characteristicId + "|notify" + notifyCallbacks.set(key, onData) + if (gatt.setCharacteristicNotification(char, true) == false) { + notifyCallbacks.`delete`(key) + throw AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", "") + } else { + val descriptor = char.getDescriptor(UUID.fromString("00002902-0000-1000-8000-00805f9b34fb")) + if (descriptor != null) { + val value = BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE + descriptor.setValue(value) + val writedescript = gatt.writeDescriptor(descriptor) + console.log("subscribeCharacteristic: CCCD written for notify", writedescript, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:608") + } else { + console.warn("subscribeCharacteristic: CCCD descriptor not found!", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:610") + } + console.log("subscribeCharacteristic ok!!", " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:612") + } + }) + } + public open fun unsubscribeCharacteristic(deviceId: String, serviceId: String, characteristicId: String): UTSPromise { + return wrapUTSPromise(suspend { + val gatt = this.deviceManager.getGattInstance(deviceId) + if (gatt == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "") + } + val service = gatt.getService(UUID.fromString(serviceId)) + if (service == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "") + } + val char = service.getCharacteristic(UUID.fromString(characteristicId)) + if (char == null) { + throw AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", "") + } + val key = "" + deviceId + "|" + serviceId + "|" + characteristicId + "|notify" + notifyCallbacks.`delete`(key) + if (gatt.setCharacteristicNotification(char, false) == false) { + throw AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", "") + } + }) + } + public open fun autoDiscoverAll(deviceId: String): UTSPromise { + return wrapUTSPromise(suspend w@{ + val services = await(this.getServices(deviceId, null)) as UTSArray + val allCharacteristics: UTSArray = _uA() + for(service in resolveUTSValueIterator(services)){ + await(UTSPromise(fun(resolve, reject){ + this.getCharacteristics(deviceId, service.uuid, fun(chars, err){ + if (err != null) { + reject(err) + } else { + if (chars != null) { + allCharacteristics.push(*chars.toTypedArray()) + } + resolve(Unit) + } + } + ) + } + )) + } + return@w AutoDiscoverAllResult(services = services, characteristics = allCharacteristics) + }) + } + public open fun subscribeAllNotifications(deviceId: String, onData: BleDataReceivedCallback): UTSPromise { + return wrapUTSPromise(suspend { + val _ref = await(this.autoDiscoverAll(deviceId)) + val services = _ref.services + val characteristics = _ref.characteristics + for(char in resolveUTSValueIterator(characteristics)){ + if (char.properties.notify || char.properties.indicate) { + try { + await(this.subscribeCharacteristic(deviceId, char.service.uuid, char.uuid, onData)) + } + catch (e: Throwable) { + console.warn("\u8BA2\u9605\u7279\u5F81 " + char.uuid + " \u5931\u8D25:", e, " at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:658") + } + } + } + }) + } + companion object { + private var instance: ServiceManager? = null + fun getInstance(): ServiceManager { + if (ServiceManager.instance == null) { + ServiceManager.instance = ServiceManager() + } + return ServiceManager.instance!! + } + } +} +open class RawProtocolHandler ( + open var protocol: BleProtocolType? = null, + open var scanDevices: ((options: ScanDevicesOptions?) -> UTSPromise)? = null, + open var connect: ((device: BleDevice, options: BleConnectOptionsExt?) -> UTSPromise)? = null, + open var disconnect: ((device: BleDevice) -> UTSPromise)? = null, + open var sendData: ((device: BleDevice, payload: SendDataPayload?, options: BleOptions?) -> UTSPromise)? = null, + open var autoConnect: ((device: BleDevice, options: BleConnectOptionsExt?) -> UTSPromise)? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("RawProtocolHandler", "uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts", 8, 6) + } +} +open class DeviceContext : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("DeviceContext", "uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts", 17, 7) + } + open var device: BleDevice + open var protocol: BleProtocolType + open var state: BleConnectionState + open var handler: ProtocolHandler + constructor(device: BleDevice, protocol: BleProtocolType, handler: ProtocolHandler){ + this.device = device + this.protocol = protocol + this.state = 0 + this.handler = handler + } +} +val deviceMap = Map() +var activeProtocol: BleProtocolType = "standard" +var activeHandler: ProtocolHandler? = null +val eventListeners = Map>() +fun emit(event: BleEvent, payload: BleEventPayload) { + if (event === "connectionStateChanged") { + console.log("[AKBLE][LOG] bluetooth_manager.uts emit connectionStateChanged", payload, " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:57") + } + val listeners = eventListeners.get(event) + if (listeners != null) { + listeners.forEach(fun(cb){ + try { + cb(payload) + } + catch (e: Throwable) {} + } + ) + } +} +open class ProtocolHandlerWrapper : ProtocolHandler, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("ProtocolHandlerWrapper", "uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts", 49, 7) + } + private var _raw: RawProtocolHandler? + constructor(raw: RawProtocolHandler?) : super(BluetoothService()) { + this._raw = if ((raw != null)) { + raw + } else { + null + } + } + override fun scanDevices(options: ScanDevicesOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + val rawTyped = this._raw + if (rawTyped != null && UTSAndroid.`typeof`(rawTyped.scanDevices) === "function") { + await(rawTyped.scanDevices!!(options)) + } + return@w + }) + } + override fun connect(device: BleDevice, options: BleConnectOptionsExt?): UTSPromise { + return wrapUTSPromise(suspend w@{ + val rawTyped = this._raw + if (rawTyped != null && UTSAndroid.`typeof`(rawTyped.connect) === "function") { + await(rawTyped.connect!!(device, options)) + } + return@w + }) + } + override fun disconnect(device: BleDevice): UTSPromise { + return wrapUTSPromise(suspend w@{ + val rawTyped = this._raw + if (rawTyped != null && UTSAndroid.`typeof`(rawTyped.disconnect) === "function") { + await(rawTyped.disconnect!!(device)) + } + return@w + }) + } + override fun sendData(device: BleDevice, payload: SendDataPayload?, options: BleOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + val rawTyped = this._raw + if (rawTyped != null && UTSAndroid.`typeof`(rawTyped.sendData) === "function") { + await(rawTyped.sendData!!(device, payload, options)) + } + return@w + }) + } + override fun autoConnect(device: BleDevice, options: BleConnectOptionsExt?): UTSPromise { + return wrapUTSPromise(suspend w@{ + val rawTyped = this._raw + if (rawTyped != null && UTSAndroid.`typeof`(rawTyped.autoConnect) === "function") { + return@w await(rawTyped.autoConnect!!(device, options)) + } + return@w AutoBleInterfaces(serviceId = "", writeCharId = "", notifyCharId = "") + }) + } +} +val scanDevices = fun(options: ScanDevicesOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + console.log("[AKBLE] start scan", options, " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:147") + if (activeHandler == null) { + console.log("[AKBLE] no active scan handler registered", " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:151") + return@w + } + val handler = activeHandler as ProtocolHandler + val scanOptions = ScanDevicesOptions(onDeviceFound = fun(device: BleDevice){ + return emit("deviceFound", BleEventPayload(event = "deviceFound", device = device)) + } + , onScanFinished = fun(){ + return emit("scanFinished", BleEventPayload(event = "scanFinished")) + } + ) + try { + await(handler.scanDevices(scanOptions)) + } + catch (e: Throwable) { + console.warn("[AKBLE] scanDevices handler error", e, " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:162") + } + }) +} +val connectDevice = fun(deviceId: String, protocol: BleProtocolType, options: BleConnectOptionsExt?): UTSPromise { + return wrapUTSPromise(suspend { + val handler = activeHandler + if (handler == null) { + throw UTSError("No protocol handler") + } + val device = BleDevice(deviceId = deviceId, name = "", rssi = 0) + await(handler.connect(device, options)) + val ctx = DeviceContext(device, protocol, handler) + ctx.state = 2 + deviceMap.set(getDeviceKey(deviceId, protocol), ctx) + console.log(deviceMap, " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:175") + emit("connectionStateChanged", BleEventPayload(event = "connectionStateChanged", device = device, protocol = protocol, state = 2)) + }) +} +val disconnectDevice = fun(deviceId: String, protocol: BleProtocolType): UTSPromise { + return wrapUTSPromise(suspend w@{ + val ctx = deviceMap.get(getDeviceKey(deviceId, protocol)) + if (ctx == null || ctx.handler == null) { + return@w + } + await(ctx.handler.disconnect(ctx.device)) + ctx.state = 0 + emit("connectionStateChanged", BleEventPayload(event = "connectionStateChanged", device = ctx.device, protocol = protocol, state = 0)) + deviceMap.`delete`(getDeviceKey(deviceId, protocol)) + }) +} +val getConnectedDevices = fun(): UTSArray { + val result: UTSArray = _uA() + deviceMap.forEach(fun(ctx: DeviceContext){ + val dev = MultiProtocolDevice(deviceId = ctx.device.deviceId, name = ctx.device.name, rssi = ctx.device.rssi, protocol = ctx.protocol) + result.push(dev) + } + ) + return result +} +val on = fun(event: BleEvent, callback: BleEventCallback){ + if (!eventListeners.has(event)) { + eventListeners.set(event, Set()) + } + eventListeners.get(event)!!.add(callback) +} +val off = fun(event: BleEvent, callback: BleEventCallback?){ + if (callback == null) { + eventListeners.`delete`(event) + } else { + eventListeners.get(event)?.`delete`(callback as BleEventCallback) + } +} +fun getDeviceKey(deviceId: String, protocol: BleProtocolType): String { + return "" + deviceId + "|" + protocol +} +val runBlock4 = run { + try { + if (activeHandler == null) { + val _dm = DeviceManager.getInstance() + val _raw = RawProtocolHandler(protocol = "standard", scanDevices = fun(options: ScanDevicesOptions?): UTSPromise { + try { + val scanOptions = if (options != null) { + options + } else { + ScanDevicesOptions() + } + _dm.startScan(scanOptions) + } + catch (e: Throwable) { + console.warn("[AKBLE] DeviceManager.startScan failed", e, " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:256") + } + return UTSPromise.resolve() + } + , connect = fun(device, options: BleConnectOptionsExt?): UTSPromise { + return _dm.connectDevice(device.deviceId, options) + } + , disconnect = fun(device): UTSPromise { + return _dm.disconnectDevice(device.deviceId) + } + , autoConnect = fun(device, options: Any?): UTSPromise { + val result = AutoBleInterfaces(serviceId = "", writeCharId = "", notifyCharId = "") + return UTSPromise.resolve(result) + } + ) + val _wrapper = ProtocolHandlerWrapper(_raw) + activeHandler = _wrapper + activeProtocol = _raw.protocol as BleProtocolType + console.log("[AKBLE] default protocol handler (BluetoothService-backed) registered", activeProtocol, " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:275") + } + } + catch (e: Throwable) { + console.warn("[AKBLE] failed to register default protocol handler", e, " at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:278") + } +} +val serviceManager = ServiceManager.getInstance() +open class BluetoothService1 : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("BluetoothService", "uni_modules/ak-sbsrv/utssdk/app-android/index.uts", 6, 14) + } + open fun scanDevices(options: ScanDevicesOptions?): UTSPromise { + return uni.UNI95B2570.scanDevices(options) + } + open fun connectDevice(deviceId: String, protocol: String, options: BleConnectOptionsExt?): UTSPromise { + return uni.UNI95B2570.connectDevice(deviceId, protocol, options) + } + open fun disconnectDevice(deviceId: String, protocol: String): UTSPromise { + return uni.UNI95B2570.disconnectDevice(deviceId, protocol) + } + open fun getConnectedDevices(): UTSArray { + return uni.UNI95B2570.getConnectedDevices() + } + open fun on(event: BleEvent, callback: BleEventCallback) { + return uni.UNI95B2570.on(event, callback) + } + open fun off(event: BleEvent, callback: BleEventCallback?) { + return uni.UNI95B2570.off(event, callback) + } + open fun getServices(deviceId: String): UTSPromise> { + return UTSPromise(fun(resolve, reject){ + serviceManager.getServices(deviceId, fun(list, err){ + console.log("getServices:", list, err, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:18") + if (err != null) { + reject(err) + } else { + resolve((list as UTSArray) ?: _uA()) + } + } + ) + } + ) + } + open fun getCharacteristics(deviceId: String, serviceId: String): UTSPromise> { + return UTSPromise(fun(resolve, reject){ + console.log(deviceId, serviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:26") + serviceManager.getCharacteristics(deviceId, serviceId, fun(list, err){ + if (err != null) { + reject(err) + } else { + resolve((list as UTSArray) ?: _uA()) + } + } + ) + } + ) + } + open fun getAutoBleInterfaces(deviceId: String): UTSPromise { + return wrapUTSPromise(suspend w@{ + val services = await(this.getServices(deviceId)) + if (services == null || services.length == 0) { + throw UTSError("未发现服务") + } + var serviceId = "" + run { + var i: Number = 0 + while(i < services.length){ + val s = services[i] + val uuidCandidate: String? = if (s.uuid != null) { + s.uuid + } else { + null + } + val uuid: String = if (uuidCandidate != null) { + uuidCandidate + } else { + "" + } + if (UTSRegExp("^bae", "i").test(uuid)) { + serviceId = uuid + break + } + i++ + } + } + console.log(serviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:55") + if (serviceId == null || serviceId == "") { + serviceId = services[0].uuid + } + val characteristics = await(this.getCharacteristics(deviceId, serviceId)) + console.log(characteristics, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:60") + if (characteristics == null || characteristics.length == 0) { + throw UTSError("未发现特征值") + } + var writeCharId = "" + var notifyCharId = "" + run { + var i: Number = 0 + while(i < characteristics.length){ + val c = characteristics[i] + console.log(c, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:69") + if ((writeCharId == null || writeCharId == "") && c.properties != null && (c.properties.write || c.properties.writeWithoutResponse == true)) { + writeCharId = c.uuid + } + if ((notifyCharId == null || notifyCharId == "") && c.properties != null && (c.properties.notify || c.properties.indicate)) { + notifyCharId = c.uuid + } + i++ + } + } + console.log(serviceId, writeCharId, notifyCharId, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:73") + if ((writeCharId == null || writeCharId == "") || (notifyCharId == null || notifyCharId == "")) { + throw UTSError("未找到合适的写入或通知特征") + } + console.log(serviceId, writeCharId, notifyCharId, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:75") + val deviceManager = DeviceManager.getInstance() + console.log(deviceManager, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:78") + val device = deviceManager.getDevice(deviceId) + console.log(deviceId, device, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:80") + device!!.serviceId = serviceId + device!!.writeCharId = writeCharId + device!!.notifyCharId = notifyCharId + console.log(device, " at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:84") + return@w AutoBleInterfaces(serviceId = serviceId, writeCharId = writeCharId, notifyCharId = notifyCharId) + }) + } + open fun subscribeCharacteristic(deviceId: String, serviceId: String, characteristicId: String, onData: BleDataReceivedCallback): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w serviceManager.subscribeCharacteristic(deviceId, serviceId, characteristicId, onData) + }) + } + open fun readCharacteristic(deviceId: String, serviceId: String, characteristicId: String): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w serviceManager.readCharacteristic(deviceId, serviceId, characteristicId) + }) + } + open fun writeCharacteristic(deviceId: String, serviceId: String, characteristicId: String, data: Uint8Array, options: WriteCharacteristicOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w serviceManager.writeCharacteristic(deviceId, serviceId, characteristicId, data, options) + }) + } + open fun unsubscribeCharacteristic(deviceId: String, serviceId: String, characteristicId: String): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w serviceManager.unsubscribeCharacteristic(deviceId, serviceId, characteristicId) + }) + } + open fun autoDiscoverAll(deviceId: String): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w serviceManager.autoDiscoverAll(deviceId) + }) + } + open fun subscribeAllNotifications(deviceId: String, onData: BleDataReceivedCallback): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w serviceManager.subscribeAllNotifications(deviceId, onData) + }) + } +} +val bluetoothService = BluetoothService1() +val DFU_SERVICE_UUID = "0000fe59-0000-1000-8000-00805f9b34fb" +val DFU_CONTROL_POINT_UUID = "8ec90001-f315-4f60-9fb8-838830daea50" +val DFU_PACKET_UUID = "8ec90002-f315-4f60-9fb8-838830daea50" +open class DfuSession ( + open var resolve: () -> Unit, + open var reject: (err: Any?) -> Unit, + open var onProgress: ((p: Number) -> Unit)? = null, + open var onLog: ((s: String) -> Unit)? = null, + open var controlParser: ((data: Uint8Array) -> ControlParserResult?)? = null, + open var bytesSent: Number? = null, + open var totalBytes: Number? = null, + open var useNordic: Boolean? = null, + open var prn: Number? = null, + open var packetsSincePrn: Number? = null, + open var prnResolve: (() -> Unit)? = null, + open var prnReject: ((err: Any?) -> Unit)? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("DfuSession", "uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts", 13, 6) + } +} +open class DfuManager : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("DfuManager", "uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts", 29, 14) + } + private var sessions: Map = Map() + private fun _emitDfuEvent(deviceId: String, name: String, payload: Any?) { + console.log("[DFU][Event]", name, deviceId, payload ?: "", " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:42") + val s = this.sessions.get(deviceId) + if (s == null) { + return + } + if (UTSAndroid.`typeof`(s.onLog) == "function") { + try { + val logFn = s.onLog as (msg: String) -> Unit + logFn("[" + name + "] " + (if (payload != null) { + JSON.stringify(payload) + } else { + "" + } + )) + } + catch (e: Throwable) {} + } + if (name == "onProgress" && UTSAndroid.`typeof`(s.onProgress) == "function" && UTSAndroid.`typeof`(payload) == "number") { + try { + s.onProgress!!(payload as Number) + } + catch (e: Throwable) {} + } + } + open fun startDfu(deviceId: String, firmwareBytes: Uint8Array, options: DfuOptions?): UTSPromise { + return wrapUTSPromise(suspend w@{ + console.log("startDfu 0", " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:57") + val deviceManager = DeviceManager.getInstance() + val serviceManager = ServiceManager.getInstance() + console.log("startDfu 1", " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:60") + val gatt: BluetoothGatt? = deviceManager.getGattInstance(deviceId) + console.log("startDfu 2", " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:62") + if (gatt == null) { + throw UTSError("Device not connected") + } + console.log("[DFU] startDfu start deviceId=", deviceId, "firmwareBytes=", if (firmwareBytes != null) { + firmwareBytes.length + } else { + 0 + } + , "options=", options, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:64") + try { + console.log("[DFU] requesting high connection priority for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:66") + gatt.requestConnectionPriority(BluetoothGatt.CONNECTION_PRIORITY_HIGH) + } + catch (e: Throwable) { + console.warn("[DFU] requestConnectionPriority failed", e, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:69") + } + await(serviceManager.getServices(deviceId, null)) + console.log("[DFU] services ensured for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:75") + val dfuService = gatt.getService(UUID.fromString(DFU_SERVICE_UUID)) + if (dfuService == null) { + throw UTSError("DFU service not found") + } + val controlChar = dfuService.getCharacteristic(UUID.fromString(DFU_CONTROL_POINT_UUID)) + val packetChar = dfuService.getCharacteristic(UUID.fromString(DFU_PACKET_UUID)) + console.log("[DFU] dfuService=", if (dfuService != null) { + dfuService.getUuid().toString() + } else { + null + } + , "controlChar=", if (controlChar != null) { + controlChar.getUuid().toString() + } else { + null + } + , "packetChar=", if (packetChar != null) { + packetChar.getUuid().toString() + } else { + null + } + , " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:80") + if (controlChar == null || packetChar == null) { + throw UTSError("DFU characteristics missing") + } + val packetProps = packetChar.getProperties() + val supportsWriteWithResponse = (packetProps and BluetoothGattCharacteristic.PROPERTY_WRITE) != 0 + val supportsWriteNoResponse = (packetProps and BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) != 0 + console.log("[DFU] packet characteristic props mask=", packetProps, "supportsWithResponse=", supportsWriteWithResponse, "supportsNoResponse=", supportsWriteNoResponse, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:85") + val desiredMtu = if ((options != null && UTSAndroid.`typeof`(options.mtu) == "number")) { + options.mtu!! + } else { + 247 + } + try { + console.log("[DFU] requesting MTU=", desiredMtu, "for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:90") + await(this._requestMtu(gatt, desiredMtu, 8000)) + console.log("[DFU] requestMtu completed for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:92") + } + catch (e: Throwable) { + console.warn("[DFU] requestMtu failed or timed out, continue with default.", e, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:94") + } + val mtu = desiredMtu + val chunkSize = Math.max(20, mtu - 3) + val byteToHex = fun(b: Number): String { + val v = if ((b < 0)) { + (b + 256) + } else { + b + } + var s = v.toString(16) + if (s.length < 2) { + s = "0" + s + } + return s + } + var prnWindow: Number = 0 + if (options != null && UTSAndroid.`typeof`(options.prn) == "number") { + prnWindow = Math.max(0, Math.floor(options.prn!!)) + } + val prnTimeoutMs = if ((options != null && UTSAndroid.`typeof`(options.prnTimeoutMs) == "number")) { + Math.max(1000, Math.floor(options.prnTimeoutMs!!)) + } else { + 8000 + } + val disablePrnOnTimeout = !(options != null && options.disablePrnOnTimeout == false) + val controlHandler = fun(data: Uint8Array){ + try { + val hexParts: UTSArray = _uA() + run { + var i: Number = 0 + while(i < data.length){ + val v = data[i] as Number + hexParts.push(byteToHex(v)) + i++ + } + } + val hex = hexParts.join(" ") + console.log("[DFU] control notification callback invoked for", deviceId, "raw=", UTSArray.from(data), "hex=", hex, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:126") + } + catch (e: Throwable) { + console.log("[DFU] control notification callback invoked for", deviceId, "raw=", UTSArray.from(data), " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:128") + } + this._handleControlNotification(deviceId, data) + } + console.log("[DFU] subscribing control point for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:132") + await(serviceManager.subscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, controlHandler)) + console.log("[DFU] subscribeCharacteristic returned for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:134") + this.sessions.set(deviceId, DfuSession(resolve = fun(){}, reject = fun(err: Any?){ + console.log(err, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:139") + } + , onProgress = null, onLog = null, controlParser = fun(data: Uint8Array): ControlParserResult? { + return this._defaultControlParser(data) + } + , bytesSent = 0, totalBytes = firmwareBytes.length, useNordic = options != null && options.useNordic == true, prn = null, packetsSincePrn = 0, prnResolve = null, prnReject = null)) + console.log("[DFU] session created for", deviceId, "totalBytes=", firmwareBytes.length, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:151") + console.log("[DFU] DFU session details:", _uO("deviceId" to deviceId, "totalBytes" to firmwareBytes.length, "chunkSize" to chunkSize, "prnWindow" to prnWindow, "prnTimeoutMs" to prnTimeoutMs), " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:152") + val sessRef = this.sessions.get(deviceId) + if (sessRef != null) { + sessRef.onProgress = if ((options != null && UTSAndroid.`typeof`(options.onProgress) == "function")) { + options.onProgress!! + } else { + null + } + sessRef.onLog = if ((options != null && UTSAndroid.`typeof`(options.onLog) == "function")) { + options.onLog!! + } else { + null + } + } + this._emitDfuEvent(deviceId, "onDeviceConnecting", null) + if (prnWindow > 0) { + try { + val prnLsb = prnWindow % 256 + val prnMsb = Math.floor(prnWindow / 256) % 256 + val prnPayload = Uint8Array(_uA( + 0x02, + prnLsb, + prnMsb + )) + await(serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, prnPayload, null)) + val sess0 = this.sessions.get(deviceId) + if (sess0 != null) { + sess0.useNordic = true + sess0.prn = prnWindow + sess0.packetsSincePrn = 0 + sess0.controlParser = fun(data: Uint8Array): ControlParserResult? { + return this._nordicControlParser(data) + } + } + console.log("[DFU] Set PRN sent (prn=", prnWindow, ") for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:184") + } catch (e: Throwable) { + console.warn("[DFU] Set PRN failed (continuing without PRN):", e, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:186") + val sessFallback = this.sessions.get(deviceId) + if (sessFallback != null) { + sessFallback.prn = 0 + } + } + } else { + console.log("[DFU] PRN disabled (prnWindow=", prnWindow, ") for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:191") + } + var offset: Number = 0 + val total = firmwareBytes.length + this._emitDfuEvent(deviceId, "onDfuProcessStarted", null) + this._emitDfuEvent(deviceId, "onUploadingStarted", null) + var outstandingWrites: Number = 0 + var configuredMaxOutstanding: Number = 2 + var writeSleepMs: Number = 0 + var writeRetryDelay: Number = 100 + var writeMaxAttempts: Number = 12 + var writeGiveupTimeout: Number = 60000 + var drainOutstandingTimeout: Number = 3000 + var failureBackoffMs: Number = 0 + var throughputWindowBytes: Number = 0 + var lastThroughputTime = Date.now() + fun _logThroughputIfNeeded(force: Boolean?) { + try { + val now = Date.now() + val elapsed = now - lastThroughputTime + if (force == true || elapsed >= 1000) { + val bytes = throughputWindowBytes + val bps = Math.floor((bytes * 1000) / Math.max(1, elapsed)) + throughputWindowBytes = 0 + lastThroughputTime = now + val human = "" + bps + " B/s" + console.log("[DFU] throughput:", human, "elapsedMs=", elapsed, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:225") + val s = this.sessions.get(deviceId) + if (s != null && UTSAndroid.`typeof`(s.onLog) == "function") { + try { + s.onLog?.invoke("[DFU] throughput: " + human) + } + catch (e: Throwable) {} + } + } + } + catch (e: Throwable) {} + } + try { + if (options != null) { + try { + if (options.maxOutstanding != null) { + val parsed = Math.floor(options.maxOutstanding as Number) + if (!isNaN(parsed) && parsed > 0) { + configuredMaxOutstanding = parsed + } + } + } + catch (e: Throwable) {} + try { + if (options.writeSleepMs != null) { + val parsedWs = Math.floor(options.writeSleepMs as Number) + if (!isNaN(parsedWs) && parsedWs >= 0) { + writeSleepMs = parsedWs + } + } + } + catch (e: Throwable) {} + try { + if (options.writeRetryDelayMs != null) { + val parsedRetry = Math.floor(options.writeRetryDelayMs as Number) + if (!isNaN(parsedRetry) && parsedRetry >= 0) { + writeRetryDelay = parsedRetry + } + } + } + catch (e: Throwable) {} + try { + if (options.writeMaxAttempts != null) { + val parsedAttempts = Math.floor(options.writeMaxAttempts as Number) + if (!isNaN(parsedAttempts) && parsedAttempts > 0) { + writeMaxAttempts = parsedAttempts + } + } + } + catch (e: Throwable) {} + try { + if (options.writeGiveupTimeoutMs != null) { + val parsedGiveupTimeout = Math.floor(options.writeGiveupTimeoutMs as Number) + if (!isNaN(parsedGiveupTimeout) && parsedGiveupTimeout > 0) { + writeGiveupTimeout = parsedGiveupTimeout + } + } + } + catch (e: Throwable) {} + try { + if (options.drainOutstandingTimeoutMs != null) { + val parsedDrain = Math.floor(options.drainOutstandingTimeoutMs as Number) + if (!isNaN(parsedDrain) && parsedDrain >= 0) { + drainOutstandingTimeout = parsedDrain + } + } + } + catch (e: Throwable) {} + } + if (configuredMaxOutstanding < 1) { + configuredMaxOutstanding = 1 + } + if (writeSleepMs < 0) { + writeSleepMs = 0 + } + } + catch (e: Throwable) {} + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + if (configuredMaxOutstanding > 1) { + configuredMaxOutstanding = 1 + } + if (writeSleepMs < 15) { + writeSleepMs = 15 + } + if (writeRetryDelay < 150) { + writeRetryDelay = 150 + } + if (writeMaxAttempts < 40) { + writeMaxAttempts = 40 + } + if (writeGiveupTimeout < 120000) { + writeGiveupTimeout = 120000 + } + console.log("[DFU] packet char only supports WRITE_NO_RESPONSE; serializing writes with conservative pacing", " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:291") + } + val maxOutstandingCeiling = configuredMaxOutstanding + var adaptiveMaxOutstanding = configuredMaxOutstanding + val minOutstandingWindow: Number = 1 + while(offset < total){ + val end = Math.min(offset + chunkSize, total) + val slice = firmwareBytes.subarray(offset, end) + var finalWaitForResponse = true + if (options != null) { + try { + val maybe = options.waitForResponse + if (maybe == true && supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + finalWaitForResponse = true + } else if (maybe == false) { + finalWaitForResponse = false + } else if (maybe == true) { + finalWaitForResponse = true + } + } + catch (e: Throwable) { + finalWaitForResponse = true + } + } + val writeOpts = WriteCharacteristicOptions(waitForResponse = finalWaitForResponse, retryDelayMs = writeRetryDelay, maxAttempts = writeMaxAttempts, giveupTimeoutMs = writeGiveupTimeout, forceWriteTypeNoResponse = finalWaitForResponse == false) + console.log("[DFU] writing packet chunk offset=", offset, "len=", slice.length, "waitForResponse=", finalWaitForResponse, "outstanding=", outstandingWrites, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:324") + if (finalWaitForResponse == false) { + if (failureBackoffMs > 0) { + console.log("[DFU] applying failure backoff", failureBackoffMs, "ms before next write for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:329") + await(this._sleep(failureBackoffMs)) + failureBackoffMs = Math.floor(failureBackoffMs / 2) + } + while(outstandingWrites >= adaptiveMaxOutstanding){ + await(this._sleep(Math.max(1, writeSleepMs))) + } + outstandingWrites = outstandingWrites + 1 + val writeOffset = offset + serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts).then(fun(res){ + outstandingWrites = Math.max(0, outstandingWrites - 1) + if (res == true) { + if (adaptiveMaxOutstanding < maxOutstandingCeiling) { + adaptiveMaxOutstanding = Math.min(maxOutstandingCeiling, adaptiveMaxOutstanding + 1) + } + if (failureBackoffMs > 0) { + failureBackoffMs = Math.floor(failureBackoffMs / 2) + } + } + if ((outstandingWrites and 0x1f) == 0) { + console.log("[DFU] write completion callback, outstandingWrites=", outstandingWrites, "adaptiveWindow=", adaptiveMaxOutstanding, "device=", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:350") + } + if (res !== true) { + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)) + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))) + console.error("[DFU] writeCharacteristic returned false for device=", deviceId, "offset=", writeOffset, "adaptiveWindow now=", adaptiveMaxOutstanding, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:356") + try { + this._emitDfuEvent(deviceId, "onError", object : UTSJSONObject() { + var phase = "write" + var offset = writeOffset + var reason = "write returned false" + }) + } + catch (e: Throwable) {} + } + }).`catch`(fun(e){ + outstandingWrites = Math.max(0, outstandingWrites - 1) + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)) + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))) + console.warn("[DFU] fire-and-forget write failed for device=", deviceId, e, "adaptiveWindow now=", adaptiveMaxOutstanding, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:363") + try { + val errMsg = "[DFU] fire-and-forget write failed for device=" + this._emitDfuEvent(deviceId, "onError", object : UTSJSONObject() { + var phase = "write" + var offset = writeOffset + var reason = errMsg + }) + } catch (e2: Throwable) {} + }) + throughputWindowBytes += slice.length + _logThroughputIfNeeded(false) + } else { + console.log("[DFU] awaiting write for chunk offset=", offset, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:373") + try { + val writeResult = await(serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts)) + if (writeResult !== true) { + console.error("[DFU] writeCharacteristic(await) returned false at offset=", offset, "device=", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:377") + try { + this._emitDfuEvent(deviceId, "onError", _uO("phase" to "write", "offset" to offset, "reason" to "write returned false")) + } + catch (e: Throwable) {} + throw UTSError("write failed") + } + } + catch (e: Throwable) { + console.error("[DFU] awaiting write failed at offset=", offset, "device=", deviceId, e, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:383") + try { + val errMsg = "[DFU] awaiting write failed " + this._emitDfuEvent(deviceId, "onError", _uO("phase" to "write", "offset" to offset, "reason" to errMsg)) + } + catch (e2: Throwable) {} + throw e + } + throughputWindowBytes += slice.length + _logThroughputIfNeeded(false) + } + val sessAfter = this.sessions.get(deviceId) + if (sessAfter != null && sessAfter.useNordic == true && UTSAndroid.`typeof`(sessAfter.prn) == "number" && (sessAfter.prn ?: 0) > 0) { + sessAfter.packetsSincePrn = (sessAfter.packetsSincePrn ?: 0) + 1 + if ((sessAfter.packetsSincePrn ?: 0) >= (sessAfter.prn ?: 0) && (sessAfter.prn ?: 0) > 0) { + try { + console.log("[DFU] reached PRN window, waiting for PRN for", deviceId, "packetsSincePrn=", sessAfter.packetsSincePrn, "prn=", sessAfter.prn, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:401") + await(this._waitForPrn(deviceId, prnTimeoutMs)) + console.log("[DFU] PRN received, resuming transfer for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:403") + } + catch (e: Throwable) { + console.warn("[DFU] PRN wait failed/timed out, continuing anyway for", deviceId, e, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:405") + if (disablePrnOnTimeout) { + console.warn("[DFU] disabling PRN waits after timeout for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:407") + sessAfter.prn = 0 + } + } + sessAfter.packetsSincePrn = 0 + } + } + offset = end + val sess = this.sessions.get(deviceId) + if (sess != null && UTSAndroid.`typeof`(sess.bytesSent) == "number") { + sess.bytesSent = (sess.bytesSent ?: 0) + slice.length + } + console.log("[DFU] wrote chunk for", deviceId, "offset=", offset, "/", total, "chunkSize=", slice.length, "bytesSent=", if (sess != null) { + sess.bytesSent + } else { + null + } + , "outstanding=", outstandingWrites, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:422") + if (sess != null && UTSAndroid.`typeof`(sess.bytesSent) == "number" && UTSAndroid.`typeof`(sess.totalBytes) == "number") { + val p = Math.floor((sess.bytesSent!! / sess.totalBytes!!) * 100) + this._emitDfuEvent(deviceId, "onProgress", p) + } + await(this._sleep(Math.max(0, writeSleepMs))) + } + if (outstandingWrites > 0) { + val drainStart = Date.now() + while(outstandingWrites > 0 && (Date.now() - drainStart) < drainOutstandingTimeout){ + await(this._sleep(Math.max(0, writeSleepMs))) + } + if (outstandingWrites > 0) { + console.warn("[DFU] outstandingWrites remain after drain timeout, continuing with", outstandingWrites, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:438") + } else { + console.log("[DFU] outstandingWrites drained before control phase", " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:440") + } + } + this._emitDfuEvent(deviceId, "onUploadingCompleted", null) + _logThroughputIfNeeded(true) + val controlTimeout: Number = 20000 + val controlResultPromise = this._waitForControlResult(deviceId, controlTimeout) + try { + val activatePayload = Uint8Array(_uA( + 0x04 + )) + console.log("[DFU] sending activate/validate payload=", UTSArray.from(activatePayload), " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:456") + await(serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, activatePayload, null)) + console.log("[DFU] activate/validate write returned for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:458") + } + catch (e: Throwable) { + try { + val sessOnWriteFail = this.sessions.get(deviceId) + if (sessOnWriteFail != null && UTSAndroid.`typeof`(sessOnWriteFail.reject) == "function") { + sessOnWriteFail.reject(e) + } + } + catch (rejectErr: Throwable) {} + await(controlResultPromise.`catch`(fun(){})) + try { + await(serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID)) + } + catch (e2: Throwable) {} + this.sessions.`delete`(deviceId) + throw e + } + console.log("[DFU] sent control activate/validate command to control point for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:472") + this._emitDfuEvent(deviceId, "onValidating", null) + console.log("[DFU] waiting for control result (timeout=", controlTimeout, ") for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:476") + try { + await(controlResultPromise) + console.log("[DFU] control result resolved for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:479") + } + catch (err: Throwable) { + try { + await(serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID)) + } + catch (e: Throwable) {} + this.sessions.`delete`(deviceId) + throw err + } + try { + await(serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID)) + } + catch (e: Throwable) {} + console.log("[DFU] unsubscribed control point for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:491") + this.sessions.`delete`(deviceId) + console.log("[DFU] session cleared for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:495") + return@w + }) + } + open fun _requestMtu(gatt: BluetoothGatt, mtu: Number, timeoutMs: Number): UTSPromise { + return wrapUTSPromise(suspend w@{ + return@w UTSPromise(fun(resolve, reject){ + try { + val ok = gatt.requestMtu(Math.floor(mtu) as Int) + if (!ok) { + return reject(UTSError("requestMtu failed")) + } + } + catch (e: Throwable) { + return reject(e) + } + setTimeout(fun(){ + return resolve(Unit) + } + , Math.min(2000, timeoutMs)) + } + ) + }) + } + open fun _sleep(ms: Number): UTSPromise { + return UTSPromise(fun(r, _reject){ + setTimeout(fun(){ + r(Unit) + } + , ms) + } + ) + } + open fun _waitForPrn(deviceId: String, timeoutMs: Number): UTSPromise { + val session = this.sessions.get(deviceId) + if (session == null) { + return UTSPromise.reject(UTSError("no dfu session")) + } + return UTSPromise(fun(resolve, reject){ + val timer = setTimeout(fun(){ + session.prnResolve = null + session.prnReject = null + reject(UTSError("PRN timeout")) + } + , timeoutMs) + val prnResolve = fun(){ + clearTimeout(timer) + resolve(Unit) + } + val prnReject = fun(err: Any?){ + clearTimeout(timer) + reject(err) + } + session.prnResolve = prnResolve + session.prnReject = prnReject + } + ) + } + open fun _defaultControlParser(data: Uint8Array): ControlParserResult? { + if (data == null || data.length === 0) { + return null + } + val op = data[0] + if (op === 0x10 && data.length >= 3) { + val requestOp = data[1] + val resultCode = data[2] + if (resultCode === 0x01) { + return ControlParserResult(type = "success") + } + return ControlParserResult(type = "error", error = _uO("requestOp" to requestOp, "resultCode" to resultCode, "raw" to UTSArray.from(data))) + } + if (op === 0x11 && data.length >= 3) { + val lsb = data[1] + val msb = data[2] + val received = (msb shl 8) or lsb + return ControlParserResult(type = "progress", progress = received) + } + if (op === 0x60) { + if (data.length >= 3) { + val requestOp = data[1] + val status = data[2] + if (status === 0x00 || status === 0x01 || status === 0x0A) { + return ControlParserResult(type = "success") + } + return ControlParserResult(type = "error", error = _uO("requestOp" to requestOp, "resultCode" to status, "raw" to UTSArray.from(data))) + } + if (data.length >= 2) { + return ControlParserResult(type = "progress", progress = data[1]) + } + } + if (data.length >= 2) { + val maybeProgress = data[1] + if (maybeProgress >= 0 && maybeProgress <= 100) { + return ControlParserResult(type = "progress", progress = maybeProgress) + } + } + if (op === 0x01) { + return ControlParserResult(type = "success") + } + if (op === 0xFF) { + return ControlParserResult(type = "error", error = data) + } + return ControlParserResult(type = "info") + } + open fun _nordicControlParser(data: Uint8Array): ControlParserResult? { + if (data == null || data.length == 0) { + return null + } + val op = data[0] + if (op == 0x11 && data.length >= 3) { + val lsb = data[1] + val msb = data[2] + val received = (msb shl 8) or lsb + return ControlParserResult(type = "progress", progress = received) + } + if (op == 0x60) { + if (data.length >= 3) { + val requestOp = data[1] + val status = data[2] + if (status == 0x00 || status == 0x01 || status == 0x0A) { + return ControlParserResult(type = "success") + } + return ControlParserResult(type = "error", error = _uO("requestOp" to requestOp, "resultCode" to status, "raw" to UTSArray.from(data))) + } + if (data.length >= 2) { + return ControlParserResult(type = "progress", progress = data[1]) + } + } + if (op == 0x10 && data.length >= 3) { + val requestOp = data[1] + val resultCode = data[2] + if (resultCode == 0x01) { + return ControlParserResult(type = "success") + } else { + return ControlParserResult(type = "error", error = _uO("requestOp" to requestOp, "resultCode" to resultCode)) + } + } + return null + } + open fun _handleControlNotification(deviceId: String, data: Uint8Array) { + val session = this.sessions.get(deviceId) + if (session == null) { + console.warn("[DFU] control notification received but no session for", deviceId, "data=", UTSArray.from(data), " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:636") + return + } + try { + var opcodeName = "unknown" + when (data[0]) { + 0x10 -> + opcodeName = "Response" + 0x11 -> + opcodeName = "PRN" + 0x60 -> + opcodeName = "VendorProgress" + 0x01 -> + opcodeName = "SuccessOpcode" + 0xFF -> + opcodeName = "ErrorOpcode" + } + console.log("[DFU] _handleControlNotification deviceId=", deviceId, "opcode=0x" + data[0].toString(16), "name=", opcodeName, "raw=", UTSArray.from(data), " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:649") + val parsed = if (session.controlParser != null) { + session.controlParser!!(data) + } else { + null + } + if (session.onLog != null) { + session.onLog!!("DFU control notify: " + UTSArray.from(data).join(",")) + } + console.log("[DFU] parsed control result=", parsed, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:652") + if (parsed == null) { + return + } + if (parsed.type == "progress" && parsed.progress != null) { + if (session.useNordic == true && session.totalBytes != null && session.totalBytes!! > 0) { + val percent = Math.floor((parsed.progress!! / session.totalBytes!!) * 100) + session.onProgress?.invoke(percent) + if (session.bytesSent != null && session.totalBytes != null && session.bytesSent!! >= session.totalBytes!!) { + console.log("[DFU] all bytes written locally for", deviceId, "bytesSent=", session.bytesSent, "total=", session.totalBytes, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:661") + this._emitDfuEvent(deviceId, "onUploadingCompleted", null) + } + if (UTSAndroid.`typeof`(session.prnResolve) == "function") { + try { + session.prnResolve!!() + } + catch (e: Throwable) {} + session.prnResolve = null + session.prnReject = null + session.packetsSincePrn = 0 + } + } else { + val progress = parsed.progress!! + if (progress != null) { + console.log("[DFU] progress for", deviceId, "progress=", progress, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:675") + session.onProgress?.invoke(progress) + if (UTSAndroid.`typeof`(session.prnResolve) == "function") { + try { + session.prnResolve!!() + } + catch (e: Throwable) {} + session.prnResolve = null + session.prnReject = null + session.packetsSincePrn = 0 + } + } + } + } else if (parsed.type == "success") { + console.log("[DFU] parsed success for", deviceId, "resolving session", " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:687") + session.resolve() + console.log("[DFU] device reported DFU success for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:690") + this._emitDfuEvent(deviceId, "onDfuCompleted", null) + } else if (parsed.type == "error") { + console.error("[DFU] parsed error for", deviceId, parsed.error, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:693") + session.reject(parsed.error ?: UTSError("DFU device error")) + this._emitDfuEvent(deviceId, "onError", parsed.error ?: UTSJSONObject()) + } + } + catch (e: Throwable) { + session.onLog?.invoke("control parse error: " + e) + console.error("[DFU] control parse exception for", deviceId, e, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:701") + } + } + open fun _waitForControlResult(deviceId: String, timeoutMs: Number): UTSPromise { + val session = this.sessions.get(deviceId) + if (session == null) { + return UTSPromise.reject(UTSError("no dfu session")) + } + return UTSPromise(fun(resolve, reject){ + val timer = setTimeout(fun(){ + console.error("[DFU] _waitForControlResult timeout for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:712") + reject(UTSError("DFU control timeout")) + } + , timeoutMs) + val origResolve = fun(){ + clearTimeout(timer) + console.log("[DFU] _waitForControlResult resolved for", deviceId, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:717") + resolve(Unit) + } + val origReject = fun(err: Any?){ + clearTimeout(timer) + console.error("[DFU] _waitForControlResult rejected for", deviceId, "err=", err, " at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:722") + reject(err) + } + if (session != null) { + session.resolve = origResolve + session.reject = origReject + } + } + ) + } +} +val dfuManager = DfuManager() +enum class PermissionType(override val value: String) : UTSEnumString { + BLUETOOTH("bluetooth"), + LOCATION("location"), + STORAGE("storage"), + CAMERA("camera"), + MICROPHONE("microphone"), + NOTIFICATIONS("notifications"), + CALENDAR("calendar"), + CONTACTS("contacts"), + SENSORS("sensors") +} +open class PermissionResult ( + @JsonNotNull + open var granted: Boolean = false, + @JsonNotNull + open var grantedPermissions: UTSArray, + @JsonNotNull + open var deniedPermissions: UTSArray, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("PermissionResult", "ak/PermissionManager.uts", 24, 6) + } +} +open class PermissionManager : IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("PermissionManager", "ak/PermissionManager.uts", 32, 14) + } + companion object { + private fun getPermissionsForType(type: PermissionType): UTSArray { + when (type) { + PermissionType.BLUETOOTH -> + return _uA( + "android.permission.BLUETOOTH_SCAN", + "android.permission.BLUETOOTH_CONNECT", + "android.permission.BLUETOOTH_ADVERTISE" + ) + PermissionType.LOCATION -> + return _uA( + "android.permission.ACCESS_FINE_LOCATION", + "android.permission.ACCESS_COARSE_LOCATION" + ) + PermissionType.STORAGE -> + return _uA( + "android.permission.READ_EXTERNAL_STORAGE", + "android.permission.WRITE_EXTERNAL_STORAGE" + ) + PermissionType.CAMERA -> + return _uA( + "android.permission.CAMERA" + ) + PermissionType.MICROPHONE -> + return _uA( + "android.permission.RECORD_AUDIO" + ) + PermissionType.NOTIFICATIONS -> + return _uA( + "android.permission.POST_NOTIFICATIONS" + ) + PermissionType.CALENDAR -> + return _uA( + "android.permission.READ_CALENDAR", + "android.permission.WRITE_CALENDAR" + ) + PermissionType.CONTACTS -> + return _uA( + "android.permission.READ_CONTACTS", + "android.permission.WRITE_CONTACTS" + ) + PermissionType.SENSORS -> + return _uA( + "android.permission.BODY_SENSORS" + ) + else -> + return _uA() + } + } + private fun getPermissionDisplayName(type: PermissionType): String { + when (type) { + PermissionType.BLUETOOTH -> + return "蓝牙" + PermissionType.LOCATION -> + return "位置" + PermissionType.STORAGE -> + return "存储" + PermissionType.CAMERA -> + return "相机" + PermissionType.MICROPHONE -> + return "麦克风" + PermissionType.NOTIFICATIONS -> + return "通知" + PermissionType.CALENDAR -> + return "日历" + PermissionType.CONTACTS -> + return "联系人" + PermissionType.SENSORS -> + return "身体传感器" + else -> + return "未知权限" + } + } + fun isPermissionGranted(type: PermissionType): Boolean { + try { + val permissions = this.getPermissionsForType(type) + val activity = UTSAndroid.getUniActivity() + if (activity == null || permissions.length === 0) { + return false + } + for(permission in resolveUTSValueIterator(permissions)){ + if (!UTSAndroid.checkSystemPermissionGranted(activity, _uA( + permission + ))) { + return false + } + } + return true + } + catch (e: Throwable) { + console.error("Error checking " + type + " permission:", e, " at ak/PermissionManager.uts:132") + return false + } + } + fun requestPermission(type: PermissionType, callback: (result: PermissionResult) -> Unit, showRationale: Boolean = true): Unit { + try { + val permissions = this.getPermissionsForType(type) + val activity = UTSAndroid.getUniActivity() + if (activity == null || permissions.length === 0) { + callback(PermissionResult(granted = false, grantedPermissions = _uA(), deniedPermissions = permissions)) + return + } + var allGranted = true + for(permission in resolveUTSValueIterator(permissions)){ + if (!UTSAndroid.checkSystemPermissionGranted(activity, _uA( + permission + ))) { + allGranted = false + break + } + } + if (allGranted) { + callback(PermissionResult(granted = true, grantedPermissions = permissions, deniedPermissions = _uA())) + return + } + UTSAndroid.requestSystemPermission(activity, permissions, fun(granted: Boolean, grantedPermissions: UTSArray){ + if (granted) { + callback(PermissionResult(granted = true, grantedPermissions = grantedPermissions, deniedPermissions = _uA())) + } else if (showRationale) { + this.showPermissionRationale(type, callback) + } else { + callback(PermissionResult(granted = false, grantedPermissions = grantedPermissions, deniedPermissions = this.getDeniedPermissions(permissions, grantedPermissions))) + } + } + , fun(denied: Boolean, deniedPermissions: UTSArray){ + callback(PermissionResult(granted = false, grantedPermissions = this.getGrantedPermissions(permissions, deniedPermissions), deniedPermissions = deniedPermissions)) + } + ) + } + catch (e: Throwable) { + console.error("Error requesting " + type + " permission:", e, " at ak/PermissionManager.uts:217") + callback(PermissionResult(granted = false, grantedPermissions = _uA(), deniedPermissions = this.getPermissionsForType(type))) + } + } + private fun showPermissionRationale(type: PermissionType, callback: (result: PermissionResult) -> Unit): Unit { + val permissionName = this.getPermissionDisplayName(type) + uni_showModal(ShowModalOptions(title = "权限申请", content = "\u9700\u8981" + permissionName + "\u6743\u9650\u624D\u80FD\u4F7F\u7528\u76F8\u5173\u529F\u80FD", confirmText = "去设置", cancelText = "取消", success = fun(result){ + if (result.confirm) { + this.openAppSettings() + callback(PermissionResult(granted = false, grantedPermissions = _uA(), deniedPermissions = this.getPermissionsForType(type))) + } else { + callback(PermissionResult(granted = false, grantedPermissions = _uA(), deniedPermissions = this.getPermissionsForType(type))) + } + } + )) + } + fun openAppSettings(): Unit { + try { + val context = UTSAndroid.getAppContext() + if (context != null) { + val intent = android.content.Intent() + intent.setAction("android.settings.APPLICATION_DETAILS_SETTINGS") + val uri = android.net.Uri.fromParts("package", context.getPackageName(), null) + intent.setData(uri) + intent.addFlags(android.content.Intent.FLAG_ACTIVITY_NEW_TASK) + context.startActivity(intent) + } + } + catch (e: Throwable) { + console.error("Failed to open app settings", e, " at ak/PermissionManager.uts:285") + uni_showToast(ShowToastOptions(title = "请手动前往系统设置修改应用权限", icon = "none", duration = 3000)) + } + } + private fun getGrantedPermissions(allPermissions: UTSArray, deniedPermissions: UTSArray): UTSArray { + return allPermissions.filter(fun(p): Boolean { + return !deniedPermissions.includes(p) + } + ) + } + private fun getDeniedPermissions(allPermissions: UTSArray, grantedPermissions: UTSArray): UTSArray { + return allPermissions.filter(fun(p): Boolean { + return !grantedPermissions.includes(p) + } + ) + } + fun requestMultiplePermissions(types: UTSArray, callback: (results: Map) -> Unit): Unit { + if (types.length === 0) { + callback(Map()) + return + } + val results = Map() + var remaining = types.length + for(type in resolveUTSValueIterator(types)){ + this.requestPermission(type, fun(result){ + results.set(type, result) + remaining-- + if (remaining === 0) { + callback(results) + } + } + , true) + } + } + fun requestBluetoothPermissions(callback: (granted: Boolean) -> Unit): Unit { + this.requestPermission(PermissionType.BLUETOOTH, fun(result){ + if (result.granted) { + this.requestPermission(PermissionType.LOCATION, fun(locationResult){ + callback(locationResult.granted) + }) + } else { + callback(false) + } + } + ) + } + } +} +open class ShowingCharacteristicsFor ( + @JsonNotNull + open var deviceId: String, + @JsonNotNull + open var serviceId: String, +) : UTSReactiveObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("ShowingCharacteristicsFor", "pages/akbletest.uvue", 107, 7) + } + override fun __v_create(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): UTSReactiveObject { + return ShowingCharacteristicsForReactiveObject(this, __v_isReadonly, __v_isShallow, __v_skip) + } +} +open class ShowingCharacteristicsForReactiveObject : ShowingCharacteristicsFor, IUTSReactive { + override var __v_raw: ShowingCharacteristicsFor + override var __v_isReadonly: Boolean + override var __v_isShallow: Boolean + override var __v_skip: Boolean + constructor(__v_raw: ShowingCharacteristicsFor, __v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean) : super(deviceId = __v_raw.deviceId, serviceId = __v_raw.serviceId) { + this.__v_raw = __v_raw + this.__v_isReadonly = __v_isReadonly + this.__v_isShallow = __v_isShallow + this.__v_skip = __v_skip + } + override fun __v_clone(__v_isReadonly: Boolean, __v_isShallow: Boolean, __v_skip: Boolean): ShowingCharacteristicsForReactiveObject { + return ShowingCharacteristicsForReactiveObject(this.__v_raw, __v_isReadonly, __v_isShallow, __v_skip) + } + override var deviceId: String + get() { + return _tRG(__v_raw, "deviceId", __v_raw.deviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("deviceId")) { + return + } + val oldValue = __v_raw.deviceId + __v_raw.deviceId = value + _tRS(__v_raw, "deviceId", oldValue, value) + } + override var serviceId: String + get() { + return _tRG(__v_raw, "serviceId", __v_raw.serviceId, __v_isReadonly, __v_isShallow) + } + set(value) { + if (!__v_canSet("serviceId")) { + return + } + val oldValue = __v_raw.serviceId + __v_raw.serviceId = value + _tRS(__v_raw, "serviceId", oldValue, value) + } +} +val GenPagesAkbletestClass = CreateVueComponent(GenPagesAkbletest::class.java, fun(): VueComponentOptions { + return VueComponentOptions(type = "page", name = "", inheritAttrs = GenPagesAkbletest.inheritAttrs, inject = GenPagesAkbletest.inject, props = GenPagesAkbletest.props, propsNeedCastKeys = GenPagesAkbletest.propsNeedCastKeys, emits = GenPagesAkbletest.emits, components = GenPagesAkbletest.components, styles = GenPagesAkbletest.styles) +} +, fun(instance, renderer): GenPagesAkbletest { + return GenPagesAkbletest(instance, renderer) +} +) +fun getErrorMessage(e: Any?): String { + if (e == null) { + return "" + } + if (UTSAndroid.`typeof`(e) == "string") { + return e as String + } + try { + return JSON.stringify(e) + } + catch (err: Throwable) { + return "" + (e as UTSError) + } +} +fun createApp(): UTSJSONObject { + val app = createSSRApp(GenAppClass) + return _uO("app" to app) +} +fun main(app: IApp) { + definePageRoutes() + defineAppConfig() + (createApp()["app"] as VueApp).mount(app, GenUniApp()) +} +open class UniAppConfig : io.dcloud.uniapp.appframe.AppConfig { + override var name: String = "akbleserver" + override var appid: String = "__UNI__95B2570" + override var versionName: String = "1.0.1" + override var versionCode: String = "101" + override var uniCompilerVersion: String = "4.76" + constructor() : super() {} +} +fun definePageRoutes() { + __uniRoutes.push(UniPageRoute(path = "pages/akbletest", component = GenPagesAkbletestClass, meta = UniPageMeta(isQuit = true), style = _uM("navigationBarTitleText" to "akble"))) +} +val __uniLaunchPage: Map = _uM("url" to "pages/akbletest", "style" to _uM("navigationBarTitleText" to "akble")) +fun defineAppConfig() { + __uniConfig.entryPagePath = "/pages/akbletest" + __uniConfig.globalStyle = _uM("navigationBarTextStyle" to "black", "navigationBarTitleText" to "体测训练", "navigationBarBackgroundColor" to "#F8F8F8", "backgroundColor" to "#F8F8F8") + __uniConfig.getTabBarConfig = fun(): Map? { + return null + } + __uniConfig.tabBar = __uniConfig.getTabBarConfig() + __uniConfig.conditionUrl = "" + __uniConfig.uniIdRouter = _uM() + __uniConfig.ready = true +} +open class GenUniApp : UniAppImpl() { + open val vm: GenApp? + get() { + return getAppVm() as GenApp? + } + open val `$vm`: GenApp? + get() { + return getAppVm() as GenApp? + } +} +fun getApp(): GenUniApp { + return getUniApp() as GenUniApp +} diff --git a/unpackage/cache/.app-android/src/pages/akbletest.kt b/unpackage/cache/.app-android/src/pages/akbletest.kt new file mode 100644 index 0000000..98a8ab3 --- /dev/null +++ b/unpackage/cache/.app-android/src/pages/akbletest.kt @@ -0,0 +1,1065 @@ +@file:Suppress("UNCHECKED_CAST", "USELESS_CAST", "INAPPLICABLE_JVM_NAME", "UNUSED_ANONYMOUS_PARAMETER", "NAME_SHADOWING", "UNNECESSARY_NOT_NULL_ASSERTION") +package uni.UNI95B2570 +import io.dcloud.uniapp.* +import io.dcloud.uniapp.extapi.* +import io.dcloud.uniapp.framework.* +import io.dcloud.uniapp.runtime.* +import io.dcloud.uniapp.vue.* +import io.dcloud.uniapp.vue.shared.* +import io.dcloud.unicloud.* +import io.dcloud.uts.* +import io.dcloud.uts.Map +import io.dcloud.uts.Set +import io.dcloud.uts.UTSAndroid +import io.dcloud.uniapp.extapi.chooseFile as uni_chooseFile +import io.dcloud.uniapp.extapi.getFileSystemManager as uni_getFileSystemManager +import io.dcloud.uniapp.extapi.showToast as uni_showToast +open class GenPagesAkbletest : BasePage { + constructor(__ins: ComponentInternalInstance, __renderer: String?) : super(__ins, __renderer) { + onMounted(fun() { + PermissionManager.requestBluetoothPermissions(fun(granted: Boolean){ + if (!granted) { + uni_showToast(ShowToastOptions(title = "请授权蓝牙和定位权限", icon = "none")) + } + } + ) + this.log("页面 mounted: 初始化事件监听和蓝牙权限请求完成") + bluetoothService.on("deviceFound", fun(payload){ + try { + var rawDevice = payload?.device + if (rawDevice == null) { + this.log("[event] deviceFound - payload.device is null, ignoring") + return + } + var name: String? = rawDevice.name + if (name == null) { + this.log("[event] deviceFound - 无名称,忽略: " + this._fmt(rawDevice as Any)) + return + } + val n = name as String + if (!(n.startsWith("CF") || n.startsWith("BCL"))) { + this.log("[event] deviceFound - 名称不匹配前缀,忽略: " + n) + return + } + val exists = this.devices.some(fun(d): Boolean { + return d != null && d.name == n + } + ) + if (!exists) { + this.devices.push(rawDevice as BleDevice) + val deviceIdStr = if ((rawDevice.deviceId != null)) { + rawDevice.deviceId + } else { + "" + } + this.log("发现设备: " + n + " (" + deviceIdStr + ")") + } else { + val deviceIdStr = if ((rawDevice.deviceId != null)) { + rawDevice.deviceId + } else { + "" + } + this.log("发现重复设备: " + n + " (" + deviceIdStr + ")") + } + } + catch (err: Throwable) { + this.log("[error] deviceFound handler error: " + getErrorMessage(err)) + console.log(err, " at pages/akbletest.uvue:198") + } + } + ) + bluetoothService.on("scanFinished", fun(payload){ + try { + this.scanning = false + this.log("[event] scanFinished -> " + this._fmt(payload)) + } + catch (err: Throwable) { + this.log("[error] scanFinished handler error: " + getErrorMessage(err)) + } + } + ) + bluetoothService.on("connectionStateChanged", fun(payload){ + try { + this.log("[event] connectionStateChanged -> " + this._fmt(payload)) + if (payload != null) { + val device = payload.device + val state = payload.state + this.log("\u8BBE\u5907 " + device?.deviceId + " \u8FDE\u63A5\u72B6\u6001\u53D8\u4E3A: " + state) + if (state == 2) { + if (device != null && device.deviceId != null && !this.connectedIds.includes(device.deviceId)) { + this.connectedIds.push(device.deviceId) + this.log("\u5DF2\u8BB0\u5F55\u5DF2\u8FDE\u63A5\u8BBE\u5907: " + device.deviceId) + } + } else if (state == 0) { + if (device != null && device.deviceId != null) { + this.connectedIds = this.connectedIds.filter(fun(id): Boolean { + return id !== device.deviceId + } + ) + this.log("\u5DF2\u79FB\u9664\u5DF2\u65AD\u5F00\u8BBE\u5907: " + device.deviceId) + } + } + } + } + catch (err: Throwable) { + this.log("[error] connectionStateChanged handler error: " + getErrorMessage(err)) + } + } + ) + } + , __ins) + } + @Suppress("UNUSED_PARAMETER", "UNUSED_VARIABLE") + override fun `$render`(): Any? { + val _ctx = this + val _cache = this.`$`.renderCache + return _cE("scroll-view", _uM("direction" to "vertical", "class" to "container"), _uA( + _cE("view", _uM("class" to "section"), _uA( + _cE("button", _uM("onClick" to _ctx.scanDevices, "disabled" to _ctx.scanning), _tD(if (_ctx.scanning) { + "正在扫描..." + } else { + "扫描设备" + } + ), 9, _uA( + "onClick", + "disabled" + )), + _cE("input", _uM("modelValue" to _ctx.optionalServicesInput, "onInput" to fun(`$event`: UniInputEvent){ + _ctx.optionalServicesInput = `$event`.detail.value + } + , "placeholder" to "可选服务 UUID, 逗号分隔", "style" to _nS(_uM("margin-left" to "12px", "width" to "40%"))), null, 44, _uA( + "modelValue", + "onInput" + )), + _cE("button", _uM("onClick" to _ctx.autoConnect, "disabled" to (_ctx.connecting || _ctx.devices.length == 0), "style" to _nS(_uM("margin-left" to "12px"))), _tD(if (_ctx.connecting) { + "正在自动连接..." + } else { + "自动连接" + } + ), 13, _uA( + "onClick", + "disabled" + )), + _cE("view", null, _uA( + _cE("text", null, "设备计数: " + _tD(_ctx.devices.length), 1), + _cE("text", _uM("style" to _nS(_uM("font-size" to "12px", "color" to "gray"))), _tD(_ctx._fmt(_ctx.devices)), 5) + )), + if (isTrue(_ctx.devices.length)) { + _cE("view", _uM("key" to 0), _uA( + _cE("text", null, "已发现设备:"), + _cE(Fragment, null, RenderHelpers.renderList(_ctx.devices, fun(item, __key, __index, _cached): Any { + return _cE("view", _uM("key" to item.deviceId, "class" to "device-item"), _uA( + _cE("text", null, _tD(if (item.name != "") { + item.name + } else { + "未知设备" + }) + " (" + _tD(item.deviceId) + ")", 1), + _cE("button", _uM("onClick" to fun(){ + _ctx.connect(item.deviceId) + }), "连接", 8, _uA( + "onClick" + )), + if (isTrue(_ctx.connectedIds.includes(item.deviceId))) { + _cE("button", _uM("key" to 0, "onClick" to fun(){ + _ctx.disconnect(item.deviceId) + }, "disabled" to _ctx.disconnecting), "断开", 8, _uA( + "onClick", + "disabled" + )) + } else { + _cC("v-if", true) + }, + if (isTrue(_ctx.connectedIds.includes(item.deviceId))) { + _cE("button", _uM("key" to 1, "onClick" to fun(){ + _ctx.showServices(item.deviceId) + }), "查看服务", 8, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + }, + if (isTrue(_ctx.connectedIds.includes(item.deviceId))) { + _cE("button", _uM("key" to 2, "onClick" to fun(){ + _ctx.autoDiscoverInterfaces(item.deviceId) + }), "自动发现接口", 8, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + }, + if (isTrue(_ctx.connectedIds.includes(item.deviceId))) { + _cE("button", _uM("key" to 3, "onClick" to fun(){ + _ctx.getDeviceInfo(item.deviceId) + }), "设备信息", 8, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + }, + if (isTrue(_ctx.connectedIds.includes(item.deviceId))) { + _cE("button", _uM("key" to 4, "onClick" to fun(){ + _ctx.startDfuFlow(item.deviceId) + }), "DFU 升级", 8, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + }, + if (isTrue(_ctx.connectedIds.includes(item.deviceId))) { + _cE("button", _uM("key" to 5, "onClick" to fun(){ + _ctx.startDfuFlow(item.deviceId, "/static/OmFw2509140009.zip") + }), "使用内置固件 DFU", 8, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + } + )) + }), 128) + )) + } else { + _cC("v-if", true) + } + )), + _cE("view", _uM("class" to "section"), _uA( + _cE("text", null, "日志:"), + _cE("scroll-view", _uM("direction" to "vertical", "style" to _nS(_uM("height" to "240px"))), _uA( + _cE(Fragment, null, RenderHelpers.renderList(_ctx.logs, fun(log, idx, __index, _cached): Any { + return _cE("text", _uM("key" to idx, "style" to _nS(_uM("font-size" to "12px"))), _tD(log), 5) + } + ), 128) + ), 4) + )), + if (isTrue(_ctx.showingServicesFor)) { + _cE("view", _uM("key" to 0), _uA( + _cE("view", _uM("class" to "section"), _uA( + _cE("text", null, "设备 " + _tD(_ctx.showingServicesFor) + " 的服务:", 1), + if (isTrue(_ctx.services.length)) { + _cE("view", _uM("key" to 0), _uA( + _cE(Fragment, null, RenderHelpers.renderList(_ctx.services, fun(srv, __key, __index, _cached): Any { + return _cE("view", _uM("key" to srv.uuid, "class" to "service-item"), _uA( + _cE("text", null, _tD(srv.uuid), 1), + _cE("button", _uM("onClick" to fun(){ + _ctx.showCharacteristics(_ctx.showingServicesFor, srv.uuid) + }), "查看特征", 8, _uA( + "onClick" + )) + )) + }), 128) + )) + } else { + _cE("view", _uM("key" to 1), _uA( + _cE("text", null, "无服务") + )) + }, + _cE("button", _uM("onClick" to _ctx.closeServices), "关闭", 8, _uA( + "onClick" + )) + )) + )) + } else { + _cC("v-if", true) + } + , + if (isTrue(_ctx.showingCharacteristicsFor)) { + _cE("view", _uM("key" to 1), _uA( + _cE("view", _uM("class" to "section"), _uA( + _cE("text", null, "服务 的特征:"), + if (isTrue(_ctx.characteristics.length)) { + _cE("view", _uM("key" to 0), _uA( + _cE(Fragment, null, RenderHelpers.renderList(_ctx.characteristics, fun(char, __key, __index, _cached): Any { + return _cE("view", _uM("key" to char.uuid, "class" to "char-item"), _uA( + _cE("text", null, _tD(char.uuid) + " [" + _tD(_ctx.charProps(char)) + "]", 1), + _cE("view", _uM("style" to _nS(_uM("display" to "flex", "flex-direction" to "row", "margin-top" to "6px"))), _uA( + if (isTrue(char.properties?.read)) { + _cE("button", _uM("key" to 0, "onClick" to fun(){ + _ctx.readCharacteristic(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid) + }), "读取", 8, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + }, + if (isTrue(char.properties?.write)) { + _cE("button", _uM("key" to 1, "onClick" to fun(){ + _ctx.writeCharacteristic(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid) + }), "写入(测试)", 8, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + }, + if (isTrue(char.properties?.notify)) { + _cE("button", _uM("key" to 2, "onClick" to fun(){ + _ctx.toggleNotify(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid) + }), _tD(if (_ctx.isNotifying(char.uuid)) { + "取消订阅" + } else { + "订阅" + }), 9, _uA( + "onClick" + )) + } else { + _cC("v-if", true) + } + ), 4) + )) + }), 128) + )) + } else { + _cE("view", _uM("key" to 1), _uA( + _cE("text", null, "无特征") + )) + }, + _cE("button", _uM("onClick" to _ctx.closeCharacteristics), "关闭", 8, _uA( + "onClick" + )) + )) + )) + } else { + _cC("v-if", true) + } + )) + } + open var scanning: Boolean by `$data` + open var connecting: Boolean by `$data` + open var disconnecting: Boolean by `$data` + open var devices: UTSArray by `$data` + open var connectedIds: UTSArray by `$data` + open var logs: UTSArray by `$data` + open var showingServicesFor: String by `$data` + open var services: UTSArray by `$data` + open var showingCharacteristicsFor: ShowingCharacteristicsFor by `$data` + open var characteristics: UTSArray by `$data` + open var protocolDeviceId: String by `$data` + open var protocolServiceId: String by `$data` + open var protocolWriteCharId: String by `$data` + open var protocolNotifyCharId: String by `$data` + open var protocolHandlerMap: Map by `$data` + open var protocolHandler: ProtocolHandler? by `$data` + open var optionalServicesInput: String by `$data` + open var presetOptions: UTSArray by `$data` + open var presetSelected: String by `$data` + open var notifyingMap: Map by `$data` + @Suppress("USELESS_CAST") + override fun data(): Map { + return _uM("scanning" to false, "connecting" to false, "disconnecting" to false, "devices" to _uA(), "connectedIds" to _uA(), "logs" to _uA(), "showingServicesFor" to "", "services" to _uA(), "showingCharacteristicsFor" to ShowingCharacteristicsFor(deviceId = "", serviceId = ""), "characteristics" to _uA(), "protocolDeviceId" to "", "protocolServiceId" to "", "protocolWriteCharId" to "", "protocolNotifyCharId" to "", "protocolHandlerMap" to Map(), "protocolHandler" to null as ProtocolHandler?, "optionalServicesInput" to "", "presetOptions" to _uA( + object : UTSJSONObject() { + var label = "无" + var value = "" + }, + object : UTSJSONObject() { + var label = "Battery Service (180F)" + var value = "0000180f-0000-1000-8000-00805f9b34fb" + }, + object : UTSJSONObject() { + var label = "Device Information (180A)" + var value = "0000180a-0000-1000-8000-00805f9b34fb" + }, + object : UTSJSONObject() { + var label = "Generic Attribute (1801)" + var value = "00001801-0000-1000-8000-00805f9b34fb" + }, + object : UTSJSONObject() { + var label = "Nordic DFU" + var value = "00001530-1212-efde-1523-785feabcd123" + }, + object : UTSJSONObject() { + var label = "Nordic UART (NUS)" + var value = "6e400001-b5a3-f393-e0a9-e50e24dcca9e" + }, + object : UTSJSONObject() { + var label = "自定义" + var value = "custom" + } + ), "presetSelected" to "", "notifyingMap" to Map()) + } + open fun startDfuFlow(deviceId: String, staticFilePath: String = ""): UTSPromise { + return wrapUTSPromise(suspend w@{ + if (staticFilePath != null && staticFilePath !== "") { + this.log("DFU 开始: 使用内置固件文件 " + staticFilePath) + } else { + this.log("DFU 开始: 请选择固件文件") + } + try { + var chosenPath: String? = null + var fileName: String? = null + if (staticFilePath != null && staticFilePath !== "") { + chosenPath = staticFilePath.replace(UTSRegExp("^\\/+", ""), "") + val tmpName = staticFilePath.split(UTSRegExp("[\\/]", "")).pop() + fileName = if ((tmpName != null && tmpName !== "")) { + tmpName + } else { + staticFilePath + } + } else { + val res = await(UTSPromise(fun(resolve, reject){ + uni_chooseFile(ChooseFileOptions(count = 1, success = fun(r){ + return resolve(r) + } + , fail = fun(e){ + return reject(e) + } + )) + } + )) + console.log(res, " at pages/akbletest.uvue:257") + try { + val s = (fun(): String { + try { + return JSON.stringify(res) + } + catch (e: Throwable) { + return "" + } + } + )() + val m = s.match(UTSRegExp("\"(?:path|uri|tempFilePath|temp_file_path|tempFilePath|name)\"\\s*:\\s*\"([^\"]+)\"", "i")) + if (m != null && m.length >= 2) { + val capturedCandidate: String? = if (m[1] != null) { + m[1] + } else { + null + } + val captured: String = if (capturedCandidate != null) { + capturedCandidate + } else { + "" + } + if (captured !== "") { + chosenPath = captured + val toTest: String = captured + if (!(UTSRegExp("^[a-zA-Z]:\\\\|^\\\\\\/", "").test(toTest) || UTSRegExp(":\\/\\/", "").test(toTest))) { + val m2 = s.match(UTSRegExp("\"(?:path|uri|tempFilePath|temp_file_path|tempFilePath)\"\\s*:\\s*\"([^\"]+)\"", "i")) + if (m2 != null && m2.length >= 2 && m2[1] != null) { + val pathCandidate: String = if (m2[1] != null) { + ("" + m2[1]) + } else { + "" + } + if (pathCandidate !== "") { + chosenPath = pathCandidate + } + } + } + } + } + val nameMatch = s.match(UTSRegExp("\"name\"\\s*:\\s*\"([^\"]+)\"", "i")) + if (nameMatch != null && nameMatch.length >= 2 && nameMatch[1] != null) { + val nm: String = if (nameMatch[1] != null) { + ("" + nameMatch[1]) + } else { + "" + } + if (nm !== "") { + fileName = nm + } + } + } + catch (err: Throwable) {} + } + if (chosenPath == null || chosenPath == "") { + this.log("未选择文件") + return@w + } + val fpStr: String = chosenPath as String + val lastSeg = fpStr.split(UTSRegExp("[\\/]", "")).pop() + val displayName = if ((fileName != null && fileName !== "")) { + fileName + } else { + if (lastSeg != null && lastSeg !== "") { + lastSeg + } else { + fpStr + } + } + this.log("已选文件: " + displayName + " 路径: " + fpStr) + val bytes = await(this._readFileAsUint8Array(fpStr)) + this.log("固件读取完成, 大小: " + bytes.length) + try { + await(dfuManager.startDfu(deviceId, bytes, DfuOptions(useNordic = false, onProgress = fun(p: Number){ + return this.log("DFU 进度: " + p + "%") + } + , onLog = fun(s: String){ + return this.log("DFU: " + s) + } + , controlTimeout = 30000))) + this.log("DFU 完成") + } + catch (e: Throwable) { + this.log("DFU 失败: " + getErrorMessage(e)) + } + } + catch (e: Throwable) { + console.log("选择或读取固件失败: " + e, " at pages/akbletest.uvue:308") + } + }) + } + open var _readFileAsUint8Array = ::gen__readFileAsUint8Array_fn + open fun gen__readFileAsUint8Array_fn(path: String): UTSPromise { + return UTSPromise(fun(resolve, reject){ + try { + console.log("should readfile", " at pages/akbletest.uvue:315") + val fsm = uni_getFileSystemManager() + console.log(fsm, " at pages/akbletest.uvue:317") + fsm.readFile(ReadFileOptions(filePath = path, success = fun(res){ + try { + val data = res.data as ArrayBuffer + val arr = Uint8Array(data) + resolve(arr) + } + catch (e: Throwable) { + reject(e) + } + } + , fail = fun(err){ + reject(err) + } + )) + } + catch (e: Throwable) { + reject(e) + } + } + ) + } + open var log = ::gen_log_fn + open fun gen_log_fn(msg: String) { + val ts = Date().toISOString() + this.logs.unshift("[" + ts + "] " + msg) + if (this.logs.length > 100) { + this.logs.length = 100 + } + } + open var _fmt = ::gen__fmt_fn + open fun gen__fmt_fn(obj: Any): String { + try { + if (obj == null) { + return "null" + } + if (UTSAndroid.`typeof`(obj) == "string") { + return obj as String + } + return JSON.stringify(obj) + } + catch (e: Throwable) { + return "" + obj + } + } + open var onPresetChange = ::gen_onPresetChange_fn + open fun gen_onPresetChange_fn(e: Any) { + try { + val s = (fun(): String { + try { + return JSON.stringify(e) + } + catch (err: Throwable) { + return "" + } + } + )() + var kVal: String = this.presetSelected + val m = s.match(UTSRegExp("\"detail\"\\s*:\\s*\\{[^}]*\"value\"\\s*:\\s*\"([^\\\"]+)\"", "i")) + if (m != null && m.length >= 2 && m[1] != null) { + kVal = "" + m[1] + } else { + val m2 = s.match(UTSRegExp("\"value\"\\s*:\\s*\"([^\\\"]+)\"", "i")) + if (m2 != null && m2.length >= 2 && m2[1] != null) { + kVal = "" + m2[1] + } + } + this.presetSelected = kVal + if (kVal == "custom" || kVal == "") { + this.log("已选择预设: " + (if (kVal == "custom") { + "自定义" + } else { + "无" + } + )) + return + } + this.optionalServicesInput = kVal + this.log("已选择预设服务 UUID: " + kVal) + } + catch (err: Throwable) { + this.log("[error] onPresetChange: " + getErrorMessage(err)) + } + } + open var scanDevices = ::gen_scanDevices_fn + open fun gen_scanDevices_fn() { + try { + this.scanning = true + this.devices = _uA() + var raw = (if (this.optionalServicesInput != null) { + this.optionalServicesInput + } else { + "" + } + ).trim() + if (raw.length == 0 && this.presetSelected != null && this.presetSelected !== "" && this.presetSelected !== "custom") { + raw = this.presetSelected + } + val normalize = fun(s: String): String { + if (s == null || s.length == 0) { + return "" + } + val u = s.toLowerCase().replace(UTSRegExp("^0x", ""), "").trim() + val hex = u.replace(UTSRegExp("[^0-9a-f]", "g"), "") + if (UTSRegExp("^[0-9a-f]{4}\$", "").test(hex)) { + return "0000" + hex + "-0000-1000-8000-00805f9b34fb" + } + return s + } + val optionalServices = if (raw.length > 0) { + raw.split(",").map(fun(s): String { + return normalize(s.trim()) + }).filter(fun(s): Boolean { + return s.length > 0 + }) + } else { + _uA() + } + this.log("开始扫描... optionalServices=" + JSON.stringify(optionalServices)) + bluetoothService.scanDevices(ScanDevicesOptions(protocols = _uA( + "BLE" + ), optionalServices = optionalServices)).then(fun(){ + this.log("scanDevices resolved") + } + ).`catch`(fun(e){ + this.log("[error] scanDevices failed: " + getErrorMessage(e)) + this.scanning = false + } + ) + } + catch (err: Throwable) { + this.log("[error] scanDevices thrown: " + getErrorMessage(err)) + this.scanning = false + } + } + open var connect = ::gen_connect_fn + open fun gen_connect_fn(deviceId: String) { + this.connecting = true + this.log("connect start -> " + deviceId) + try { + bluetoothService.connectDevice(deviceId, "BLE", BleConnectOptionsExt(timeout = 10000)).then(fun(){ + if (!this.connectedIds.includes(deviceId)) { + this.connectedIds.push(deviceId) + } + this.log("连接成功: " + deviceId) + } + ).`catch`(fun(e){ + this.log("连接失败: " + getErrorMessage(e!!)) + } + ).`finally`(fun(){ + this.connecting = false + this.log("connect finished -> " + deviceId) + } + ) + } + catch (err: Throwable) { + this.log("[error] connect thrown: " + getErrorMessage(err)) + this.connecting = false + } + } + open var disconnect = ::gen_disconnect_fn + open fun gen_disconnect_fn(deviceId: String) { + if (!this.connectedIds.includes(deviceId)) { + return + } + this.disconnecting = true + this.log("disconnect start -> " + deviceId) + bluetoothService.disconnectDevice(deviceId, "BLE").then(fun(){ + this.log("已断开: " + deviceId) + this.connectedIds = this.connectedIds.filter(fun(id): Boolean { + return id !== deviceId + } + ) + this.protocolHandlerMap.`delete`(deviceId) + } + ).`catch`(fun(e){ + this.log("断开失败: " + getErrorMessage(e!!)) + } + ).`finally`(fun(){ + this.disconnecting = false + this.log("disconnect finished -> " + deviceId) + } + ) + } + open var showServices = ::gen_showServices_fn + open fun gen_showServices_fn(deviceId: String) { + this.showingServicesFor = deviceId + this.services = _uA() + this.log("showServices start -> " + deviceId) + bluetoothService.getServices(deviceId).then(fun(list){ + this.log("showServices result -> " + this._fmt(list)) + this.services = list as UTSArray + this.log("服务数: " + (if (list != null) { + list.length + } else { + 0 + } + ) + " [" + deviceId + "]") + } + ).`catch`(fun(e){ + this.log("获取服务失败: " + getErrorMessage(e!!)) + } + ).`finally`(fun(){ + this.log("showServices finished -> " + deviceId) + } + ) + } + open var closeServices = ::gen_closeServices_fn + open fun gen_closeServices_fn() { + this.showingServicesFor = "" + this.services = _uA() + } + open var showCharacteristics = ::gen_showCharacteristics_fn + open fun gen_showCharacteristics_fn(deviceId: String, serviceId: String) { + this.showingCharacteristicsFor = ShowingCharacteristicsFor(deviceId = deviceId, serviceId = serviceId) + this.characteristics = _uA() + bluetoothService.getCharacteristics(deviceId, serviceId).then(fun(list){ + this.characteristics = list as UTSArray + console.log("特征数: " + (if (list != null) { + list.length + } else { + 0 + } + ) + " [" + deviceId + "]", " at pages/akbletest.uvue:462") + val writeChar = this.characteristics.find(fun(c): Boolean { + return c.properties.write + } + ) + val notifyChar = this.characteristics.find(fun(c): Boolean { + return c.properties.notify + } + ) + if (writeChar != null && notifyChar != null) { + this.protocolDeviceId = deviceId + this.protocolServiceId = serviceId + this.protocolWriteCharId = writeChar.uuid + this.protocolNotifyCharId = notifyChar.uuid + var abs = bluetoothService as BluetoothService + this.protocolHandler = ProtocolHandler(abs) + var handler = this.protocolHandler!! + handler?.setConnectionParameters(deviceId, serviceId, writeChar.uuid, notifyChar.uuid) + handler?.initialize()?.then(fun(){ + console.log("协议处理器已初始化,可进行协议测试", " at pages/akbletest.uvue:476") + } + )?.`catch`(fun(e){ + console.log("协议处理器初始化失败: " + getErrorMessage(e!!), " at pages/akbletest.uvue:478") + } + ) + } + } + ).`catch`(fun(e){ + console.log("获取特征失败: " + getErrorMessage(e!!), " at pages/akbletest.uvue:482") + } + ) + } + open var closeCharacteristics = ::gen_closeCharacteristics_fn + open fun gen_closeCharacteristics_fn() { + this.showingCharacteristicsFor = ShowingCharacteristicsFor(deviceId = "", serviceId = "") + this.characteristics = _uA() + } + open var charProps = ::gen_charProps_fn + open fun gen_charProps_fn(char: BleCharacteristic): String { + val p = char.properties + val parts = _uA() + if (p.read) { + parts.push("R") + } + if (p.write) { + parts.push("W") + } + if (p.notify) { + parts.push("N") + } + if (p.indicate) { + parts.push("I") + } + return parts.join("/") + } + open var isNotifying = ::gen_isNotifying_fn + open fun gen_isNotifying_fn(uuid: String): Boolean { + return this.notifyingMap.has(uuid) && this.notifyingMap.get(uuid) == true + } + open var readCharacteristic = ::gen_readCharacteristic_fn + open fun gen_readCharacteristic_fn(deviceId: String, serviceId: String, charId: String): UTSPromise { + return wrapUTSPromise(suspend { + try { + this.log("readCharacteristic " + charId + " ...") + val buf = await(bluetoothService.readCharacteristic(deviceId, serviceId, charId)) + var text = "" + try { + text = TextDecoder().decode(Uint8Array(buf)) + } + catch (e: Throwable) { + text = "" + } + val hex = UTSArray.from(Uint8Array(buf)).map(fun(b): String { + return b.toString(16).padStart(2, "0") + } + ).join(" ") + console.log("\u8BFB\u53D6 " + charId + ": text='" + text + "' hex='" + hex + "'", " at pages/akbletest.uvue:511") + this.log("\u8BFB\u53D6 " + charId + ": text='" + text + "' hex='" + hex + "'") + } + catch (e: Throwable) { + this.log("读取特征失败: " + getErrorMessage(e)) + } + }) + } + open var writeCharacteristic = ::gen_writeCharacteristic_fn + open fun gen_writeCharacteristic_fn(deviceId: String, serviceId: String, charId: String): UTSPromise { + return wrapUTSPromise(suspend { + try { + val payload = Uint8Array(_uA( + 0x01 + )) + val ok = await(bluetoothService.writeCharacteristic(deviceId, serviceId, charId, payload, null)) + if (ok) { + this.log("\u5199\u5165 " + charId + " \u6210\u529F") + } else { + this.log("\u5199\u5165 " + charId + " \u5931\u8D25") + } + } + catch (e: Throwable) { + this.log("写入特征失败: " + getErrorMessage(e)) + } + }) + } + open var toggleNotify = ::gen_toggleNotify_fn + open fun gen_toggleNotify_fn(deviceId: String, serviceId: String, charId: String): UTSPromise { + return wrapUTSPromise(suspend { + try { + val map = this.notifyingMap + val cur = map.get(charId) == true + if (cur) { + await(bluetoothService.unsubscribeCharacteristic(deviceId, serviceId, charId)) + map.set(charId, false) + this.log("\u53D6\u6D88\u8BA2\u9605 " + charId) + } else { + await(bluetoothService.subscribeCharacteristic(deviceId, serviceId, charId, fun(payload: Any){ + var data: ArrayBuffer? = null + try { + if (payload is ArrayBuffer) { + data = payload as ArrayBuffer + } else if (payload != null && UTSAndroid.`typeof`(payload) == "string") { + try { + val s = atob(payload as String) + val tmp = Uint8Array(s.length) + run { + var i: Number = 0 + while(i < s.length){ + val ch = s.charCodeAt(i) + tmp[i] = if ((ch == null)) { + 0 + } else { + (ch and 0xff) + } + i++ + } + } + data = tmp.buffer + } catch (e: Throwable) { + data = null + } + } else if (payload != null && (payload as UTSJSONObject).get("data") is ArrayBuffer) { + data = (payload as UTSJSONObject).get("data") as ArrayBuffer + } + val arr = if (data != null) { + Uint8Array(data) + } else { + Uint8Array(_uA()) + } + val hex = UTSArray.from(arr).map(fun(b): String { + return b.toString(16).padStart(2, "0") + } + ).join(" ") + this.log("notify " + charId + ": " + hex) + } + catch (e: Throwable) { + this.log("notify callback error: " + getErrorMessage(e)) + } + } + )) + map.set(charId, true) + this.log("\u8BA2\u9605 " + charId) + } + } + catch (e: Throwable) { + this.log("订阅/取消订阅失败: " + getErrorMessage(e)) + } + }) + } + open var autoConnect = ::gen_autoConnect_fn + open fun gen_autoConnect_fn() { + if (this.connecting) { + return + } + this.connecting = true + val toConnect = this.devices.filter(fun(d): Boolean { + return !this.connectedIds.includes(d.deviceId) + } + ) + if (toConnect.length == 0) { + this.log("没有可自动连接的设备") + this.connecting = false + return + } + var successCount: Number = 0 + var failCount: Number = 0 + var finished: Number = 0 + toConnect.forEach(fun(device){ + bluetoothService.connectDevice(device.deviceId, "BLE", BleConnectOptionsExt(timeout = 10000)).then(fun(){ + if (!this.connectedIds.includes(device.deviceId)) { + this.connectedIds.push(device.deviceId) + } + this.log("自动连接成功: " + device.deviceId) + successCount++ + } + ).`catch`(fun(e){ + this.log("自动连接失败: " + device.deviceId + " " + getErrorMessage(e!!)) + failCount++ + } + ).`finally`(fun(){ + finished++ + if (finished == toConnect.length) { + this.connecting = false + this.log("\u81EA\u52A8\u8FDE\u63A5\u5B8C\u6210\uFF0C\u6210\u529F" + successCount + "\uFF0C\u5931\u8D25" + failCount) + } + } + ) + } + ) + } + open var autoDiscoverInterfaces = ::gen_autoDiscoverInterfaces_fn + open fun gen_autoDiscoverInterfaces_fn(deviceId: String) { + this.log("自动发现接口中...") + bluetoothService.getAutoBleInterfaces(deviceId).then(fun(res){ + console.log(res, " at pages/akbletest.uvue:604") + this.log("自动发现接口成功: " + JSON.stringify(res)) + } + ).`catch`(fun(e){ + console.log(e, " at pages/akbletest.uvue:608") + this.log("自动发现接口失败: " + getErrorMessage(e!!)) + } + ) + } + open var getOrInitProtocolHandler = ::gen_getOrInitProtocolHandler_fn + open fun gen_getOrInitProtocolHandler_fn(deviceId: String): UTSPromise { + return wrapUTSPromise(suspend w@{ + var handler = this.protocolHandlerMap.get(deviceId) + if (handler == null) { + val res = await(bluetoothService.getAutoBleInterfaces(deviceId)) + handler = ProtocolHandler(bluetoothService as BluetoothService) + handler.setConnectionParameters(deviceId, res.serviceId, res.writeCharId, res.notifyCharId) + await(handler.initialize()) + this.protocolHandlerMap.set(deviceId, handler) + this.log("\u534F\u8BAE\u5904\u7406\u5668\u5DF2\u521D\u59CB\u5316: " + deviceId) + } + return@w handler!! + }) + } + open var getDeviceInfo = ::gen_getDeviceInfo_fn + open fun gen_getDeviceInfo_fn(deviceId: String): UTSPromise { + return wrapUTSPromise(suspend { + this.log("获取设备信息中...") + try { + try { + val handler = await(this.getOrInitProtocolHandler(deviceId)) + val battery = await(handler.testBatteryLevel()) + this.log("协议: 电量: " + battery) + val swVersion = await(handler.testVersionInfo(false)) + this.log("协议: 软件版本: " + swVersion) + val hwVersion = await(handler.testVersionInfo(true)) + this.log("协议: 硬件版本: " + hwVersion) + } + catch (protoErr: Throwable) { + this.log("协议处理器不可用或初始化失败,继续使用通用 GATT 查询: " + (if ((protoErr != null && protoErr is UTSError)) { + (protoErr as UTSError).message + } else { + this._fmt(protoErr) + } + )) + } + val stdServices = _uA( + "1800", + "1801", + "180f" + ).map(fun(s): String { + val hex = s.toLowerCase().replace(UTSRegExp("^0x", ""), "") + return if (UTSRegExp("^[0-9a-f]{4}\$", "").test(hex)) { + "0000" + hex + "-0000-1000-8000-00805f9b34fb" + } else { + s + } + } + ) + val services = await(bluetoothService.getServices(deviceId)) + for(svc in resolveUTSValueIterator(stdServices)){ + try { + this.log("读取服务: " + svc) + val found = services.find(fun(x: Any): Boolean { + val uuid = (x as UTSJSONObject).get("uuid") + return uuid != null && uuid.toString().toLowerCase() == svc.toLowerCase() + } + ) + if (found == null) { + this.log("未发现服务 " + svc + "(需重新扫描并包含 optionalServices)") + continue + } + val chars = await(bluetoothService.getCharacteristics(deviceId, found?.uuid as String)) + console.log("\u670D\u52A1 " + svc + " \u5305\u542B " + chars.length + " \u4E2A\u7279\u5F81", chars, " at pages/akbletest.uvue:665") + for(c in resolveUTSValueIterator(chars)){ + try { + if (c.properties?.read == true) { + val buf = await(bluetoothService.readCharacteristic(deviceId, found?.uuid as String, c.uuid)) + var text = "" + try { + text = TextDecoder().decode(Uint8Array(buf)) + } catch (e: Throwable) { + text = "" + } + val hex = UTSArray.from(Uint8Array(buf)).map(fun(b): String { + return b.toString(16).padStart(2, "0") + }).join(" ") + console.log("\u7279\u5F81 " + c.uuid + " \u8BFB\u53D6: text='" + text + "' hex='" + hex + "'", " at pages/akbletest.uvue:674") + } else { + console.log("\u7279\u5F81 " + c.uuid + " \u4E0D\u53EF\u8BFB", " at pages/akbletest.uvue:676") + } + } + catch (e: Throwable) { + console.log("\u8BFB\u53D6\u7279\u5F81 " + c.uuid + " \u5931\u8D25: " + getErrorMessage(e), " at pages/akbletest.uvue:679") + } + } + } + catch (e: Throwable) { + console.log("查询服务 " + svc + " 失败: " + getErrorMessage(e), " at pages/akbletest.uvue:683") + } + } + } + catch (e: Throwable) { + console.log("获取设备信息失败: " + getErrorMessage(e), " at pages/akbletest.uvue:688") + } + }) + } + companion object { + val styles: Map>> by lazy { + _nCS(_uA( + styles0 + ), _uA( + GenApp.styles + )) + } + val styles0: Map>> + get() { + return _uM("container" to _pS(_uM("paddingTop" to 16, "paddingRight" to 16, "paddingBottom" to 16, "paddingLeft" to 16, "flex" to 1)), "section" to _pS(_uM("marginBottom" to 18)), "device-item" to _pS(_uM("display" to "flex", "flexDirection" to "row", "flexWrap" to "wrap")), "service-item" to _pS(_uM("marginTop" to 6, "marginRight" to 0, "marginBottom" to 6, "marginLeft" to 0)), "char-item" to _pS(_uM("marginTop" to 6, "marginRight" to 0, "marginBottom" to 6, "marginLeft" to 0))) + } + var inheritAttrs = true + var inject: Map> = _uM() + var emits: Map = _uM() + var props = _nP(_uM()) + var propsNeedCastKeys: UTSArray = _uA() + var components: Map = _uM() + } +} diff --git a/unpackage/cache/.app-android/tsc/app-android/.tsbuildInfo b/unpackage/cache/.app-android/tsc/app-android/.tsbuildInfo new file mode 100644 index 0000000..be11d95 --- /dev/null +++ b/unpackage/cache/.app-android/tsc/app-android/.tsbuildInfo @@ -0,0 +1 @@ +{"program":{"fileNames":["f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/boolean.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/console.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/date.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/error.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/json.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/map.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/math.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/number.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/regexp.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/set.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/string.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/timers.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/utsjsonobject.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/arraybuffer.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/float32array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/float64array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/int8array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/int16array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/int32array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/uint8array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/uint8clampedarray.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/uint16array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/uint32array.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/dataview.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/iterable.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/common/common.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/shims.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es5.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2015.collection.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2015.promise.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2015.symbol.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2015.symbol.wellknown.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2015.iterable.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2018.asynciterable.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2018.asyncgenerator.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2018.promise.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/lib.es2020.symbol.wellknown.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/shims/index.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uts/index.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/hbuilder-x/hbuilderx.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/hbuilder-x/index.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/@vue/shared/dist/shared.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/@vue/reactivity/dist/reactivity.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/@vue/runtime-core/dist/runtime-core.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/@vue/global.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/vue.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/shims/common.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/shims/app-android.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/app-android/array.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/type.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/typevariable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/object.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/annotation/annotation.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/annotatedelement.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/genericdeclaration.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/serializable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/proxy/type.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/socketaddress.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/proxy.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/comparable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/uri.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/autocloseable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/closeable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/flushable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/outputstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/inputstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/url.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/package.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/accessibleobject.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/member.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/field.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/parameter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/executable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/constructor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/consumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/iterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection/iterable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection/assequence.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection/binarysearchby.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection/elementat.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection/groupingby.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection/iterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection/withindex.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/number.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/float.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/sequence.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/asiterable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/assequence.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/distinct.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/elementat.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/filterindexed.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/filterisinstance.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/filternotnull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/flatmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/flatmapindexed.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/flatten.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/generatesequence.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/groupingby.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/ifempty.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/minus.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/oneach.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/oneachindexed.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/requirenonulls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/runningfold.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/runningfoldindexed.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/runningreduce.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/runningreduceindexed.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/shuffled.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/sorted.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/sortedwith.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/zip.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence/zipwithnext.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/double.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doubleconsumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/spliterator/ofprimitive.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/spliterator/ofdouble.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/intconsumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/spliterator/ofint.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longconsumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/spliterator/oflong.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/todoublefunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/tointfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/tolongfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/function.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/comparator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/spliterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/iterable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/cloneable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/abstractcollection.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/abstractset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/hashset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/map/entry.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/bifunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/abstractmap/simpleentry.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/abstractmap/simpleimmutableentry.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/abstractmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/biconsumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/hashmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/linkedhashmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/jvm/functions/function1.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/jvm/functions/function2.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/jvm/functions/function0.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/sortedmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/map.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/intstream/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/intunaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/primitiveiterator/ofdouble.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/long.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/primitiveiterator/oflong.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/primitiveiterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/integer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/primitiveiterator/ofint.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/supplier.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/runnable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/doublestream/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doublefunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/doublesummarystatistics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doubleunaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doublebinaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/longstream/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longsupplier.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longbinaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/optionallong.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longpredicate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/longsummarystatistics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longtodoublefunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longtointfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/stream/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/unaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/collector/characteristics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/binaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/collector.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/intfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/predicate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/optional.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/basestream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/stream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/longunaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/objlongconsumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/longstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doubletointfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/objdoubleconsumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doubletolongfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doublesupplier.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/doublepredicate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/doublestream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/optionaldouble.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/intbinaryoperator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/objintconsumer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/intsupplier.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/optionalint.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/intpredicate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/inttodoublefunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/function/inttolongfunction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/intsummarystatistics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/stream/intstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/charsequence.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/appendable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/jvm/functions/function3.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/collections/grouping.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/random/random/default/serialized.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/jvm/internal/defaultconstructormarker.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/random/random/default.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/random/random.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/sequences/sequence.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/navigableset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/treeset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/linkedhashset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/set.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/sortedset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/random.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/listiterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/abstractlist.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/randomaccess.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/arraylist.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/intrange/companion.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/openendrange/defaultimpls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/openendrange.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/intprogression/companion.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/jvm/internal/markers/kmappedmarker.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/collections/intiterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/intprogression.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/closedrange/defaultimpls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/closedrange.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/ranges/intrange.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/collection.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/list.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/invoke/typedescriptor/ofmethod.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/invoke/typedescriptor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/invoke/typedescriptor/offield.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/method.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/reflect/recordcomponent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/guard.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/permission.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/domaincombiner.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/accesscontrolcontext.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/privilegedaction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/privilegedexceptionaction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/javax/security/auth/subject.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/principal.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/enumeration.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/classloader.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/cert/certificate/certificaterep.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/key.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/publickey.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/file/copyrecursively.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/file/readlines.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/byteorder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/buffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/readable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/charbuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/floatbuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/doublebuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/shortbuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/intbuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/longbuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/bytebuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/locale/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/locale/category.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/locale/filteringmode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/locale/isocountrycode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/locale/languagerange.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/locale.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/charset/charset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/path/whenmappings.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/path/copytorecursively.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/io/path/pathwalkoption.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/concurrent/timeunit.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/watchservice.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/watchevent/kind.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/watchevent/modifier.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/watchable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/watchkey.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/linkoption.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/void.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/filevisitresult.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/filteroutputstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/printstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/stacktraceelement.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/throwable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/exception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/ioexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/temporal.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/temporalamount.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/duration.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/temporalunit.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/format/resolverstyle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/temporalfield.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/valuerange.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/temporalaccessor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/temporalquery.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/format/textstyle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/zone/zoneoffsettransition.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/zone/zonerules.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/zoneid.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/temporaladjuster.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/zoneoffset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/month.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/temporal/chronofield.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/era.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/text/attributedcharacteriterator/attribute.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/text/format/field.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/text/fieldposition.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/text/characteriterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/text/attributedcharacteriterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/stringbuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/text/parseposition.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/text/format.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/format/formatstyle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/format/decimalstyle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/format/datetimeformatter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/chronoperiod.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/chronolocaldate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/chronozoneddatetime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/chronolocaldatetime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/instantsource.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/clock.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/chronology.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/period.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/isoera.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/abstractchronology.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/chrono/isochronology.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/dayofweek.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/localdate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/offsetdatetime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/offsettime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/localtime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/localdatetime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/zoneddatetime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/time/instant.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/attribute/filetime.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/attribute/basicfileattributes.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/filevisitor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/openoption.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/attribute/fileattribute.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/completionhandler.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/filechannel/mapmode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/any.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/consumeeach.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/consumes.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/consumesall.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/count.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/distinct.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/distinctby.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/drop.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/dropwhile.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/elementat.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/elementatornull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/filter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/filterindexed.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/filternot.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/filternotnull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/filternotnullto.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/first.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/firstornull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/flatmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/indexof.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/last.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/lastindexof.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/lastornull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/map.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/mapindexed.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/maxwith.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/minwith.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/none.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/requirenonulls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/sendblocking.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/single.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/singleornull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/take.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/takewhile.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/tochannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/tocollection.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/tolist.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/tomap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/trysendblocking.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/withindex.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel/zip.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/coroutines/coroutinecontext/defaultimpls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/coroutines/coroutinecontext/key.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/coroutines/coroutinecontext/element/defaultimpls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/coroutines/coroutinecontext/element.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/coroutines/coroutinecontext/plus.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/coroutines/coroutinecontext.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/coroutines/continuation.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/disposablehandle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/opdescriptor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/atomicop.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/atomicdesc.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/lockfreelinkedlistnode/makecondaddop.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/lockfreelinkedlistnode/tostring.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/concurrent/atomic/atomicreferencefieldupdater.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/lockfreelinkedlistnode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/lockfreelinkedlistnode/abstractatomicdesc.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/internal/lockfreelinkedlistnode/prepareop.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/selects/selectinstance.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/selects/selectclause1.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/receivechannel/defaultimpls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/receivechannel/onreceiveornull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/receivechannel/receiveornull.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/runtimeexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/illegalstateexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/concurrent/cancellationexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/channeliterator/defaultimpls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/channeliterator/next0.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/channeliterator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/receivechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/sendchannel/defaultimpls.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/selects/selectclause2.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlinx/coroutines/channels/sendchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/channel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/readablebytechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/scatteringbytechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/writablebytechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/bytechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/seekablebytechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/interruptiblechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/spi/abstractinterruptiblechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/mappedbytebuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/gatheringbytechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/filechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/filelock.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/asynchronouschannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/concurrent/future.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/concurrent/executor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/concurrent/callable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/concurrent/executorservice.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/asynchronousfilechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/accessmode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/directorystream/filter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/directorystream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/filestore.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/copyoption.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/spi/filesystemprovider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/pathmatcher.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/attribute/userprincipal.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/attribute/groupprincipal.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/attribute/userprincipallookupservice.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/filesystem.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/file/path.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/io/filetreewalk/walkstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/io/filetreewalk/directorystate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/io/filewalkdirection.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/io/filetreewalk.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/kotlin/io/filepathcomponents.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/file.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/writer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/printwriter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/reader.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/dictionary.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/hashtable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/properties.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/provider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/cert/certificate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/cert/certpath/certpathrep.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/cert/certpath.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/date.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/timestamp.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/codesigner.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/codesource.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/permissioncollection.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/security/protectiondomain.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/class.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/activity/screencapturecallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/keyevent/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/keyevent/dispatcherstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/ibinder/deathrecipient.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/iinterface.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/filedescriptor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/ibinder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/sizef.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/basebundle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/persistablebundle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/byte.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/sparsearray.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/size.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/bundle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/arraymap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/sparsebooleanarray.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parcel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parcelable/creator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parcelable/classloadercreator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parcelable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputdevice/motionrange.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/sensor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/sensormanager/dynamicsensorcallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/sensorlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/memoryfile.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/hardwarebuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/messenger.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/message.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/handler/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/messagequeue/idlehandler.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/messagequeue/onfiledescriptoreventlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/messagequeue.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/thread/state.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/thread/uncaughtexceptionhandler.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/thread.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/printer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/looper.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/handler.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/sensordirectchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/triggerevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/triggereventlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/sensorevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/sensoreventlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/sensormanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/lights/light.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/lights/lightstate/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/lights/lightstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/lights/lightsrequest/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/lights/lightsrequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/lights/lightsmanager/lightssession.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/lights/lightsmanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/keycharactermap/keydata.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/androidruntimeexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/keycharactermap/unavailableexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/keycharactermap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/vibrationeffect/composition.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/vibrationeffect.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/combinedvibration/parallelcombination.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/combinedvibration.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/audioattributes.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/vibrationattributes.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/vibrator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/vibratormanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/batterystate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputdevice.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/keyevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/context/bindserviceflags.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/applicationinfoflags.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/componentenabledsetting.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/componentinfoflags.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/androidexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/namenotfoundexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/onchecksumsreadylistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/packageinfoflags.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/property.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager/resolveinfoflags.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/insets.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/rect.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageiteminfo/displaynamecomparator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/attributeset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/xmlresourceparser.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/drawable/drawable/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parcelfiledescriptor/filedescriptordetachedexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parcelfiledescriptor/oncloselistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/networkinterface.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/inetaddress.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/socketoption.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/selector.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/spi/abstractselector.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/protocolfamily.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/datagrampacket.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/datagramsocket.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/networkchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/membershipkey.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/multicastchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/datagramchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/socketoptions.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/socketimpl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/socketimplfactory.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/serversocket.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/serversocketchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/pipe/sinkchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/pipe/sourcechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/pipe.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/spi/selectorprovider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/selectionkey.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/selectablechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/spi/abstractselectablechannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/nio/channels/socketchannel.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/net/socket.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parcelfiledescriptor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/fileoutputstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/io/fileinputstream.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/assetfiledescriptor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/assetmanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/fonts/fontvariationaxis.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/typeface/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/rectf.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/icu/util/ulocale/availabletype.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/icu/util/ulocale/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/icu/util/ulocale/category.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/icu/util/ulocale.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/localelist.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/paint/fontmetrics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/paint/align.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/paint/cap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/paint/fontmetricsint.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/paint/join.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/paint/style.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/path/direction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/path/filltype.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/path/op.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/path/whenmappings.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/path/copytorecursively.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/matrix/scaletofit.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/matrix.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/path.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/patheffect.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/shader/tilemode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/shader.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorfilter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/maskfilter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/blendmode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/xfermode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/paint.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/fonts/font.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/fonts/fontfamily/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/fonts/fontfamily.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/fonts/fontstyle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/typeface/customfallbackbuilder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/typeface.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/resources/notfoundexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/canvas/edgetype.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/canvas/vertexmode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/text/measuredtext.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/color.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/mesh.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/region/op.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/region.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/bitmap/compressformat.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/bitmap/config.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/displaymetrics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/picture.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace/adaptation.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace/renderintent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace/connector.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace/model.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace/named.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace/rgb/transferparameters.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace/rgb.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/colorspace.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/gainmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/bitmap.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/ninepatch.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/outline.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/porterduff/mode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/recordingcanvas.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/bitmapshader.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/runtimeshader.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/rendereffect.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/rendernode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/drawfilter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/canvas.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/movie.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/om/overlayidentifier.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/om/overlayinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/loader/assetsprovider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/loader/resourcesprovider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/loader/resourcesloader.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/typedvalue.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/configuration.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/resources.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/colorstatelist.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/typedarray.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/res/resources/theme.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/drawable/drawable/constantstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/bitmapfactory/options.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/drawable/drawable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageiteminfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/permissioninfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/versionedpackage.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intent/shortcuticonresource.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/net/uri/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/net/uri.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textlinks/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textclassifier/entityconfig/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textclassifier/entityconfig.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textlinks/request/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textlinks/request.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textlinks/textlink.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo/accessibilityaction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo/collectioninfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo/collectioniteminfo/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo/collectioniteminfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo/extrarenderinginfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo/rangeinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo/touchdelegateinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitywindowinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilitynodeprovider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilityrecord.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilityevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/animation/layoutanimationcontroller/animationparameters.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewgroup/layoutparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewgroup/marginlayoutparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewgroup/onhierarchychangelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/contextmenu/contextmenuinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/contextmenu.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/point.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/window/onbackinvokedcallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/window/onbackinvokeddispatcher.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewparent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsetsanimation/bounds.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsets/side.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsets/type.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/displaycutout/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/displaycutout.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/roundedcorner.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/displayshape.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsets.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsetsanimation/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/animation/timeinterpolator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/animation/interpolator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsetsanimation.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewoverlay.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/animation/layouttransition/transitionlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/animation/animator/animatorlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/animation/animator/animatorpauselistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/animation/animator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/animation/layouttransition.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/pointericon.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/motionevent/pointercoords.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/motionevent/pointerproperties.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/motionevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/translation/translationspec.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/translation/translationcapability.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/clipdescription.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/dragevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/animation/animation/description.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/animation/transformation.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/animation/animation.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/animation/animation/animationlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewstructure/htmlinfo/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewstructure/htmlinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/autofill/autofillvalue.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/autofill/autofillid.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewstructure.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/animation/layoutanimationcontroller.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewmanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/viewgroup.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/accessibilitydelegate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/abssavedstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/basesavedstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/measurespec.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onapplywindowinsetslistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onattachstatechangelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/oncapturedpointerlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onclicklistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/oncontextclicklistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/oncreatecontextmenulistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/ondraglistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onfocuschangelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/ongenericmotionlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onhoverlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onkeylistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onlayoutchangelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onlongclicklistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onscrollchangelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onsystemuivisibilitychangelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/ontouchlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view/onunhandledkeyeventlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/touchdelegate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/property.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/attachedsurfacecontrol/onbuffertransformhintchangedlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfacecontrol/trustedpresentationthresholds.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfacecontrol/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfacecontrol/transactioncommittedlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfacecontrol.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/syncfence.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfacecontrol/transaction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/attachedsurfacecontrol.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/animation/statelistanimator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/display/hdrcapabilities.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/display/mode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/hardware/display/deviceproductinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/display.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsetscontroller/oncontrollableinsetschangedlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/cancellationsignal/oncancellistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/cancellationsignal.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsetsanimationcontroller.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsetsanimationcontrollistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowinsetscontroller.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surface/outofresourcesexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/surfacetexture/onframeavailablelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/surfacetexture/outofresourcesexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/surfacetexture.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surface.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/scrollcapturesession.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/scrollcapturecallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/longsparsearray.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/accessibility/accessibilityeventsource.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/contentinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/onreceivecontentlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowid/focusobserver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowid.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/translation/viewtranslationcallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/translation/translationresponsevalue/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/translation/translationresponsevalue.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/translation/viewtranslationresponse/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/translation/viewtranslationresponse.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/inputtype.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/surroundingtext.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/editorinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/completioninfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/textsnapshot.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/correctioninfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/extractedtextrequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/handwritinggesture.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/previewablehandwritinggesture.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/extractedtext.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/textattribute/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/textattribute.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/inputcontentinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/inputmethod/inputconnection.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/locusid.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/contentcapture/contentcapturecontext/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/contentcapture/contentcapturecontext.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/contentcapture/contentcapturesession.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/displayhash/displayhash.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/displayhash/displayhashresultcallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/view.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/style/updateappearance.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/textpaint.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/style/characterstyle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/style/clickablespan.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textlinks/textlinkspan.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/spannable/factory.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/spanned.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/text/spannable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/textclassifier/textlinks.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/clipdata/item.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/drawable/icon/ondrawableloadedlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/graphics/drawable/icon.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contentresolver/mimetypeinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/syncadaptertype.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/syncstatusobserver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/chararraybuffer.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/contentobserver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/datasetobserver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/cursor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contentproviderresult.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/accounts/account.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/syncinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contentprovider/pipedatawriter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/applicationinfo/displaynamecomparator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/util/uuid.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/applicationinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/componentinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/patternmatcher.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/pathpermission.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/providerinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/attributionsource.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/componentcallbacks.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/componentcallbacks2.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/short.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/java/lang/boolean.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contentvalues.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contentprovider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contentproviderclient.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/syncrequest/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/syncrequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contentresolver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/clipdata.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/activityinfo/windowlayout.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/activityinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/configurationinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/featureinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/featuregroupinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/instrumentationinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/serviceinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/attribution.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/signature.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/signinginfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intentsender/onfinished.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intentsender/sendintentexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/userhandle.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intentsender.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/installsourceinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/permissiongroupinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intentfilter/authorityentry.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intentfilter/malformedmimetypeexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/intentfilter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/moduleinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/resolveinfo/displaynamecomparator.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/resolveinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/installconstraints/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/installconstraints.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/installconstraintsresult.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/preapprovaldetails/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/preapprovaldetails.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/session.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/sessioncallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/sessioninfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller/sessionparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packageinstaller.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/changedpackages.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/pm/packagemanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitecursordriver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqliteclosable.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqliteprogram.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitequery.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitedatabase/cursorfactory.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/databaseerrorhandler.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitedatabase/openparams/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitedatabase/openparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitetransactionlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitestatement.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/database/sqlite/sqlitedatabase.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/serviceconnection.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/broadcastreceiver/pendingresult.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/broadcastreceiver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/sharedpreferences/editor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/sharedpreferences/onsharedpreferencechangelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/sharedpreferences.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/context.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/componentname.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/menuitem/onactionexpandlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/menuitem/onmenuitemclicklistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/actionprovider/visibilitylistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/actionprovider.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/menuitem.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/submenu.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/menu.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/actionmode/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/actionmode/callback2.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/menuinflater.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/actionmode.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/transition/scene.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowmanager/badtokenexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowmanager/invaliddisplayexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowmanager/layoutparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowmetrics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/windowmanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/layoutinflater/factory.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/layoutinflater/factory2.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/pendingintent/canceledexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/pendingintent/onfinished.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/pendingintent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/transition/transition/epicentercallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/transition/transition/transitionlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/transition/pathmotion.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/transition/transition.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/transition/transitionmanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/searchevent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/window/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contextparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/contextwrapper.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/contextthemewrapper.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/application/activitylifecyclecallbacks.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/assist/assistcontent.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/sharedelementcallback/onsharedelementsreadylistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/sharedelementcallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/application/onprovideassistdatalistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/application.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/widget/framelayout/layoutparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/widget/framelayout.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/window/splashscreenview.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/window/splashscreen/onexitanimationlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/window/splashscreen.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/remoteaction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/util/rational.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/pictureinpictureparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/framemetrics.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/window/onframemetricsavailablelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/window/onrestrictedcaptionareachangedlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfaceholder/badsurfacetypeexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfaceholder/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfaceholder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/surfaceholder/callback2.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/session/mediacontroller/playbackinfo.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/mediadescription/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/mediadescription.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/rating.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/mediametadata.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/session/playbackstate/customaction/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/session/playbackstate/customaction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/session/playbackstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/session/mediacontroller/callback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/session/mediasession/token.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/resultreceiver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/media/session/mediacontroller.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/layoutinflater/filter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/layoutinflater.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/window.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragmentmanager/backstackentry.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragment/instantiationexception.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragment/savedstate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/loader/onloadcanceledlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/loader/onloadcompletelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/content/loader.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/loadermanager/loadercallbacks.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/loadermanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragment.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragmentmanager/fragmentlifecyclecallbacks.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragmentmanager/onbackstackchangedlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragmenttransaction.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/fragmentmanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/view/draganddroppermissions.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/pictureinpictureuistate.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/outcomereceiver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/actionbar/layoutparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/widget/toolbar/layoutparams.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/widget/toolbar/onmenuitemclicklistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/widget/toolbar.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/actionbar/onmenuvisibilitylistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/actionbar/onnavigationlistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/actionbar/tab.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/actionbar/tablistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/widget/adapter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/widget/spinneradapter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/actionbar.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/taskstackbuilder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/request.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/prompt.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/abortvoicerequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/commandrequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/completevoicerequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/confirmationrequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/pickoptionrequest/option.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor/pickoptionrequest.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/voiceinteractor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/app/activity.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/app-android/utsactivitycallback.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/app-android/utsandroid.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/app-android/utsandroidhookproxy.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/app-js/utsjs.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uts-types/app-android/index.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/webviewstyles.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/viewtotempfilepathoptions.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/drawablecontext.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/snapshotoptions.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/cssstyledeclaration.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/domrect.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unicallbackwrapper.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/path2d.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/canvasrenderingcontext2d.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unianimationplaybackevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unianimation.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unisafeareainsets.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unipage.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/iunielement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unievent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unipageevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewservicemessageevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unicustomevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewmessageevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewloadingevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewloadevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewerrorevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/nodedata.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/pagenode.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unielement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewdownloadevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniwebviewcontentheightchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/univideoelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unitouchevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unitextarealinechangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unitextareafocusevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unitextareablurevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unitextelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unitabselement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unitabtapevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniswipertransitionevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniswiperchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniswiperanimationfinishevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unistopnestedscrollevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unistartnestedscrollevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniscrolltoupperevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniscrolltolowerevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniscrollevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unirichtextitemclickevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniresizeobserver.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniresizeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unirefresherevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniprovider.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unipointerevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unipagescrollevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unidocument.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/asyncapiresult.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/iunierror.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unierror.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/nativeloadfontfaceoptions.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unipagebody.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uninativepage.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unipagemanager.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uninestedprescrollevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uninativeapp.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniinputkeyboardheightchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniinputfocusevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniinputevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniinputconfirmevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniinputchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniinputblurevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniimageloadevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniimageerrorevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniformcontrol.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniformcontrolelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unicustomelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/unicanvaselement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/sourceerror.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/uniaggregateerror.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/utsandroidhookproxy.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/iuninativeviewelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/iuniform.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/inavigationbar.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/index.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/native/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/checkboxgroupchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/pickerviewchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/progressactiveendevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/radiogroupchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/sliderchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/switchchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/pickerchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/pickercolumnchangeevent.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/uninavigatorelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/uniclouddbelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/uniformelement.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/lifecycle.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/index.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vue/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/base/index.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/env/index.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-actionsheet/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-actionsheet/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-addphonecontact/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-addphonecontact/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-arraybuffertobase64/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-arraybuffertobase64/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-authentication/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-authentication/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-barcode-scanning/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-barcode-scanning/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-base64toarraybuffer/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-base64toarraybuffer/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-chooselocation/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-chooselocation/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-choosemedia/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-choosemedia/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-clipboard/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-clipboard/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createinneraudiocontext/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createinneraudiocontext/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createintersectionobserver/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createintersectionobserver/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createrequestpermissionlistener/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createrequestpermissionlistener/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createselectorquery/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createselectorquery/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createwebviewcontext/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-createwebviewcontext/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-dialogpage/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-dialogpage/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-event/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-event/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-exit/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-exit/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-file/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-file/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-filesystemmanager/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-filesystemmanager/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getaccessibilityinfo/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getaccessibilityinfo/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getappauthorizesetting/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getappauthorizesetting/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getappbaseinfo/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getappbaseinfo/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getbackgroundaudiomanager/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getbackgroundaudiomanager/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getdeviceinfo/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getdeviceinfo/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getelementbyid/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getelementbyid/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getenteroptionssync/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getenteroptionssync/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getlaunchoptionssync/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getlaunchoptionssync/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getlocation-tencent-uni1/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getlocation-tencent-uni1/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getnetworktype/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getnetworktype/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getperformance/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getperformance/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getprovider/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getprovider/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getsysteminfo/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getsysteminfo/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getsystemsetting/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-getsystemsetting/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-installapk/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-installapk/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-interceptor/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-interceptor/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-keyboard/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-keyboard/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-loadfontface/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-loadfontface/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-location-system/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-location-system/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-location-tencent/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-location-tencent/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-location/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-location/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-makephonecall/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-makephonecall/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-media/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-media/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-modal/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-modal/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-navigationbar/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-navigationbar/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-network/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-network/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-oauth-huawei/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-oauth-huawei/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-oauth/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-oauth/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-openappauthorizesetting/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-openappauthorizesetting/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-opendocument/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-opendocument/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-pagescrollto/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-pagescrollto/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment-alipay/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment-alipay/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment-huawei/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment-huawei/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment-wxpay/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment-wxpay/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-payment/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-previewimage/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-previewimage/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-privacy/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-privacy/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-prompt/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-prompt/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-pulldownrefresh/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-pulldownrefresh/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-recorder/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-recorder/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-requestmerchanttransfer/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-requestmerchanttransfer/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-route/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-route/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-rpx2px/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-rpx2px/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-scancode/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-scancode/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-share-weixin/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-share-weixin/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-share/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-share/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-sharewithsystem/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-sharewithsystem/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-sse/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-sse/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-storage/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-storage/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-tabbar/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-tabbar/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-theme/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-theme/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-virtualpayment/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-virtualpayment/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-websocket/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/lib/uni-websocket/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-api/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-ad/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-ad/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-crash/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-crash/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-facialverify/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-facialverify/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-map-tencent/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-map-tencent/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-push/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-push/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-secure-network/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-secure-network/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-verify/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/lib/uni-verify/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-biz/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-component/lib/uni-camera/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-component/lib/uni-camera/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-component/lib/uni-canvas/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-component/lib/uni-canvas/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-component/lib/uni-video/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-component/lib/uni-video/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-component/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-openlocation/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-openlocation/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-compass/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-compass/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-canvas/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-canvas/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-locale/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-locale/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-accelerometer/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-accelerometer/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-getbackgroundaudiomanager/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-getbackgroundaudiomanager/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-localechange/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-localechange/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-memory/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-memory/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-preloadpage/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-preloadpage/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-createmediaqueryobserver/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-createmediaqueryobserver/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-__f__/utssdk/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/lib/uni-__f__/utssdk/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uts-plugin-extend/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uni-map-tencent-map.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uni-map-tencent-global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uni-camera.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/uni-camera-global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni/global.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni-cloud/unicloud-db/index.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni-cloud/interface.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/uni-cloud/index.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/common.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/app.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/page.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/process.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/vite.d.ts","f:/hbuilderx/plugins/hbuilderx-language-services/builtin-dts/uniappx/node_modules/@dcloudio/uni-app-x/types/index.d.ts","f:/hbuilderx/plugins/uniapp-uts-v1/node_modules/@dcloudio/uni-uts-v1/lib/uts/types/uni-x/app-android.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/batterymanager.d.ts","../../../../dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts.ts","../../../../dist/dev/.tsc/uni-ext-api.d.ts","f:/hbuilderx/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/socket.ts","f:/hbuilderx/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/index.ts","../../../../dist/dev/.tsc/app-android/app.uvue.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothsocket.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/os/parceluuid.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothprofile/servicelistener.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothprofile.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothgatt.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothgattservice.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothgattcharacteristic.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothgattdescriptor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothgattcallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothclass/device/major.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothclass/device.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothclass/service.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothclass.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothdevice.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothadapter/lescancallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothserversocket.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisesettings/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisesettings.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisecallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/periodicadvertisingparameters/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/periodicadvertisingparameters.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/transportdiscoverydata.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisedata/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisedata.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisingset.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisingsetcallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisingsetparameters/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/advertisingsetparameters.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/bluetoothleadvertiser.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/scansettings/builder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/scansettings.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/scanrecord.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/scanresult.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/scancallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/le/bluetoothlescanner.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothadapter.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothgattserver.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothgattservercallback.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/android/bluetooth/bluetoothmanager.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api16impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api19impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api21impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api23impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api24impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api26impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api28impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api30impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/api33impl.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/legacyservicemapholder.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/mainhandlerexecutor.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat/registerreceiverflags.d.ts","f:/hbuilderx/plugins/uts-development-android/uts-types/app-android/androidx/core/content/contextcompat.d.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts.ts","../../../../dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts.ts","../../../../dist/dev/.tsc/app-android/ak/permissionmanager.uts.ts","../../../../dist/dev/.tsc/app-android/pages/akbletest.uvue.ts","../../../../dist/dev/.tsc/app-android/main.uts.ts"],"fileInfos":[{"version":"1b4884e0922d24ad93952038abddda154213ad1637a9cbbca22442cc86a174ed","affectsGlobalScope":true},{"version":"87e0a7f9366dc80be7b72c6d0a6e23c4f68cd2b96c90edd3da8082bfdd237af9","affectsGlobalScope":true},{"version":"2c44751aff2b2161d0450df9812bb5114ba050a522e1d5fa67f66649d678fcb4","affectsGlobalScope":true},{"version":"68566331a40bef8710069a7f5ac951543c5653c1c3fa8cc3a54c95753abbcf7a","affectsGlobalScope":true},{"version":"173b34be3df2099c2da11fb3ceecf87e883bd64f5219c0ee7bc6add9bc812cde","affectsGlobalScope":true},{"version":"9c867cbb4270f3c93a0ffaa8840b3034033a95025cd4f6bf9989ecb7b7c54a4e","affectsGlobalScope":true},{"version":"b0d201829b0da0df7653b76f3e1ea38933081db01bfecdeada115180973ae393","affectsGlobalScope":true},{"version":"7b435c510e94d33c438626dff7d8df57d20d69f6599ba461c46fc87b8c572bce","affectsGlobalScope":true},{"version":"25f08344cf6121c92864c9f22b22ab6574001771eb1d75843006938c11f7d4ab","affectsGlobalScope":true},{"version":"91d246126d32ab82fe146f4db8e0a6800cadb14c781aec7a3ef4f20f53efcf45","affectsGlobalScope":true},{"version":"b15b894ea3a5bcdfd96e2160e10f71ea6db8563804bbaa4cdf3b86a21c7e7da0","affectsGlobalScope":true},{"version":"db491a26fb6bb04dd6c9aecbe3803dd94c1e5d3dd839ffed552ffaf4e419871a","affectsGlobalScope":true},{"version":"463cb70eebbf68046eba623ed570e54c425ea29d46d7476da84134722a6d155b","affectsGlobalScope":true},{"version":"a7cca769cf6ecd24d991ae00ac9715b012cae512f27d569513eb2e47fc8ef952","affectsGlobalScope":true},{"version":"bf3de718b9d34d05ea8b7c0172063257e7a89f1a2e15d66de826814586da7ce4","affectsGlobalScope":true},{"version":"0aca09a3a690438ac20a824d8236bfdb84e4035724e77073c7f144b18339ec65","affectsGlobalScope":true},{"version":"1acbd1d3afb34b522e43e567acf76381af1b858055f47c0ceedd858542426f0f","affectsGlobalScope":true},{"version":"e62d4c55b645f4d9b8627bdb6e04ab641d25abc48b27a68983963296fcee1300","affectsGlobalScope":true},{"version":"a5a65d5d74cac1e1e27de4adc0ab37048332d91be0fd914209ca04ccd63b4141","affectsGlobalScope":true},{"version":"5eb86cedb0d685b8c1d1b51d2892402ecd6e0cff047ba3e683bc7cbc585ebd9b","affectsGlobalScope":true},{"version":"cb4d3f49248d601600b9e5e6268c3a1925a0e3d3a6b13ff7e178924fc7763aa4","affectsGlobalScope":true},{"version":"7ce21134b8a21e2672f56ceda596d33dc08f27a9900ec068a33dd471667a0dd9","affectsGlobalScope":true},{"version":"105e17a5ad5e5fcf937f1a7412b849c67d98e17aa6ac257baf988a56be4d23de","affectsGlobalScope":true},{"version":"471ea135c34237d3fcc6918a297c21e321cd99e20ac29673506590c0e91d10d0","affectsGlobalScope":true},{"version":"6c71e7f5dcdf436e701fee0c76995e197f1b8b44ed64119881c04ad30c432513","affectsGlobalScope":true},{"version":"bfea9c54c2142652e7f2f09b7b395c57f3e7650fb2981d9f183de9eeae8a1487","affectsGlobalScope":true},{"version":"5b4344f074c83584664e93d170e99db772577f7ced22b73deaf3cfb798a76958","affectsGlobalScope":true},"db8eb85d3f5c85cc8b2b051fde29f227ec8fbe50fd53c0dc5fc7a35b0209de4a",{"version":"8b46e06cc0690b9a6bf177133da7a917969cacbd6a58c8b9b1a261abd33cb04d","affectsGlobalScope":true},{"version":"c2e5d9c9ebf7c1dc6e3f4de35ae66c635240fe1f90cccc58c88200a5aa4a227c","affectsGlobalScope":true},{"version":"c5277ad101105fbcb9e32c74cea42b2a3fbebc5b63d26ca5b0c900be136a7584","affectsGlobalScope":true},{"version":"46a47bc3acc0af133029fb44c0c25f102828995c1c633d141ac84240b68cdfad","affectsGlobalScope":true},{"version":"bf7e3cadb46cd342e77f1409a000ea51a26a336be4093ee1791288e990f3dadf","affectsGlobalScope":true},{"version":"3fb65674722f36d0cc143a1eb3f44b3ab9ecd8d5e09febcfbc0393bec72c16b5","affectsGlobalScope":true},{"version":"daf924aae59d404ac5e4b21d9a8b817b2118452e7eb2ec0c2c8494fb25cb4ab3","affectsGlobalScope":true},{"version":"120ddb03b09c36f2e2624563a384123d08f6243018e131e8c97a1bb1f0e73df5","affectsGlobalScope":true},{"version":"0daef79ef17e2d10a96f021096f6c02d51a0648514f39def46c9a8a3018196be","affectsGlobalScope":true},{"version":"571605fec3d26fc2b8fbffb6aa32d2ef810b06aa51c1b0c3c65bbc47bd5b4a5e","affectsGlobalScope":true},{"version":"51536e45c08d8b901d596d8d48db9ab14f2a2fd465ed5e2a18dda1d1bae6fe5a","affectsGlobalScope":true},"897a4b80718f9228e992483fefa164d61e78548e57fbf23c76557f9e9805285e","ab2680cfdaea321773953b64ec757510297477ad349307e93b883f0813e2a744",{"version":"8a931e7299563cecc9c06d5b0b656dca721af7339b37c7b4168e41b63b7cfd04","affectsGlobalScope":true},"7da94064e1304209e28b08779b3e1a9d2e939cf9b736c9c450bc2596521c417f","7cce3fa83b9b8cad28998e2ffa7bb802841bb843f83164ba12342b51bf3ae453","dc44a5ac4c9a05feede6d8acf7e6e768ca266b1ce56030af1a3ab4138234bf45",{"version":"451f4c4dd94dd827770739cc52e3c65ac6c3154ad35ae34ad066de2a664b727a","affectsGlobalScope":true},{"version":"2f2af0034204cd7e4e6fc0c8d7a732152c055e030f1590abea84af9127e0ed46","affectsGlobalScope":true},{"version":"0c26e42734c9bf81c50813761fc91dc16a0682e4faa8944c218f4aaf73d74acf","affectsGlobalScope":true},{"version":"af11b7631baab8e9159d290632eb6d5aa2f44e08c34b5ea5dc3ac45493fffed5","affectsGlobalScope":true},{"version":"9ae2c80b25e85af48286ea185227d52786555ac3b556b304afd2226866a43e2a","affectsGlobalScope":true},{"version":"b2bd4feee4a879f0ec7dfaf3ea564644f708dcfef8ef850a069877bd0dc29bdc","affectsGlobalScope":true},"da82348fbea425ebf7201043e16ab3223a8275507fbddd56d41c2d940b3088e3","6ef32eb62bebf8fcb1c46fb337bf7b71bcb2156c939b1fc8ecc95031fda524ec","90120973d7759d9eb9a3f21f32188e1e11b29f281831b250504b3115c32bb8db","66565de38b3ede65cbb93df52cbd1373ba0af3e0a0cdcf5aa8e8e359a65e6054","26eaf2db7f66e70d2fc327f9ac8693c2806c7b433cb5da5d4b0cd3070b8a8529","4955e566886d9477bff3b32fc373e8cc15f824909069f472d20acd6b0dd75fd3","c342ae063a7c7d37aecb3d8bcc5b4ebf087a67be6c6189985ec96675fdf430e9","550178d99241eb541fc8a25d80d9cb667d96ebe685f1c1c98907f4caab49cfee","471000b5f93ae5077a5a7c45f69fd5a05a53874e156631d18f68c325e17f493d","0ce6f81b6ec2822d2500d5425a17436a3e18e422747a7fed1d6ae85d43912dd3",{"version":"009285985c380cc60693b2e5f13222a3193c0bbe06a5868a66cda52a5bc879f6","affectsGlobalScope":true},"a98d682390a4414a1952de79cd1ff4d454fd1728c0eec0b3882f3c646eb707a7",{"version":"c197d7bb1a50b2b1001a19aea7560b192ea04ca45295538898cea732ad1430ec","affectsGlobalScope":true},"4b1cb3ca7bab4a67110e6b7f6d82186c8cd817de53503610e5ea183f51400d88","471395005d84cdd5cd68955940b5c18da09198326e64bd87b6fd6bf78b1b75ef","37b5295487a3f7e704ab81e5676f17c74f1737d21da3315453bbb3c44b6c7b4f","acc08a2d267c697e34a96d27d8c69e7bf66c9d70fc9e9a3c0710ee6c8b59bf06","c54f1e4b0edff3ef7b5d421ed9d9b12215c23c5707830a15c914a57af3d4d8c4",{"version":"c9b287642c4b156a56b81cd1b2fb17208ac93e1906f64603f9b4f89652c3ac39","affectsGlobalScope":true},"0c34c0d35f33f398a590ca4a6bcc162e32873a942d8c040b394d86321e2db521","0912310adac9d4b59eb8370994b0260035b3e52a64ec8cd27a32c9c5d56f9a37","b20f9fd12d0f20b756c4407195037d0e6df994b18ab7ba117a1645f79dc8146a","097ff4639376fd52ce9f658560ad85ea4dfbcb80e1f0c38baeaf2f9f24edadce","3a077826173de93d4275960a32e5ecbeca73cec6817feeeebbfe32dcdc19f69d","a9499471d2c97e01b4c47cd990a7e59f90371dc6ff5044073063102ef10aa2d7","25952a12ebbf9ee23e92f3d0273c7c8f1b962379d9b9a8f8656c00ab5bbb6b28",{"version":"ae0e01c62ba1a1c649851b7fd53c73ecb34928f08bb61c67b76696242b65e510","affectsGlobalScope":true},"9bdcdd8c1c888de8e99bba6c66ebebe4f9c3b85f3c159dfed4c0a60aabcfb359","a864eeac83c751a0de401747346416c5abb6c2b64e8292f9238786650beee874","bfa98bf77f78e5ff08fdfed7ed3e8d94493794c1d0ae88a083a6c301418f507e","48b2ca9ba65a7dccebd12e4430bec879e68789b1a9f6328772175d4246689513","84cdab2632d7b88822afa1056cba80c8bc6d5706efa0336646dd535c9b859c97","55e92954e07a35ea79589985ed517976140ee5948288f5c0cef89202f748686d","86e75445bc6bf503e718a28b5deefcf5eaedc7d7442569b33e555c54e3120bed",{"version":"6eebe91a65a022376c9d83adc71affbe3a8738a23f88079a61c5cbaa90ffccda","affectsGlobalScope":true},{"version":"d0699ff9dd5c078015624b1bf923aba8ec2c8d5c7dcf866c7af65f328348aea2","affectsGlobalScope":true},"9377424a30a137dd21c7b300c20eb35bc4b18a7e0c68a19dcfb55462572f4ae4","1a45a2fbb039686a96c304fbe704157de2f3b938cc50e9c8c4bcca0ceb0de840","a864eeac83c751a0de401747346416c5abb6c2b64e8292f9238786650beee874","72629fa2f66fc7113a777cb09117e22b611e83e9099b2b814fadfff32305d932","48b2ca9ba65a7dccebd12e4430bec879e68789b1a9f6328772175d4246689513","912a048453180016af2f597f9fd209b2ef96d473c1610f6be3d25f5a2e9588d3","80fb74ae1b5713532effc5bbf01789379563f65591a55eb1ae93a006009945fc","5ca437d9f0411958f2190f19554d3461926615e1e7a5e9fe8a8bff2834b423cb","135ca31f7cd081ce0321f1536461626134be5ae8e34ef5365ed0a60ec4965cf2","e35fb080eb67373cf41a5cd2f80820c6610d9bbbd420516945a2ae9d13cddb99","e30ef09059535d6a4a6c2e972710f17abe1d9ed9ed3353c22f007bc733d24499","7cf25154e3ff5e0c296d1c2e8edd595cbf88674c5c1edee5bd1d395103caa2be","84cdab2632d7b88822afa1056cba80c8bc6d5706efa0336646dd535c9b859c97","01a225ee75e5bb89a103639d825be5f7e7b993625c3503e9ed23ca59faceef0e","b2821ba038982e2234b8b1862a3abd93dab22e5a9ccb96388f4e49c8a60493e0","df4d4e7211100ac276830cd3c93e75eceb6da94c8ed22df9f9c296abf283a9c7","1ff1b7a4d416e891c46924d0b540573fd09c6ce17030968778268ab33c0d7562","a8cbca97e5d078c9a16c8242de1860baafd720dcc541a1201751444b69acac18","52d444c5ab7d9dc6b01f6aee7c97a7e14370fdc2ac482ef6903a044caf58e898","5630a60d7a15f9f4887879fc0ebfa80436a631f7e98b6613149333b0c1928649","c5b7d50d5fd3e45905ae1c2e6f39296e138b7c8b42af696b58091a20fea98de4","35841b91f9336761af471a2b26d414e94c779592a33a4589daa6b3036fb2841e","7691a1558a2e973614d2baf0720451901e656f1f4dad4fc635ffcfab75ace090","f46b92a70beb1f076e300ab20e0e9a9e3f011f2b690211b754c662537e2eb3ae","536b2c25d25ce5003998f0c4e1c6aa088f07deee5a8fc7e3b95e9716097b3a82","f341bd294158b62cec7f2414f9cb899c7cbcc4dc98db97b7f95996b10a2368e1","b122cfde1e19d45ece3c084caabae30eb4be2fa0fe1d8e85a6b6eb498f6bb849",{"version":"a2528540afb60b403e90fa9b6eefc321bf8e33ae0c9fdc61ea0bb4b4b8e95cbf","affectsGlobalScope":true},"8d0d38b9142711f83451581d2a4dd1b9c894d4115d2a3dc66cf37043399b0186","bca4234e52ebd600eb3993b9e909c162492ed1d499bd4b603b8ec09c581b87d0","a9cf7836c8d1a2d00db539bd47553c03691857bd7e7094adf07424553ec7d8d7","f2c35324d08eed12460111bb500959c0b137b2b476de608945b84ddd9434428d","42009ca9c0f6e5b96a977df586ab38ae0efe15d6f21ff715ddc39b46cbea3de5","55aa60487b827d6a3849637c56a803519a6ad533a9bccdc2da2cfc235ba785af","175b9e8d927cb191714027bedb36ecadd66cb661ed7a0eeab10a99d3174feb11","00a81ef0fdbd28a5bd0b59acadf560aaebe88bbc807301ee49f3004966ac41d4","40d3ccdce3ef46b73fb825797d1455e185d389ca0bcd581fe466a01008b454f0","c0dfe8aa401326a3225f821f57caf6175a6a1ca43cb881c957b5376c74cd6f68","d3281f4c15b919ff92d5b54bf06840835c13b26a6408b9312bf4de4db2cd31c8",{"version":"cb05cec6b5af32fe72618bf75f582ec334a05f1830a16c99267d7eb9a68f47ba","affectsGlobalScope":true},{"version":"c53006904ef39d538ad1bb5dca6796a2af28c13e7aee27e0a0829eff9e8981a3","affectsGlobalScope":true},{"version":"dfcfc75aede1c22fca588e7e08f653f244b315ac140208994bb0195bc542bd4f","affectsGlobalScope":true},{"version":"d23808465b4f1757a4e156999c841e50cf2d2cece887fec6620380b7e6f1f3b6","affectsGlobalScope":true},{"version":"90718d3552de669111355e1af51a55915f0ee3cab37ae0b42fb29658e67dc704","affectsGlobalScope":true},{"version":"a889109696b87c4b65231330e0c9c762297468148ed3cee9bd12927630ce1c5d","affectsGlobalScope":true},{"version":"e8584f9c219e7184e57677f85907d286989cf6c0d268764dfd203d82c07067df","affectsGlobalScope":true},"0c976c92379daff60e2dd5a6f0177d4a1cb03eea2fb46cc845301b2fe008cd65","5949dc54449ff89a7d153367aa4e647bb7aaeb1e1859d73fd1832aeef1bf4d03","71e4472487f1226ae8b9f2cd8d833a8a43028d9774c7f631bc36202c5addefcd","d713807b783bed6d32aaa1ebb404e5115c5355fed08b48c9185cc4b15c529d8f",{"version":"d2284f4211cdbc263e4ddc5da6775cb9e3b9c974414daa5c6553b64ed7ac9584","affectsGlobalScope":true},"30f2258b429c538edc5e7f77521eabf1e1801f85493b6917debf034329b7610d",{"version":"70ef0e093e72da577af1c5166c85c170e74037dd6490b0e54538071eaebce218","affectsGlobalScope":true},{"version":"ecdf82037e2f7f79bc6e0ca99db3df8b49859e2963ff0ef57acebc383f5babd9","affectsGlobalScope":true},"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855","e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855","e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",{"version":"1c679a785ee2011015dba247d59774164d69eff9da62f6231f8d0386a66f75ed","affectsGlobalScope":true},{"version":"24558e1ae6d171b174b099588022e6f8ae5422b2ab6a0aaf7bda4dc1fbf0cf56","affectsGlobalScope":true},"e83987b96aa90096cbc834f30586d735afb007f7f3add5837582083262f729c0","9f6c89c7fe74d403f49242a9fae4e95e4aa0bfda9688ee175c7bf395e365d1be","a347103f1193e083d7eae55d73163f22ec4cfc6f0e19aaf084484542cf4c487d",{"version":"0cf62f8acc6b9613240f98604dcb990e95ec11f5a751aeea68347258fcf58ae7","affectsGlobalScope":true},"76d81c4ab4cb5b483b01947cec4560333ee23c0cea3f475dee16960b6a29c626",{"version":"47c995ab27f4637b68e370286e65950f5c6a766bd614297d4bcef7775271ad6c","affectsGlobalScope":true},{"version":"be20b80c26e821788b73fe9b45538d2cf52166f36c9c00c2434a888279c9a205","affectsGlobalScope":true},"a35f40ec1f82bcba279411c3638b66979f19dc6469339c3e7573b8cd9bb2cde9","7d36ca73a9413c0c6ad90d6b8653fde0aa8a9f776ff34eb95e8cb090082b3adb",{"version":"7b40e9058b51bab447e560ccb8b0b6e82fc29c96230d92e1198c5cf526714969","affectsGlobalScope":true},"e4eebdbfee01ca34d7c9acdd67576def4f44efc02717cacc0a94742125db8f36","93098cef2ba7cf98085f7589abcff9dd31bb6eb376c2ab1c2ae325c501ac37c6",{"version":"0ee6d4f3ea203ad71e6e1f204ea2aefb8a5106c00b655618df1408016457cc29","affectsGlobalScope":true},"3885e78287c92997e90357a8d9da13de0ef02f56c3ecc890825915bfca0e2dc1","16e777cff1467ff5e067423320938328934602207ee28b815fa0f7c3ca3ddf4d","61f418b2995586a9e2e9b6d0610fede51a14c396d94c551d7972dea0970d3d3b","04c348aa829a5136154a8225d2fc41e942f22fe9e9b21f3e5713f716339e892c","e560b8ac75a2ac0a85c928cb4ad68b2bb996a72b1838c16f43e349daf1533be0",{"version":"022419723b65c827db878d09988d37dfee43662a622d8303ae4b2c2ab1195b88","affectsGlobalScope":true},"6adfce0b2d1e55f3724a9b8d80401aa294d36c6c44c6684dcfffe204a28c4c3a",{"version":"f7a1b29f7148b2650a24e1961f79e85086d0f8629411ec2b3755dda39baacdc7","affectsGlobalScope":true},"34ca7f0250eaf790149dbe4022ed10d8f310e9fe2ce5a9377854b9ddefa96647","75b28d992fd27e2475e7ebb79780903f89599babf37047c11a611b726ae3b10a","f58c7dd0dc1cde8855878949f13fda966ad36d547670500dfd1d2975d77e9add","da49d860726ca40170c20dd667d86d5c6220c5b10f68aea54862326c80e816f3","fec001187fdb73a0415bcc5b65d5341aa084d8c6921386b1df13a2db27327eac","8f4cae1a80427212f0d9e38918428932ebb1e2e94f06bccd80bd2ed0ace83e13","8ae116c4b542ce7665c8ada0ee2d8d7f7f84feecead3d2d91936dd9f3d00365e","1001304704bd20ac5c723e8dcda6a3577e8154b85f09d11329a8f62f0338e0f9","66178c7d50696d3bcd84dcf50ef1b607914d8f225db87e6bec3fa499b300b0fa","b198a349485602af3e30b8ce1721af5772cf462a917545b69f49af2fc1399e74",{"version":"f9f7a3c251059daf58f2cb84ee303fd640ffd6f6432bec70fd02b10db49a885b","affectsGlobalScope":true},"ce7a25f45110b733aee55750a2d9526e3e57d87d60ec468085845ee2a3466f38","9d9b8a786a39bd0f64faf720ef50743d9bee9deed9bc493309109c7a69dc847a","9546037b91a1558f46a7bfe90e2a6c58f5dde86b4fc52436fc1ed43b1dff618c","824f8f2073290e557359eafd5dbbd7c8d800589b8c7b27fd0bac77c3e9ec1584","d32f5293ce242eda75ffd87d1d9c88ca7ab9cbbd3adc2e75ed5f5d91d718c812","39315a07038f36a5c39be701a11bb36b5f995ed165ecd1107d1b90d8fa5ee8b9","cabccb604562f055ecd69ddb8f98ce700490313b9719a020c8acb72c838bf3c7","e453a6941b8a60022c3e2722e2decdfc3a30e317593685b25665f10e7399b0a7","268a279b265b88e18233aeee1b446db001f13fa39b87c93af2970d3eca676b75","9cc805dbadb66e241938afe56e3eb8715afc037a8ca0fd7ecd1dbd34e95d55f7","4981a30867a9f5dabd2e36f9d4a4cb0e3da83704c01504c7e2590635ee68d632",{"version":"3ea1c94bb38871a157a1400327fb03d7baa921c877001983ed5d27f95a9628ce","affectsGlobalScope":true},"74cb1a48eae2381ed2ca8cff3ba9eff3edc598a0864b0b60d91d4026698f5f10","0175552d4da3ae3ebacb639e6be5ef1dc92932efb2779a972c0c9f2b8ad61ac1","21784ebe37df62eb842372bd55e9d6feaf5df98ac3498999ce4ea9834e4720d0",{"version":"46f56438c8d80c16ec82701e3e251c131f9c08737a461afce71140e97a0e044d","affectsGlobalScope":true},"d207896ee02f8232c30d952e1d6f5eaf6c2d1884042c72c0ac86340bef96311a","0ec2245cfe10fa400dc1e0c91d6b101452d56c0a4b9eedc781c126dd7ab1b8b1","0ce5f07cd563226f61a710f3238f1762907b79c79dd3bda6e01a660655fc7bdd",{"version":"2b69a342b0d4dd19157a09e487de4b699dbfee34534094b5e29cba70b4a9a5b3","affectsGlobalScope":true},"ae9aa4620f5390abde7e5aabacc29b9e58086bd61ec6146bb09c4c869013aa98",{"version":"fbb211f32062fd3bbfed5402c47fe27d6cf2da6389962befb5e79159048379c1","affectsGlobalScope":true},{"version":"8b3e9ba8a2089619b7b12f30b8bacbfc63d15a9e8156c95948b9a62c98949bef","affectsGlobalScope":true},"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",{"version":"88524de3f2125343de37624fb2f22366906a3f8825446c82c27655b048f5b7e0","affectsGlobalScope":true},"6d66e4cb555573a5c7778c3d6dc15c13ff70a169e792299b84c535ba9fb5f25c","0da20aeb2621b0100b5be15c95ec498759640fee41633e676ed69031776a7958","17fe76234b14785d9e646000aaf44cfe0c55b29136b63e328bfb5886c90c79cc","67664ea51c8faf5fabe34c265b4372fce2efdfa1fed87ac7180b00ad172d7427",{"version":"f7ac217354320f2e8f0b442d84d1fbcfd71dd10e5a339a3eab101e50f46f18cc","affectsGlobalScope":true},{"version":"1fe7e290f6773931107c3317c5b078a690658fc475409a50053bae664e0b10e6","affectsGlobalScope":true},{"version":"933a55ab40a6e8580cc33ab627acb1015b265b667c8937e125d8eef349d08a58","affectsGlobalScope":true},{"version":"73c1f0ce08aec056d63aa0e8746c32640beed9bc6b058a9e69a9b7f7db85500f","affectsGlobalScope":true},{"version":"693a4abc9d5d02250ddb2256e525b8de4acb8b9ea78c3bcc64495acad39ef1ad","affectsGlobalScope":true},{"version":"cc3c5f94d36382152a3ee02d17ce0535b926e23085b26585374097a8e0cd6da2","affectsGlobalScope":true},{"version":"3d83308305d7a70dab616279b7451b14a64c0899c0f90368e20bdcdfbb1dc9f7","affectsGlobalScope":true},{"version":"09a53cd5cafee0bf013d37ac760d0d986d5f07bb87e87b72088616c1cf039ec7","affectsGlobalScope":true},{"version":"aa9dd79da69b3ae334799c5bdb273f317bd8a83116090238e36948c17a5016bb","affectsGlobalScope":true},{"version":"e102353d0a90d791a48b0ffe4b75f84cdbe0003a17f5c37a132944ff8ec504c9","affectsGlobalScope":true},{"version":"0bf0d6a78c12edb7c8152330d45a0dce0655be12d50e2e7c36b409e54671f7d9","affectsGlobalScope":true},"9f7b2656602d7d7e21f098645ed78f653192ec94264479c3a4c3118ca0e624c4","472d6d7882ce8dc9867e6e7189da6a10abd14acbb117fe3a7b141c8a6b004b12",{"version":"a1d8c09fb9ca29aba20a893d80f90355a65b40dcc1a1d4edf6d81fc7146b913d","affectsGlobalScope":true},"8ada05c75004dafa783fc5009b9d7441d0f1f7674c3aa71e9f184f3d9cb2d4a7","939987b4943d33cfb79350cb1abaa935ca0422ce9eac25df4c6666b5dd7aebe8",{"version":"f7a8fcb170adae683199f52ff6222949c21448c30aba9acb9e9145573337cdb4","affectsGlobalScope":true},{"version":"57456bdad9bcb39b755dc1c55bf39145ef916366d71919045744fec6232e4e34","affectsGlobalScope":true},"7d0eae63c838547cc5f9aa5f8b8d38f98797b8839d01d19ca376ea2dace3b184",{"version":"7d8f65f6eb43d8c03dceea51cf070b6a2b4f6eda10359aabd0a6b0b70d311413","affectsGlobalScope":true},{"version":"4532773e0dcd56d7087fc88a74f709b0e8ad2182d09b22efeb3cc9709a92c8e5","affectsGlobalScope":true},{"version":"f2396d6396a6c32c11a74fcba000de70a42f1ff3c49ee7972672f1242f2202c9","affectsGlobalScope":true},{"version":"57664623ed533dbf07a910033d0d18a2dbcce365dd37070054a8b95881d35312","affectsGlobalScope":true},"65d28696eaf13f7133e05646187622152d780d8e873fb9088c857b7f75224521","70dca951c363978db43c827526657358a0f17e455cc6e462fbc1647a73e18027","1f7b8dd60e8bf371b351e4db9c742b06b5761f7905fb192b74f69be7d24de011","878fc82293a01092b46977d23da7de4cd76a6156f0ee5629a64d6e47a2f7340f","1274284761f2ca91661361184aebee1aab8d182e001b9a1cf90d48a299901f59","3e9426560268baf40851dfcedaaee9aa91cf53c3f1fbb5e441c08d66bec71e01","ba4577447b3130f44f47ced751ed73938899f82b33fe38d2683d6465c6726b8e","afe3f4f1a07ebebdf5fcfb018d11821d3f82d4447b149b57d1d094dd6167478d","008f83c3eca1e9d5ed018121b1416318ca7a5892d0108c489e46872215a7b8f0","915ce332ff510c9bbc50b1034b227919bdb2882a491da1111c4a5d4194ddccc1","bb6a9a471540e43ef1034b4ac9b38314e09e702ffd65f7fa313919206b1e1825","655ee5d83a484733e356a09e6dec7e6883bd30650924c24fa63a104b2f1e7cb7","0dfc7a76c2202fe46de58b14d69be16e6564258d634f801fc7f5a07c0769357f",{"version":"bc85a8bd1d0f01e5c486e95c751de49cfd2708e7b4f91469b4d0b03a873824fb","affectsGlobalScope":true},{"version":"c0217fbbd217a04c25dc1ff891f362f3527ac631e3ab5bb53deafdaeb7f05e8f","affectsGlobalScope":true},"a5f5c27f33351bc649f0db4ec5f4fc6a3b3b93632b9079e42b666a4c2a906b10","889a4b116d0a2874becafbc012f29e1743742a2a16bc2a5e32939345b48746ca","938899d9003b29618d528a2ac9be584863f578869abc51afe7395fe83b048288","d428fadfe52305f61068519e0fed36b614fbee27cdd1248420288bbac0eb9981","5314cd7e2327942ec1073748eec91be325fee87c3daf2f2df67c70c8ed1d32cd","af70ad282ae0daa8a878a0943505edd06bac9afe6788cb9914964419bd124a5b","3907833472ec86ad47624f24c54fe45f32f7f5aaebe39f0625ddae09bf165310",{"version":"afe90f86512f9bf9c87b2d96c5e7624e6c89abc052e7f63b438816cf917c5c7a","affectsGlobalScope":true},"f93d4bf9ae90941e2e8f87d983958c1f4904f503558f766e11e016c1798661a0","4163c1368d4b8dac8014648fc6c47b582e36814fa75b6bad10c8a89b312878f0","57ebd4e6ba6f07e2d7871a8e197066e102f5810bbcc51d4af300142c79927619","b320a66c5796a0a185acdfc5b390707bfc6532f6c588f2c667e9c0c506a8108e","8aa27c6c362357245f6a043709c87e1e97432888363226d2d2060f6a6335a641","55bb782d85a4116b8203d5c67ac4f9f265b5d180482a5d5b18868dc747220348","0730c93b722979a30434470baf2601c44dbbf27f590c88339931445121a0f856","c0f4fa18b383ecd58e2946cb2ec648295e974e511edd52211238a5c73870b8f5","ce190b39ec46e0811f4d5a306221b9d07c3d69c28aeb1c189020e5ee1ba6d6e0","aa15ddf5ab076b368c3102787bea4ee30f138d5d08c5119765bdc87d0e1e628a","d3792b49fb4900be5e49c10345e2e69d3e5286fb06dfaad5e8f24ae9cad79a2b","5c41d402dc225b9ed8cbed8d203cb0754b48a393d04d31338baf0f361921ffe3",{"version":"5df47f508bce633d8cbb580b3091bbfa26ecb67998c2f2c4257e5d834868a2db","affectsGlobalScope":true},{"version":"6cd14162d6cd752135a2d5eafa947cd2dbb2f23915e4ac7f4c5f03d28f25ccb2","affectsGlobalScope":true},"344c09199680044b1c1a2f8d7f9af6d253467742031b316a1400dc7160349cf1","08f96cb316059d4aeb3eaa87d1d632c2de37b66ca882fa86fee98d97edb362a6","bafaec4721e829c036143ce0372e994dd9a04b81fd45b163127822499a5be780","12beec0daa7067d5ff7dcce4a5f847d6eacea981d831a6f5e1e3040355a636ab","75a8fa09afe7401553d916c495280e02a7776f7b4394478d1dfd1d5094b226de","fa63b36d31c377f487e74554b86fc9452ab33eab671d2e1a92b266c2d285b3c1","0ca9460437590f155bfda16c72fc6aa85ed69eaed61abfb15e7d17c6481c8c98","5a3cc85260fee55928ea0473c7e2178dfcecec0300a3e2cfd72b321c515b116d","e419ea59e45e901ac47760222309e1d6cbf905d3b0732b1be746f8307fbc5632","8eba116cfa525aceb90e96b226bd35f0aac1a5ba4af626edf79b1932be2ab2f4",{"version":"ed04e5093c78b1038b94fa3fcdfae6e6e6c4c856668f7b58938422292f720170","affectsGlobalScope":true},"4cf3e54b60466892e4782efce2832e67029c219258dbf859713142b8468cccb0","25d19ddfd1625e14587ea2e2d278d303fd843bb0c0a8cac97db65bfe170d74ac","b7bac09cab3b868af839583fd808b970441662ff016c47eebb8cc029cffb1c03",{"version":"2f3339e4be06b5376e846646e02dde0dc580869f77c76b67e8266df1ff0da9bd","affectsGlobalScope":true},{"version":"41544533d451561feba169258c39f7a0914587b5b7a2782e2a361cb4084e7dde","affectsGlobalScope":true},{"version":"d24721a3bdec26eecb5e550cb6ad0be4f682a5402a2e1f3ca0312fa4e2aa6067","affectsGlobalScope":true},"508d0c2a8062f9e65265dee7ce8d5e5df1aaaaa52a1537664c6b515bdd462cd9","9cafb7769467f24254e78435e386b95c85834944b551036e6da5820ed71f3f90","019846416e2c563952d5d56f00e2d95ec02e24111aa34906a871b546db2dd635","14c65748ee544af29c09b77844bb0ab13bb9fcd586366e60565400b8b4b2e575","293d6b22b591bc372f67ee65646d378484febc984475a166cd511b861ebaeadc","4d38c0a76acc8ba18466747f7b6132525c44bd4f1a8d5a7a00dd48153b9ed373","2b822e4179a445ff9a264ccf3f3ddf18b12d0ca1c43fca46b8e83ae9b27f9ce8","752a522b6f9583718c8bc788a3bff461aaf468da14fce1de8350a52a6ec543ea","43254e37c67c155efa2a4185b2f09c6a53f60d375a4f7252e2fd44ce62b9a877","e8de61d2225590862ba665d7bd6a3918c6e0c76c870b72edb96df2a859c844a6","cad8ede726a86b768cfbfebaffc1dc147ca5d887362e4bf6a76a0a6676947abb","9dd293866b16d3e68bb486870ba844bb48e39ab1e8080e499a2e933f41c5b2e8","168ae5cbaf7f4eb23cbbff164a5fc8e13511a28df68e7b981bd2e5a9a5d0d30b","ff81f2cdd12cdbeb9746ce4351b1005ca3f79e0a5297f8aaf60b57ecf1b259a4","c1df74fd014265eff0ab4a94bc18bc701dc459a66396ec095989349f9547e20b","e25dbe91e193d5a371f2b7ee685980dd7d9c7773d73ddfb40062ead9d4d87e06","c0520b526446893d852fcebd86f1dcaf0da9f42d9d953c0f0e9c2c9085ebb9eb","28a314d11a60b789f88b033aaab6f2b3070fafb474333f4e1d77b4cd391a01cd","4054cfe0584c236dfe9f03cbf8bf2fab1af3332adeb0f4e3bed9cd18381cba03","ff7633a4cba69d99ec40403401e0e47d50d69935ef138d36984d74ac70c64609","061bf022b21dccd86838af7cdf6ecee1623ae0d0872f0cf2a54fef0cf24deb98","fd439ae63c59b70c9383d31254044a05b086441a6f55369f7c19f94e388ddf0a","0f433d1f2f1aecb58a59989c8c7f1844e14af21162ec942745af62ce2a0c4730","ff4d4e79496b0a5312af29f164069069160a5d9e97bd300cc7961fcc56c5f706",{"version":"6056a7951b168a286f1b1a42719f91e1bb4ff48687a1e24cce9952d710950e24","affectsGlobalScope":true},"3dd380f1f150de28baf660ff0a30795bb907cdb77208e2ceed4a96e6d7e31e6a","82bc47a1bb6091fc44e8de288f3726fbc923b9baced69bddceabb122f8a9406d","a7e6b329e75a08af5f998cdff8c7177c87a642e335af537521cb3265eea1dd2c","4f62cbe98592811e02271b745d68f3747dc3f2834c24cbc88bf7074e2e58fda4","2267e79ebbd334043401e7baa494b30de66930946e01d2360e775aaf73fb15a2","7301ff04803331d2a62763b8a95d0f4454bd959309ba1acdec0f25e7f814bf59","743890e38a2060e5f97ba232848586096e093d22786c72e643a0b1bbfa186c7e","3951e58dec597f0a7864dbe8f9be12248231b524bc2d56b0f2e11dcf1a8fe7e9","84ae9e5587719c8fdab716e7163718971f7be3ff94eddf87fdf4395cf98e81bb","1685c3aa5a925af7eeb86097bd0fdd9da4f2087022a6a43d40e06bb70caf2d2c","a3c7760e6789b5ae6fb25be9c1a501917ad55791cf44ebb071b19d7d4c15fb09","d7e6c34dbe5984bc38756278335ea4f8c45f52c475c5a1cfda591b7524608ac1","d99703c657c04f452f4349cf7d17767cb046aa1c322f2f475e2d60f44f78941d","b7c2a02d5e6e1170f919c87c06d42c2532fba8533c25a49c35679c0f43655fa8","1a4a7340add98906b51512bf75b337fe2b7bd7d201555736511237824d5f8d7d","820771f85e390e837f0bf3baa303d8a29865a8a920a9217739805f64fc9c592e","993f6d2d9aa48046d1a75e9227dfd386c8f04f717612858ef81c7b2df4d60b09","30de8bb015209ecf6dcb39fe9b247776451c2155295e38321121154390448b01","4dfff491b066d98543a57bcc1e936a962c1a345bd874fb314e768c785036ed2a","05ef0df715bda5f39800cd8fa097f6546d1fd093efab998e9c549c4e83fbf39c","0f5631b6c9aece81d36177183be75e4bbcfdbc2df79db43540fbaea584b6e052","fd5664e951516f7650f445c51ff813622114298dfe2000f506330123b597704b","2fa0c17b437fafc0115a7c4925c5a9a683395e6fe0e41a1d281e190345e64f81","8bb50a0991ef3b274f233fe489515919c98f9f902c12c4a82d93ecc6a8f6cbe6","b06896e4d71694f1fa32a0931133334f0905bd84df6d6f7c97ee7b5eef3e4dc4","bc45da1f9643877f9ec9ee40c24bec9ff04396d2733ea35009ee34c946e2ccf0","85abfe12e182b4e10fae58249c079527d496090d2809f1429c2c8969c7714675","a19a8f35e2e9c0b5d8c7a854760bbd761531853d528b826e6c47a76ace499a92","01ce918f83d21b1fd2a6f912020fcca4961aed06b310044bd4de32f9ef3dba1d","685ffcbfddcdb506972e6123cf3df582408fde89dc62b0cc1b81059f088c93bb","86eee1c56d83b2c730bdbac50fac5735457001f843ac22faf452ed11d1c5179c","9fab9dc02a23fb29aca89d45ff859aa97576d7bb0dc7fd9eefcaedebca469f1e","4460512dadae371455bbc45f62996224fc7a8d9e87da6cec8fcc92f1c6926fac","e631dcb0c43d6668ff9d30a022b48def006761d0dd7e4ced60f53616ac2feef9","ec222cd4c61a0ee9583bcd487b5ad9bd56f3ed2cf21eb2b00829531e2205eaec","8b4c95d080a9bbae5e9625638eff827529597d3bb4c456c2bd118bc467227a7e","72629fa2f66fc7113a777cb09117e22b611e83e9099b2b814fadfff32305d932","eae9569e05a3e8653bf802216097bcc7c61e8ab25638d95a258e4588c01b3f24","fe81e729beec4e44555d9e8c48c00e162ea669638a65510e12a83cb997acbcf1","35cdc38597d33ee2188cfb281a80a5f1b72d1abbc35a6c443243a697f0144119","48b2ca9ba65a7dccebd12e4430bec879e68789b1a9f6328772175d4246689513","aab15d1a7b8fa2350476b46f3a85619c665d32fcb295eb0e70138fdcfbaddd4b","dfcc41a421738ad0b1b00d7638967195197eaefe15c71619b2dd27478c2b4ef5","912a048453180016af2f597f9fd209b2ef96d473c1610f6be3d25f5a2e9588d3","52195d96d12b0013e87994d65c220e2089204160c9d7784a20465b0cdc04c40c","5ca437d9f0411958f2190f19554d3461926615e1e7a5e9fe8a8bff2834b423cb","08592ff23d68090ff3b4c97027cbd77e043631a3ac2eeb265bdaf965fe6e6f18","363a47f946268d493af60c1048985a5876d913ed5b7f02355e3c9dff1c332390","f341f2976f4dc47ff5ae7b682e10d7c58c156808f087cc198e381b4ea6fe7cd0","135ca31f7cd081ce0321f1536461626134be5ae8e34ef5365ed0a60ec4965cf2","0e9c7378b81ffbc45219398fb18427866da10dd7883e431ea9230b11a9a46521","20457eeecbf2ff62b89087aa9a2d1b546448f4be455d9bcbf2f225df7abab3f6","85ee01deaa3b60978c6f1402aa1da57f03136867e2a78cb0870b65efabf1ec4e","2ca77dfc7eab8233418f9c979fb0b948e83b53ae339a97062c4433cf0f61eff4","4d09c54a3030a86d865d7ace361e9d1d64966ef2a26ab229a93bd09bea9a2d98","56fdf522a085e174230c31fe43818dc738c58b334d9b2be52381f1a1933c755c","3986d59c8c244b09b16090dfe95e6fa0984f4f7d52122ff1788f08712a396a2d","c4aeaef1a5ffece49128c326909815106d6175dc5d8090a61c7d3a3372de5e7a","a37f39da73d92d1a9c8494744aaa093254007aa29803be126f05ea6baee1b52b","a8cbca97e5d078c9a16c8242de1860baafd720dcc541a1201751444b69acac18","5f1be2f84383c83ac192b11f03b27c4b3cd27ad7a628615bd0f8ea79a159a2b9","65aa982fe7bb50732cfbf038802b2c083ac3595fe1dae42ad61f86055afe96ec","49d03df10ec1aeb459361cfa2dfc00d6747597f633d45b5fa52b5a9ab4e3f029","5e9be59aaf37fdb412cee4f1febf1497da4700086c5338f6d4acf944fa07703c","86f98a0f7e9da79548f9ae9b44b8801151197a79f8dafee4c5c966aea8d83cb4","cd1f260d2b17cc6ae80f3e71b5011b1cb676c780f673455a2182e76f371e11ce","a185189e03f51b5488afeb6ef407f0d166a8b3d5870a262b7d93fa7768843833","94a16be1fad46258203d586e32492dd8ecad21af7da670f652a7a2715b6330da","f6a769b22de85a46d193fc235a1eb1920e8ab9d77e6476cef948aa83a611418f","17c0308cbd36ca46f862f9c9cb7384ec4a2167b87c615d52150704b98aff2ea0","86e75445bc6bf503e718a28b5deefcf5eaedc7d7442569b33e555c54e3120bed","f341bd294158b62cec7f2414f9cb899c7cbcc4dc98db97b7f95996b10a2368e1","7c5ad63a2222f6881711c0101c30b0fe5587a215e039627c48e1fa50470fe4f8","b6b976fd4ccf129b255a541b86f8e92360cd314be6c9c19d7d200efb1350a293","a15a07e052234577d884c8f1397773153d2559f74432d64645af6bbf7f2fd268","16ac88b6e2411ea7352c688a8927f20427d45f0d7eeb91474ed5603c6fb9954d","a36877da4fbdf323a2d7d9579f52ce3c6394adee7a3c9f662df917d70628e73a","cc77d5904c9399be5f10b78d28ab9b5a8f58d130ed64b6fa2fd4a5a8de2bab31","1ad5aef5a9afaff23d7c914895299650acc79facdc4afce5102beb4bb14fe58c","535bbc2e3edaf99f3e403d836d36a9b7bb72043851d5e0bbe0ff9009ef75d221","332bd6850e05e8376dd7aaae887e29e68b5d6fd6f35590352613b4c043e1565c","1a0f3f69194bd562290d5450b61b6b5faf9dc863f51d74cdbaa4f7ccb5884bec","6469f087e68b71fe2984da04055d4c6b7d00e6d022030bac4c39eb180599e3b8","8d96421a664e47a29d7112faa8950756c0644469a054c32a4cfca454f47d0451","8ab99edb6cc00cb65355d887a301efb4a946e91826a91c75656392e0907a6bb8","45b29a06927685ae092dc2c00e2702030abdff9d31b5c3b79ba5cebf4530bc77","b2b3f0067e54d2ab55ea63fb9e3f6702e416211115e5ff0054d68ed68f50b8cd","cab0c1b90f7e73faf646b033a9ec7e2aa948ff248677c6cf0671238f78cba51c","f2b2b0df1a754fc725704c5aea5a3c5a3804d5bee2244d4d4cd015f6faa31eaf","33c37917cee47bd1b2c7a1c698189e581448397cfb743155ef3faea8e9727b51","8d2aea0d547a2deb1b76851b54f9b31a54982814a1dcacf565caf45329d38078","f78c3364bf104749bd20f007e01a963bf8968813f257e32aff4c2271158f2a35","8e34e4c926ba29d400f9d1d27b994064a6576c9006659cda5cdb287038fdd44d","6d7e5ad77f7a3ac8212278318f1f132f0572312e0c2d0379c52d82272053ce4b",{"version":"00c3bd7d0b81b9641ee3e1c6be10a7438a2f9b13e4a29ad00efdf1b8e90e57fd","affectsGlobalScope":true},{"version":"6b9ab0629916122c75fd6813e28deecdb55980e0962b55163b480537ad20da2d","affectsGlobalScope":true},"d374ba45d857ef1a599ade48ba5795449c0b67fc1a5293a1af2a7f4428f0ea8a","daa4902692d92dd039d7b618bfa972571987a2ea17b69d84eeaedaa271bc4a85","7f006666a78fc908ba961e15aeceb42cf11cf3a9cb829ba20c859f162d96d8e8","c6fe1dc8cd4819f5a4d5ce428ca926e01f0b9af24d736ee0e57b08cbdd29a30d","8d11717eb46f8b6ea9ddc810e31d2e61c992b3cdd69e99b9b08d6da9a564323d","dfca0880eede4bd0a62ddef7a1174c874ca4ddebd93109ae2b4ecbd5ac150e8c","d91ece5c2ded27862b5ff08725a6b98933c7847a17b4679d3e266d1f627fc26e","a9e2075bc20d1e51d6a724df4b27fc150473485b7234873a49cabdf21777cdaa","73d9e27f10f3d6321570013ffff9ea39aa19dd2544ef8ccba287da5d4621a0a0","f1d7f8498a3ea071ef8e8c0fe6950b11912d59ca3e298ca4ad25ae7a70474c4d","2ff73e85f4a525bcdcdbed03a1a0fe9be08f0090a51b77b330ead8552796484d","74a70afe5b9183b8ed54f8b618b6c7b5f87545d08a3f27be87f0c04b12737380","faaa5a2c9f2de293541bc03c0e6c5b418d8f1d22dc86cc97b0aebd204b2eb0b7","a4d77a8f1a164f73c5c871c66f0cf0fc6069e88d254c5a2a3e9c860e04af46a9","2d7fcadb253a1f0e3084a59df37b1a8c7420308a6ad0ded806725d45b9146ff7","d7583cd8878805c9a5c8d7b33352b6f627a5e05a91f31c6e7febda71ae05ad08","69f92747ed87de2bc5b3dce46be6d709301560db92458d187204515a8a0d54f9","b2468d006a1b89c08e211d70b397649862993d7df51cb4f5e7ef9a4ef4ded294","ebd7918bccc99330f0f507517a5150c3212de44ed4b2df6ded63931edd879fb9","f70f956499ef2c168ba60b9166770ce4b552d5d7b0744860a1b8fe223eaf0150","b086789e795ad0865294f2f995bafe829848a88b812168603d4286a08adbc4e1","c104366dcffc50b776bf99222d730d878d38f5d2de69fc359932c60d26fea2c7","533cafa1cd5613b6c76537fc202888dded05c93714d3177b91df3deab953f2e0","91daa1d1fa377ddb70d28370c2fa069a1a68af7da50ca0816ec1deb992d2b9bd","fe283a7c4f85d6263eb4a882ec092e1133c3f7825c07aee85ed6368e49318a9d","89bac0788076639601d1ec623475cf87d05d76e2c97a6455b1ce44fa226443db","c4eafaae3cf912bd6560ff720dde500f139999449eb3af8befe62c019506f763","01f0f1cdff3613cbaa9301ab1a56b22b68395b149119cd66bbf4437f29f6a097","6cf8b1f9f26ec41fe6075b90a15d969fbbf19c125754724f60c17f804dde6d09","15d9e6d0e225cba1cf9e786e3b36dc6586aadc4dc80c20c3cdc4d3927006e4f1","182d1e9b977b1f36ab4814fb8f92d76e50dd43118ef78fd54f6561d9db380cdf","1e0e7d6ac06cf5689cbf34faae5e76dd22f450058ca895ce9ee632ab12fb0773","88f7913106c046053d4695c76ad186a1372982e9d7023bc06e7b12afc53041a3","14381aa050834692adf4d8fa52039c6853583a7057f0b302fc0ce39010b3b084","271e537784948096ab9075c73fe286c8ab9e54652a0785bc57f0c1e0e25e8040","c4bdc8d6eccfd6f701f33caca1baf268118fedcc149416e8b160bbc60e2f7568","5a5f923f9e8670867f2ab9110d8c6f7fef3af5cdfb8e597283f543520969290d","3b40b249c2074096638a0a5bbda23c88de9d64491f49d21905c35702ad3abc23","4cf35c7c8928f8ce8b3974f90b2df6f87802faa20cb01b36b1a3fe604c0e608c","1f30014472031f5949a480a0326f429625cf741d71c1a1631f749ec041f83efc","717bda150f7e1e3f132b275baa927bbb8a8c141fb9f9fc616e789e974259b88d",{"version":"d0d16f81243a3b0a8950755762360a172cfc97dbbd7883ced1bfd9a0547f7293","affectsGlobalScope":true},{"version":"dc93da53c0afa9e2ef87b2b5770901298c1ae89fba1566d524e4470a008cb472","affectsGlobalScope":true},"7d7f6176a7d6584b63eed02da2e22a0e0b56d05f9fc223560510fa85c2494157","7bb8d975284ee7e83caef4a6660e5b6e5b22639990ec6afb9c72240bae38477a","9a2bb86b48da3b36f507b18adf6ea49411219861457007aa698c7114a43ae330","c937af838b35476ce819eb8fcc73eec0b4f3f7e058eb237df7d09849a099a2e6",{"version":"e0a941b34819530fed74b8ff51a0240796d73d4529872811d3fbc86204df25f5","affectsGlobalScope":true},{"version":"bf5ae5c165a79b0c75075661f516e77736baab4ce735277057d8bbad0ce079cb","affectsGlobalScope":true},{"version":"9e2a80556df7c861fbb1700df993105c9eb87c2452b451a4e3f28c06880af96e","affectsGlobalScope":true},"2d39c7530ee926487230366b7150abbe92fa3efc153c2a143b05d597f69d3ba9","314a74180004918f499b14357a21ac0c3470de8a72ede907437ce31f55c8083d","5e4d519bd805e7af474d599460f17992167c21c6ec112f61b841cb69eb495017","2549e869c207e3df89d72771828e2832a4eead9ff128bca9385c7e08483f6a89",{"version":"68933c01f0cb1e837860140b6d55745f8736e11081819949ab788dcd55e50348","affectsGlobalScope":true},"0de8ebb2d6faa3b59fbb011b36090bc8f11cf830414599ac20510e18c54c3760","cab087dee51008a724eeeaa557dc196a96d8565528bb5b2751cdcff50c784c02","2b118de643af6feb7d35677a341dfc5330df4ca6f99f7317126c59a20087f2fe","943245ec0265e73e55a467522923be0ede6340a7aeba02cdfa05250b8fc6432a","6e5a06351ea78f9630f27f14bda8f4d6249d095c007b1650b76ac15fff8849f1",{"version":"5f486f2d2f8bdda5f04a8e632dbe311d17cced9a948165f5561f183c60c6548c","affectsGlobalScope":true},"416d8875a3957c49d9b202d6b29906602c66f5dd2089b9115bf682cc9617721c","37a45a71b36020f795db35d47325aacc8352fee42f89c40d0596ce87e8a14406","39fb7ae1e4029d22df578f6af3e38e28ebab7dd0fc431ff8d8705a3084fb6baa","2894363fbd4e14663c347aaa3af9e587b900f747c5180089617d608ecaba4928","fb155553a26ff986c247d44b210176d036b6c3af68ac121dac4258bf84139c73","065931ba395e7ac2a8bf2a2d25e43e30d12d91472fb66b5ff572944ed0a8599b","12f2e3d88c2fe899b01e761a711cb9ab0855b885ab5047545c80a07587b0322f","a7fb6fe4e891705def0a20c14a03fff842e7f02885fcacb6d8174bef8ac527b7","476f9d38b6c986b0919aeeb55d7460de04547b5408fc6f23462712c74e5319ba","b4d06649929013f22e1a3c19ba03c54b775723e9ce9d9817a9d5c07b7a723487",{"version":"53a10ac4e60b6fe717bb6a7b5e5e15a78ce0974c732bf8fc033b2afb85507311","affectsGlobalScope":true},"37c4e54d98672a014990c5cc5ee2764733524508401f13e96be41158d7a24b71","b4180f6a6bd888934c401f4fa942b15f541a83050a402d284105acc63d841132","ec01e64f267f273509144084264af4fe0c99ea1df0452d3647086b4bc5126f85","a5e0e8727e93389ae507010820522a0347d639b98cc2b8f47c31001f700b46b5","e4fa14ce302faf613cedd78324f1ff9a5240c14da2f739ee9c3e44f7f32cd500","ef8dd99a50f909d00eb48e8f330bd164707d4d73d73ee8da976eaa9a8ad78194","5a9b2994d95efdad1c31d362cc9490931c5ca54c757710bf96fa8ec375f99ba6","da2dad9f4a1375687238924e68618e66d8b44a2f13ef1e19c1ca67af9aa48050","8597db354a1958602be38febe019c41112a1858fcdaa5b31f7f96696b508f1ae","57fdc643ce04e28a3ad2b8698e10e135dccd9573600edc54114553eed7d61de4","26a2b3109b6b4e3f3c6e59f3a9380dfbdf0d2067a3e2c2e4239a7fb19c9cbe16","6d301edace2ce47fd77e3b4a206e62721fb957ec304b393d7a2d76f5bcf7e425","97dfbe76bd64e99aefc31dcad34f620cb964d5311f67b036af0a74e196c4e337","eff62c3bdba713fbfbcabbe6e879c861a3e49d4356501dc0494d7005c6d170fd","ad968161114377051ec921642eefa5aa03918bc86d5b7f489f892cdeca187ba8","9a037c033d765b5b15ee7b24b0faa03be4a234cd3cde7b591244740d1d896d91","f0ac680163b9b69bd10b07e4359430696c7e5bcf4a5ef93f3aaa0dafa1341760","1ef8098ed9417f3deae4708ef473a19bad787f89e26f6e3a26434ffb142230e6","38e52e370b2f1775822244082d37bff0b5601a998b8454f3f60946eb74b6b486","7be3acbe810d148937b1a5393b29b4b87aae3ff780cad0df56569243288f559e","2defa550e94d324c485863b0b413ea5ff65a3826fb2461ec2a30ccde09a8eb76","f8431a49b199abed47b748993ee3e6fb92f2464a9abd1e6437ea2950b6395133","e258ea8dfb76fc89658e7ffdcd39d4a46df8b7a1d00c61e18fc3aff28eb63ccd",{"version":"09f6df45916a5e9ee14e4a2b40f266803a91d7bd2f8c98978eb448ce501ae33c","affectsGlobalScope":true},"f7c73d40cb6b2772726626ecd1ffe6b30079f105217d4563dbea0777a43cb257","0ad188a0c41be3b5327f4855131c589c94b24b122a1233910525aa6433ebcbf4","5404343cc937fb78099f0890a8af9823fd52183a5f1beccab8c5a9149b830fd8","655d837006fb67d4456389d8e11f80f970f06adfc5e05afaa2f69d3096c8310a","dd047d11abdbddcc255977dedeb98fe706f9792ce27a557d6f52198de535e637","4c9bf7c67120a0adec99f7781d725c3c84253b82e877f17818a2b7b56b71b51c","b6a9fd4fc7f44d79aa5154e13fa04467d9aa7076b8243ac2d9f17096ea2c9f88","6104a69f7a5a13b0e25d65c45e6ef2ebd5bbda44f3610e029feeb7697608464c","1898f6e54bb9e727399cf88fc94bc2d56b828b391ce090dc64107783a3f8179a","03abca2694ce6bf8e13e29d912e287e9c8f05d2fcb4fdfd12e2c044ad49be2c1","269a485cc622c70385c9d8bd75a1c6a9829f00791a91ef5c50db138a3f749878","f2dc9835081fd8a062eebecd44dfc266d183c17f3eda6a27a8dc6f400bdfc916","9c133dbef6fa77538d85999fd99e4e95a3c3baefc1b347c4ecc70ba8fa42146e","1351f9917d46893576b31ba8cbe6170ec21dbc0b660ae90c5447460ecc69f331","78867443da55c381ebad91792ecf62e90658e874d42a0b6e56db58f87e1f3bd0","95791d4cf732e9797ed23d1a8e996f1b9b8f6f74ced346989f5189367d717094","caf5b2b247095ec178b2106eb58bf2de3abdf4fb2b8bcec0c07801dd6fc122ec","cddc62f8805397eb7ff97afc508e901da5a5f06f234bffe4bda40d5831492e07","2d7f41a8cc85416e07dc37a689143e90d7b8ff05aa6d796e359e36184bb53bfc","4138741ccc0169616d06cddb6412fa4722991b66cdc7508fdaaa2bdb052c641e","c27591d30abf7c9e49bb841dff23fd0b53a49570d7c06f291982dce93c082298","84044337bb29b3664936e8d2391762fb94e17fbac52bb7f7342c1209a82727b0","3a3af247acd8be98ad1ab0c9415033e777cca0926be96415b2d5726f44669e89","88360381bb09f280154dcf23ca7401203415cbd42ea0269ca29588f047479365",{"version":"c53046ce667f4610dbce0270ef156389eb4774e98a4b380280fbaec42a560004","affectsGlobalScope":true},"9a029036e52c3f3c417db0f96d4aa5cb396ba3369fbf54c18a7f5c8327dc61d3","bd191a65a62fad90de56095e63ee5ce02f418c3ed5bcf31f431ccbd168bcb1ad","5e3692c1e55d9a1731dfd75d9d1c92f937fe5c100f4bb4133740b9be88252d51","eb3ce02a21a9687e4820cd782148efaccf25dcab30cc61fa3f5745fab605b51a","ffa16f8fa2e2e089054db64ecbd68ec231780fe3fe93ae6be6d20bac6ec1d349","0f609e50a3fe7106fbeb7f03f175bd2b5fef80116b5a966003f40ef1f538f778","8637e4e565df51cff7d87eb37c966c6b3d512b9b99837e7a45190e98191badab","383b02728b975436cac2af7c824e870c8ac526284554add3c6c871a15772f224","0530dc90350c688a14d28ceb2b83e1ea171743fd714d50f325f3a9414f638271","cdf2fd79caae15b879620fdcfa4c332f8057fe61f9fed7d287f69183b73596c9","d2cee5300d554a42877553d07147141ced6ea24b62469bf3275aa21dda72e16c","ceb0c6a1be8f82af04c926bd1415f9c7b27a7fcd82ea2d11a399d2bdd34fc991","9962e9856da50be85f51827780dd22e7c50e40d0b10f43feb645d4e288262ce5","ed0cef4ea04010efbdc021718b38d0153332aed1cdc5da08a8250169fe6671d4","e323d87324a2ab6865618e2cb85b179ea0aaf23bcbdfc1e8f75f9d9c4d6e47c7","b035c7b4238e4a66ee92c5a659dc7053b99b6cbd981464f896d05b869b86a4e9","746460fbc7176eaac56aaf2d6c012aa570edb79b6adc270d0823782d5241dee3","8b5f4a170a448eb33afd81d14508cd67c034f2874a26cd3c0e5013f9d3b20e6f","ccf2a9443c7d3d597cc255f049fe6285a92051ee7d77acb15abe9f8b304af5bb","8c41e31895a7f618b9c4ec21dfa76f1618d3544e33113068d734a010a94be3be","745293d338addd1d06ebc34c069e6eafd48b1dd2810f1a7f29426f56dec7c296","a8962cb27310764798659c5c625338334353f433bd593589713899f898a026ef","977064b49adf1163c9dbbf8c6e605b53a6f9f5d60224f9da9d6c41f420ec451b","fd962a6497cd4eb83756ac4b2c05b2e57407bccb9c1541c6fac2b01c21cf7df3","adc332be8f60a31380ed3f36c2f8159658db0fb9842a701beb2445ac741a4a7b","55396fcc7f38f85d796f6ed859cca892b15cfc7a1dfc86eab1cfc12722066f06","744b2ee6f99824b818b3ae3995a6f5ada77b2466d62708342ef1edd4194d5432","221707264ea9e4f5edebb158d253c992de71fd893bb828131b39849325b40096","f6bf383fe5dc5db4c76b419936f6cd75afd911d65c91a0a2e2080b20fcacc4cc","591edd22ca220888d94d9b1390836593fca0413e35df6c8831e29690c45ebc66","2edf042cec5ad67ad011306db9dc55177fe039db534e47107f2a1b1c2a6b5203","58be5c2c6ce611500e90159ff3e89196b375cfc58486f6d1cd3cf6f5fa8b0477","04e4b17250f4544674528bde25fedaa773512f5d414059150bb9585de4f308bb","72fc1934abfd8631032cd45765ce561a709b1a9d2bc052e01cd23ae15ab4779b","c55e0f84841a72781ac06713c1bde2af5df634c9b2a634310f8e81d32ec65aa9","821e25125e30e5db5c4e2297b14417f591d6893a0aed9c60d83aff61929fab5f","0dbf32e20194d17b7e81f263723c3260171041ca94fea76edc03aea2b65ce5d7","8633c326ad88f616ad39146f101ad151e4dec84dd8f855e20ec2a7091c6a861c","8c789c05a5ae32e91e76030f083c7a4f07b358909f2126ae2c5a6965dee585e5","5f69658ce29a40c9da49ecd8c5bc00974b6c13b7c69392f73da8cf063d459042","743add252578c72b91dba3b5b24780bf1d795b37ffa1c4eb0b9afe7ce655758b","7d03876c6751c6cd0085777ab95ea1a6936ea7fa4c55e39ce1acd4cbd8fa414e","ad2c50dcf141f05c8dcf0c3075a2c1fba07ec0989b546cfc1f648b970a1f1ecd","815a3887a8b48983d6e1213605e86af077fe29eb1ce462828aab9b8244f28f0a","9e3d3e9185ec58977654c1080391ecc510384f7a602917e7e3c2585c0eb2fa1b","64370ec477c0d0396d351a90eb1e8fe965df6504c284e3afcc179e35dd7a46cc","adb8be01759dcde2b2c20cb97f5b30923f73eed1a045e4bec80f2efcfc40f057","129c5c2750578601624ebdbcab5b492a378597c58267e41602c6abe4474cf01c","b4f2b05a4cb6f1b60e510749c59a5b2e73d545148b96b9ec44006d2b109f73d9","36a7a029734d8b642c0203c4b4c5a043b7ad3e77a2372f15a1e3b18c4c8e98c2","09a340ce78671c5fe9ae1eb7dd75619c16cfe9313616eb69772722f95bbd1383","269d0d6341a258518ca935220436546fd31674e843b7feb6a559aa33e3f6d969","61ee290b1031985aca3d7813cfbd110265a81e64db1f2687f470d6f5bb86bb37","088f73d46c41477e3994ba19ff7bbc4bec258959fff34502dbb32bb89dbe9d2c","09c874e70a7bea5a7f50dcc809b6dc10a940f3a526eb99e707321fbca54870e7","a1087db82a364995d822ed2e8f0df7ed9083fafbce2fcabf42f706540964ed08","d89f4863796df6d7ec9209ecb20111169f1b858b06f1f372b81ddee612b67673","702eec9fff70f487a3a8126520da6d4272e5f1a06afd1434fab82e0e1c67581c","082667d78d6caa1af550863dc82d3a02ea98d7d13aaffa996dba7118a38e3637","d1c16d1a221e8508cfa07428e40d25cf13ac3e15eb1be56b9983c12f5e4b3b52","ddfcef0d83a8d28dd74fad1ef491aaf96665293c2db2ab0e30fa1246b30bfdaa","ce190b39ec46e0811f4d5a306221b9d07c3d69c28aeb1c189020e5ee1ba6d6e0","26bbe692f03d5fd9b8c7db4771924c884fb824c7e15741ce0ebcd21dc740bfe1","6fa256e84d8c393367953a9e8f831067dd5ff7a17720f56638430d64a53b6a59","b1176cf4139caf3c419158635d8244eff4fb536dc9c3676a4e9832d5e87366f8","b1a3a7a628ae703abeeaf38d438ba8ae1ac81ed6f4c2d6d6bfaa50a6fd59af82","332d661343ba55b976f473bba7e7e1462252a755b217fbc18368cb3b83c3baf2","d8ac5e1d124cbe30f92bdcdbda476b74042b4bc872a69fa0112de80ae54767dc","a0706609903d97e064fd4ff626b656646709f61f222611c894c93cf95f858dda","8f6538929a220c1e97395e01d66fb3425a03e66f44a59111e32f6e0a284aa749","cb14cc9645f50b140368d9920be58b311e7b75f4a4236b7cb67d24faad5f67da","ade2f900f4c2709e765284557d182ce29a1d2ab3f16977b87b4fd20f8d707098","fa7696850063bae59497a1a0e4d3b44ac091d8be5ae520db8bec2e0190efb8ca","344c09199680044b1c1a2f8d7f9af6d253467742031b316a1400dc7160349cf1","08f96cb316059d4aeb3eaa87d1d632c2de37b66ca882fa86fee98d97edb362a6","60ca8ee5c716848a696a09b248b8de95c59d9212bfe0684070f31ad35522f716","1ee6a5a21cc924db75824ac1f67ef52d22bf9a062f60c68ca6bf964c43fbd485","747abcb18fd45b5b9fdb041afe2a627981f4b13094ab6e85d97b6fc341b82481","82f95fc67c9f1ef0e447ace8b6a0aa5f66dd41866b73ecc5750f56e4580b23bb","aace255eafff90c463d8887ebcaf49e91c1550475e8734bf2d314830eae43a13","bb376587e4f5de049168215ede898496a4890a1fa56dbda5f695ddbea65cdfe8","17ad767dffe1f74026f43703d5b6cf2c58b402594789d1b13367ca9ddd1e76cf","401b52860e2affda86f210dc992bbb04b295f5213f66cd7dad5cbade48c6f0df","d6e5fe84f7706e293cb2c9568463c089a9d4cf91cab1d41dad977f3dd817a031","5c34fa4b0a4eab50696597521c3772e85f16971b23a09a83fca5de773331de73","3e009db57fa7b6b911c8c2591192b7b14004141eb69342ebfcf480902e442165","2dd7ecb8f8f96b918e4ed232a6b8658425c02fcddb606893e4474b6ba0babc1e","4ebe2d794da78a4e7349397a4c7917598c6e5474fc34cb9c7d7888833d57e53d","b8e84b8ab2cae56cf718aa4a9e087126580d9dba2300bbdd4e537272a54d3218","a8730eaa0849d53f805650d7ee72dc6430fb51564ff02f6739c4726d3f55e722","2aa21b20f325a0e5a448e224bad102a9ec55946d5aca71f3a2ea3b77117cb4fe","412152b80cee0e2b41df15a064aaa3beb401624722ce4f42d1faa687e425395d","2c8aaa1ad469b02d0ea6ffbc0ae45c5a0b7292da541da4bcb36d2f7c8a74d562","f1f74fd1806f567a1465a13b1349fb39e78a61ab9ab5583e9dd277c23b0c96aa","7c8bcd43cf26003fed5c992433bfafa9f8cb04171e90d1d188fa693a76eaf264","4c051e20a9c70fdfc3a6305814e6bf6d3f883e56af9d5a2620ee0ee97d7c47e9","c79f031b125521f02ff8e57a21e4663cf875c73ed9f7917b0aa19f59be03f86d","678f0778bfab92a24c39d668a3eb9d18ee43808d03c3e008f04d1aa4bd9f9c07","ddf4dc65e27dcffe8488bbff178555b6380366caa74dc376f3cb3f9e6e32059a","11cf055837eb988044327967fe40aa6138ffa546a724ab669eefe4ccb3876ad6","3ec76d02d40f47ffd40422d870726eb11e21f84b93355bcaa7c2ebda47518d55","cfb827fdfa837d2c1a3b9934e01c1e1020f04108fe13ddbb4645091b8a9b7eb4","2196278c32234e18024cbfb9b1cad10fb4c850918261233aa4e53c9b41d5ff57","a3b63358d8feb4f760d42fff0f5602e7d2b9a79f1316126f828447b74513a8bb","83e2e9468aaa2431cd5cc30a7aaeff4766ce6a094c63cf4e3330be4971b55959","6ad35e8ff0760a44cc1ca4e544d53dcec2f96e1119bab4af93f77ed393a06dc7","ec655a72d99e359574b7cdceffdfc973a2aa0bf4864fb5469d1012362dbc9bbc","986e48b630d61a5ea069d5ffd0a7300eac72b537a6a80912e9f9c76d36930c3f","d79c4eadb9ca3c70a7018332d5981dfcd39f12c69e6278d5edbc866ce53a3542","53ef3a0a6f11f41f2f8753cf0742825678d6475a0804fa9a4f802e30b63890a1","799c1ef4436ca2668a0a1366ee77aa00441f928dfeb9e211e4fb5a5b651e3b9c","4d9296c82df8d850d1c92b055d8edd401bf2578a92acbb84978cc8c82f627c39","18f2da2d3f20ab01a79f72fc3cab4821d3e242132d41cfd89ee23b432c520410","6023e2b65e129cef896d2577b8d49b8da99c6f4f92a35bcf57f7a8261a9e5c3d","e1e0d47c18ea9556fe6bb718076dc0a05f24ccd3534c46b903c40fc1a3c4ea86","4df731380bec33bece48e7e73bef837bbcb0a39705f5cc8c4fc128c0bfc9cc15","abab4a99902f64688599b579ce3a2e3c9d9f756832f652e2ac2aca0c211fa612","d2778b1c5a63a8852473957a15bbf9e19dc46c3d18535d044f8c6a9697b854db","ce8193e780b1b6e7aeac6fc5adb2421d4b47c3ac6fe1fb5c7019b6368afcf045","5c728a147dbec80d4bef9f2603eb0574ea905e12897b249d609131bd77e761fd","3beee00c82ac683f7635df13f90003a40dd442dddbef2f12ecd561a58fec5dfe","e8a1e5fcee64c1f4cdeadb11b6ba6eca0a9319f49eb24ad3186efb5bf8c85050","e58d5b76f455469bdb9c00830d63547a11c4b150123d37438b368203c0dbc2b0","0961943e3a9bf8b833aa45a7e0547ccf1af29c646f1234c319478d4e27ba7bfe","d3c43a6caa5b4d37a75bf7716ad0bc76d6419f4d8cb955be95a50e57b78ae133","e691cddd472bd6e35a75a139dd84344271e0cffbd1c66a944dd550a4f2d5dd4a","7a2c67c88ee622ffc18e4e4bb5f28bfcb1d80a5e8f87fae3e988a66214cda825","30ca33e57008650ac6ffad58112d136f98dfdbbc854b01612cda3554d9d2e29e","25f55a6c552f7b7c3d5930b560624e444ad34301efaecb8696e31448d61ed016","db0fcfe9c8f46e4b50cc4bec237dfbc06d06e17577490303f49290c0376218aa","85d910c7fb524e6af2ce3bf19024ad561792b7bee8ebb9f60a78508e3493e1de","614141f565a53aab34ca221fb7f7f48f350a6b8326aed727372b463a3d656907","ffe36a78df6c331c084bda4423d58e3dc82af8b4caf71ab3426b13c0fd615a51","343af1b830264da5aca4b3e66778b28654a21c9f56bb158e7a11cd023f10af9d","93ca2ff8a26ea7d0a0016b54edca86e3b2e315ceada458fb51070786f734276f","f0dd292ad7376cb3f6cac4ec175859cf8f52f936bba242b355811847c945faf1","a66d7a9a45abfec6b8e6ca21270f4d79fb164617438db6f9e8f766c18693b1eb","705782add397d850ef2c43386c3ef303451a596bf0dd6d4e9b0b5aa268ca882f","5d8c75cb2273fe77d02eef4825ef2644b64fd9be42dd566b854caf517236d7b7","7145f05bd45befe493641be2f92a35f2f09c37d2fefeeb8ae81020290bf37af1","f35496848b5fd7f8ba4da23a1e5642bfe208a7b4bffaf568b20e3c32a370ec89","cb1b8359d6dd3d36cc50608767a7268aa8c16ea4e901a289e5e636aa4b434b5f","7d6d719158a4dd7f5d29081b7a042c10c09755b67299319da5aab5bdcbcba997","ecdc08bd88a78a419b1e558f2b36bfe4c59c6751b6b693f7bbe72a7e84856589","d7af6d2ae358f2339a78199f0bc7261b70822a8a412430e1785bdff222397f72","08e344398d2ca604137aeb9151c0a8561c133d565f64020b230417a1096c92af","2dad929037f16ff8f6b6ae2b7fadbf8ecc215edd685747910611f4f4816def08","a944bfeb4cc0c9a84115b97a73b9d8e35d20ab27855f581005a63310b8ea6c4b","9c9fb13d1dc12f656aa4dbb6ebc002d8ded86ed8e6cfb3a372ca75d07bf69834","f1fe7cb78ebce029f3666107dd30760baabe6a96ecfd81091730982325e161a2","90675347e5b537b13557004281d7aee8767191bcff998ab0a29fcb606cdc8e2e","e7d263c3b1f75330bb023216bfea9e5001dff78391bdd6f5cbde657a122cd4e2","c7f9a127648afbfca1330cd5e0048612a1816254ef79f3760b811807be7848a5","956c02246a61ab5bf3324ef11d64c9b79947d7dbb8c0d9ca75917a1b39757eb8","a694a26773a7942ad64e9316f198e8d764750dc9ca02c2489a4deae53f731392","f4237b98241a34e70ebcda021db7d84ed2708a73be69576d6d62abc520cdbbf9","190dde699551989bd2640fae72b63cee03f35723f74616cb45051d527f98f0eb","45f29e5d29a07383eefc470cb97aa649d86bd3a5d097edff727f3f1ca0ecb70c","7db2fcc3af5774098dd8eefddb5794898650c728a51269dbc572de65f06a70fd","a3dc743a8451983ff951261ec138300ae765dacc66784993abc2040c11f91edb","81b0b5762d148af8db8549f093262e092191bdf57001710b5fa22f12caed942b","b18669a0eea99ae24d02b99d35e565e4aa51e38e663697e13de822e556b2119b","8f1338dbc2acf1e4b5d1a1a02395549a7d183ebb8a1c3f0172563134e6c79af5","8c43a8a5d47bdcf6f66c247c199ded68e92b6650f6de1f55917caee845d1d61c","3b0cf7fa9d1cd27c5a187b58de15e0053aacbad2eaa7309341072eac0ffca8cc","e58e9157afd209ac26f56598483be9c3a923b48a66d7ed4ea7470a6428c97ad5","c49ca117a3159ddc4fd476df68bc7398fbf1dc1258ad7e5a73c84bd2b5eea6db","fa4721034015900bec6f6e88324bd2b8c2485b0b8c4dc2e01db4d7dccb992e81","cb86027e0b2ebe1b4b00b5bee470d5b0f0bbcea8bef86082d3fbe4439472ae3f","b519b10c28ef75f97b4fe89cb09eeba0c84b7ad4a588b68021900c9b3e9ed1e2","f787c1b82e0b68c7370b05175ea8f2875589152499b5aa5382d0061101531501","434099b9d122ec3e07316fd44b24155c5c9671a79479bf9e54033edf0d61322a","188f1d7152635ecaed19c16640b82c807ce2cd40cb284627bbe8d1f798d3080f","23620c124cc224b2a9011963bf0071d719953c291abee0f8508a9a4f5b9fd585","d7d7d12f908a1f4c19096df80cab1e70ea000b52a4671c1c4322c208a3a8ed1b","ebe1188fb6d9fd08c976e0118bfecdde9151a29f7937d6b6de9b7b3b058a472f","e05aa3af45093756bea6ca83b2d2a3de6d48e9ccea1bafca85e9123bcc4a2aa7","b4a7e1082338f041784cac7fbff09af0243e6e3f1633785d5588d35d0f3b65f3","ece2dcb5dd42f11d0d126241c2647d18c4694a6bd861e8571f7905942466f132","b663445f403019b4916ad3417b322d283cef4664d40b510bd10c6b7d23aa13f5","04f25e861fc2bef69dca7f8bdfa3c3f7f4c845e3f043101cec4bb8623c90a8b5","19361c1e7dbde76440cf3ee339c8fb4cb25919673e9d68447de1d107d129f858","c91118e0323bc3666ddb99dcde29582307fb5e57c67dd269a390816735bb2a9d","9c296dcf2de6dc7aebb490d44191b7ab319f5fa42ce3990bae61331f88fdf34a","ef601641c988dfe44c62cb92473cc055dedb95b8f19b094c2082387715601505","4f691b2d3d09b55f30d222354bbcd9debdccbe9cc5d5b56f648d91a56e84250b","c20f21a26caf3d44d0ece98eb639020887ca409463713da59c0517bd0f3613f6","e60b8141222612b42838e9454ccbbaacb4c546b08b435b9f42fa0ebcd0b4c50a","0ed82f68db0ea7ff57c68e53278f2fa46d10820fd3e496657060f9f5829968cf","a1d384871a20db7405523716436cd64104241bd3af204b49beac0193f2c6a6a7","b954387f67c7580f25eb8cb667dd87919926f301ae702688534c31a8b9ef33d1","77863145f1b1e2be653edc181a8ac97f6532cc2545c991e16fee3e1ba1947694","050d5cc22e44542116a27c8b38f8c26acc9c89ec288f96e07d7ebf59a3dfbb93","bba0f55793b9e9b995fe5641811221c4f2cbede8dd63100452bf7d890399dddf","81e0761ba89fafa1531f3d65e7694573f91a771b82a62773f8b42156dd7fa7e8","7fa84f8fb7cdf2cac7ffb56aade25b9de8c5622424489df39e5baf4313d61803","792b69b5c9bd1a3974f31e5b7fe927266240b3afca52ad7f11cbe121b24227d7",{"version":"1c7d5c73abb0d80b28a9accbeef613e32f46f61764e57994264aa406f9dd4015","affectsGlobalScope":true},"eb6a61e3e360355c21e5c3f3ffa7949450f339e4ff9d7bd11ee43d81e69655f2","27f494d2c924fbdc7d28c132ed4c2fb06eafe080f4d2ad2500a41b535265a578","98f6b92223429b6ced05baf7a08fe5561ca224ae6b0f2fafda91e0012fd56e88","abea1c36354df260fe0d27c5f8a00fcaa4b5f9cd2694b16dbe8b0bce29e94fca","0f2d602c888bed8c628a23a90ebf5dfdfc80dc8fbbf01af3d97c4dec02130e27","3c3db9f2edbb74e8baed1bc7b976e51c274083d97b7b9c0df99eb0d43ce7492d","f5954727545ab80036cd4ad2058327deb7de2f08b127eef8a23c34da8a717dec","bd34a89094c34484b6e262b9bf583ddc4dfe32285e7865d30bad2bed7db0ac4d","41de2ec2cdc4bcdf0a94e79943fd384d14ae82438dd4cd283d55471af7fba7a5","e06b9db953a58fcfbde3199029e49f76a68c7ff1c81936a7f69e9e1570e6b6cb","7174632e42d416c012b0ee4b712bea972648e3a1c8729fcddb753158ffc26ba2","9b550696d520fd1eda162fe1c7ea332350533d5c5fb34d9961cfa9cf28835f21","0dd3533681d5dc8672bb617667cf9942c7122fade9b581fd2f622a40b98ef50e","9f31681b3a78572c165aee31e2912a22c73b891b70d8e4e11c9d99ce3618ac89","c31da7c7031f18d7a37c7c394cdfa8a45d74f2276b8853759dce612f7f126aa9","ad7661b28c644035590876bf25674b0a66ff68c5ad87e7d5bbaf9fb6658b959d","4d8353150f5710b8ef253885058ff57255eda45b34efa313152093574fa31896","0d7e603f520aa3c6c3f82802bcbd20ccda006f1b8d8517c8af2372b387918822","a831ced03d48b6506c904e1428e593f853d7dc7bcc6580302c3a802e3add7d5b","9d17ded6a8ddabc7f2b4af96b7d63cc7d833fb1432653d7bed6a87b3fd50aef4","732f051920c02b646380bf0e7fc7725b844622ffedee94229f2a0cb56e5b3002","9902a9ddb3289e22ff9eb3d088bbea6159c2849241b293ba9fc62399ba2633ce","ed254541641bdb808757cd2c9556488146e21993189cf1541d5f344c64c9ee21","cdd832bf3559de3d4c78bcefb8fa2700271de43e747830c8b56d6a39977ec0fb","6fdb1f6633ebffeba20ce84fc0ff7c5351fe10292c801b705dd7d094c461793a","84ae86fa5d548727173c18dce4b54d941dc90e56a50a83096ebb13ed1c74f8f3","077409a04723a54a174aa81bd7234ced52784e1993204e39a5ff76e16954b3a0","93a4223fb87f6f08a54d81a9fe9017a166e22201aca2adc92083dbc5f8c82e22","d17bdf16a98cb1d9cb60d2806b9e6243e85bf107691d042f97305d2ccfb3ad5f","afdd5cf3f750c4f170ea46ac629c3f6ddccd7d01916fb3e5cf35575e7e8bbc09","9cd62e28694a6a8180a210e2aa69588402dd5fb0d2f6b2e814e5e48acb9bd3d5","556fe05cfd69aea30fecbaa6a9e763d325e0b5418dec6bdf42c77f2c7001f38f","66e14d1dd2694388b5200597d2203249bd512c0b33e2bb0c8e20e0ccb6ce5c19","8cd7adef4696e91ad2d7f9cb19fe172df9491cdf7d5f74dfb56698c562fff100","16ebec91286d987b7b3574e6743f646c3a38e736b640bf1cf266758a25ba054c","9e141855150a843699a0f9948a5bc3d3b496caeb307f774170b143f8e1355cf7","ea7979a7d3ca3473f574de4524cf3a7dcf2e9166a5d88044491bf32f44db93ca","f5eacf63902f9c644544325308d3f4f095b24664a3d652c0df94d39f73def7fb","ce9acaf05dd94224e2f02c5d2722aa1c1a55b02b0c00ea5483aa580fb5e3ed17","a10e70700657b1a522ffe0e2e19ea006279f5c02724de93e230c45c0d9699038","8e9416b93758ad9def7697b93e819641cd3a6ba0dd98eba30c5ae674b9796e5a","5035bd0f00a11d52f37078a01c8e38ef5049f711e8d8d5d6bd8765dd75eedbe3","3a7c937988194783679bd5604ae1905350bb305dedab606108097b92e7880b40","f26596c9d2a8e7a679c526ec2067b807e0dfaffbbd01d907fad71d1e0f317c2f","032b9aac3ee8faa3a37fb12ad21a0679101a2ec299fe7f5ebc8eecaed3626b35","dbcdea372752a34e3e35ce7298a7bc55cf3d0ba8ded38f0bb702eee9e8fd78a1","a4aec41fa3ae87b326ac2dfe722f7f1ac950fa79e98c2a0cf1681389ffd8000b","6da7cc6a95d8a400b13e3324b80d930e29f33d0ff8478746c0736c4b7b735ad5","53ba0138cc988cc490460b2d63642165acb8dc9295bb0160d3619a7f494a75c6","228058754c307e8a6f463282d7592e00a77ea982ad805f060285acd430a9202c","d683d4c086e9d379b587f1a8d2bcf08fc578965a8b2f629a23fa1a40cbbb02d8","5672b74da3fd8413f8bd1e44c51786318df43c11a5888752f8f7a6ef83b155c5","627fc6289efc69d28b63b2f51d6315df0bfa89c80aaec98a8363f8c2892092ed","0ea593e1f2ed36b3b319999dfd2d1c0eb6630db4166f60ab674437890bf70f05","3a1a55e44ff931dda5109446c1aef61448967a1072bfb68f6a8f58235ca57646","1e3904334ca650e0cd4c1195057a61fc326faad4f183bf0d5b83f8edb9a172d5","cc1a8cd74c898fb100b75e19ae74e527d45f976dd9da0bf17a95bfcde5ee4857","ff44328b18d2e7fc49bba1f655effdac76c43499945f92085d505b9baccec57a","054e9d21bd7c6356b8907d47327a9bea9f74061db9e102757fbf68c531b0b201","644f323a03a4d4b9080876f14a4ca7486cd2b32b1a62912e632d6d6c50f0c7b8","74ccad7875f86853a7299762dccf250d4474dacd208b69510c6fd0ded2956f83","5428e15aa050a3c5a9d6927e3bbac5f4dc0181d60d505aa1bb46f11218ad7750","b02c9e98e1c92e5302e82b082539989f104e66724513cf3d40884520b89276d5","7875b94e7742ff2fbb58b16ef1de2d344ba8e456c55e4b32833fd2f2ff2e2b8a","024a9a6812092cfa7d68c1db13c5347c69af6853171c3938c84af6ae6119dbd8","1398cb78035b8496a6bdb4f9b02efc4423acf2b9dd5bb56a888b9dc54e5f41df","55722abdc8c0f2a35ef8b579740a176c99a523e440289af759a99130896f9a5a","c35d8465f290f7a2b012af4c0f5153d59b0048e6a53917447424f4d0f7e285ec","a6a1e002f336a705e184dd0ed930dc24de6055573cf4f3fb88177258c039ce9b","66119d0902a244abfdc64aa09ddeb45df77a4ed660e09af085332de5612fe3ad","647f9457d6fd45ae3088075887e81f1b3b6fe3aeb3f16c6d058aa3e02564a32d","8bb59adec1d0b331313f9d9a8dde66b93bcf653da2996fcfe9a09901991821a2","ba3d4b235e44723cfd62568e6f710d16c8a315ac94854388c946eae0390ef05c","d3075474f41dda8041511f344cc14d92c5022d3fb7784946a66f1432e367c153","3a26a54e0444a162600d448cfc74c94fe3223b8a9a448fe4cc5287a0b5814240","990d5da3ccc4c7f53ab38bfd5ed1006f2009cd011d7bc9eda8627007096c9342","72687978aeea3c59d2fc8eb7ada86b6fcfd6b2793510f94729e8723b3f898b9a","2ff6232559542b0ac0eae1bc25e0725fbec9d77d07a10729ed8df0e2050b0ede","2892034410fbd3f1fa8964e403e3016bfb28643b217c019c68b72f4506829627","1ff062ef989ccd1fc8c59a56dc263b732602a8750128a3b4bc490d0b4e7b38ba","edac0c31533eb5973134040e6cc055471ab761f0a696063ac8c515a966f8d031","0293007b2f09bb2d169cb1d6f1b0977944e7cf53146ffeca483b44acc667331e","1bba5544f5ea9c9fe8ea3dfbeff82b670c9717fd49a508d467035cc8d4be19db","912c63800c0c6203563dbd7cbe648171e465a0144b49226c030ddd17a799b76c","68766bd7e0ad21c70f514df89300b94923f089e5514f589f78ad69d9fcbafc57","b11dec0c8c49c05d3bcaeba2bd40977871de0842e78d5bc236c3bfd1c9532a4b","a1f3235668ee764c1114ce65b0d6cc1f373ea754a8110d82e77f7102e461dfbe",{"version":"000b16f53426795ece4898152bf39bc6fb110a4b84b8699077fa1c65b1513ce8","affectsGlobalScope":true},"f278558cd1f3e00ba92d5af86c12c3ae5de12641e656fa96e17aa39f21463097","9fae27a9efe2a4ec9653cb17bebb6f82cfd7715da0301933db2b295564e0a621","b877079e0600fd3296d00447dfcb1aa155d33fe820ae0a8c26fa15d2e53fe55b","bf879f9650597b053a5904aa86fc82d86410f8961025e24601334e5f7bffa61f","f690a0c22258aa8994ae970976386f41025a1020a1eb001b2e0f46d475ac0f38","dcb6094ed617189ed8cc93b5a0f7a95e9df9eb22896a1496646b5991ce96b599","d7264a09d37f7ad76f42a177800dc2d09a3eb513fe5157b7cd0508c1edce9ff6","64c4ac585530e596a074a940021259dcac015b00358e3c00455eb218e2c3b108","db009cad7d4fa5e654123add729aab8658f297aa407a30d1145e2646259f82d7","02fe7bda7abc0397487734247e290cd0078e6fe939f7cfd89ca2ce55a25f8b2f","d1f1b64386fba9f6e7cc92aa2952f1f082fad079106af3743bc8d6c9865f8392","93c4e88bd6e911de0d00b1da1a0b755718d6ba9fec907e41df41705332dab633","b12de681912a47ad06dd8f06b362327f049e9610cb75c8b3bcb01dae7aa3f584","dd7efc446b21e0f635d821f002c5ee4cbbe709624cf22695762c597649248b77","ca70b2c7b205715eda31ca675c6dd8dd6aeb0f767e44e5dac5f70fbfb80eb1e1","2c1de79b584d583742366ec5963f820bb51e70c6efe945c153bb5dec9afc9cf3","85eb49cc42a708fbd0421cd8ec241833068108fb876f1719df64b984cdb73828","ca6a2c48267a23f2423358a2c79b2bf954057635634db7d927770c68c6c57ba2","6c424627a938110b1232234d5ae82b2d6e409df1bfcc129c74d654f790a33b12",{"version":"a7a15de1f0a94b36ce0f85a5dbe8be4d7f50bfccc153369be4311edc0f30eb73","affectsGlobalScope":true},{"version":"942c873f6e17cdc4ca0d1640c7857293ce02078a2fff61928db548ad1264d9aa","affectsGlobalScope":true},"09bc4a3da3b3f03e249db6ae02554ee710ddad7855bd860a9d0c142f6f28e075","b6ce4fac77847abe5a71d16aa166f911cc29fdedd0933e8b32b082ad9854c7d7","9341f2cdc9bbbf672dbcd84395fabbc051f08c6f1a78b7b7f76c0a245785f314","ecdc2d85bfdccbfe6bb010adb2edf9a990d578f0d5f08f40fc8b6947e1a0a562",{"version":"46c63d1dff48183edabf7884fffa3b83b25bfbb8e0a8b4052b87dc0ef694f77b","affectsGlobalScope":true},"47fd42ff510df0fe8c3bd069a5352a63ef2bd80f6a446963b4869a7312f194c0",{"version":"f55b6ee76119d458b0a41cd8dc056e0c512c4ce3a5790e73916b66bef8eda100","affectsGlobalScope":true},"18e00b0d331ca31c944720ec257f986fb11416351fbefbf85367e9087e6f74b6","2270b74ca53eedbcd679f239bf865abb7a373645ae2120f1bffe3f8abeb7acb5",{"version":"9f8189808acd0707df9490e439d3e333d688cbafedf50aec73a3760cc6c1e766","affectsGlobalScope":true},"d95c0afcbc047e4a95568b7a75b4fdf7f3da706f779070d637ffd2ac147ab6ca","addb28e20358c99c9b27abbcf65d27008de9290ecfb8895b661559c950da3e7f","de2ca34b110fe7664bac04673980433cd0be925ad5efddad90daed12d5573ccb","0e1062234d1237d80f39bd4832b0c941d4a2985681f8aeb00cdba5e40d664abb","e15b2eac876adc3f3591ca27e73b9231bd2723f0c611cf45aaf0daffd0bd660b",{"version":"890c1b6abd30cb19fd630c375798bbd345b1e50f0151ae69d6f16ebe54bd6aba","affectsGlobalScope":true},{"version":"435444eccfb98da7325964354c703a6f4944fc977125d03e34374ae85932b4d5","affectsGlobalScope":true},{"version":"1fbc7faa8b4d497a585d518b0028aaee4efbb1724e8ae8f3eeaaf167ef096245","affectsGlobalScope":true},{"version":"86fdc88e019f822afb6ffa55bd6740e32d637edc4f487f866fed40fb43000805","affectsGlobalScope":true},{"version":"8959ce0a238cd6c14fc39f61a95cf04a10dea4a217308a50dfcdb12dfed6d707","affectsGlobalScope":true},{"version":"e7318d96b2db5825ea9c771340c672314dbc8de540abe4e0a9bb20f3e6e7932e","affectsGlobalScope":true},{"version":"c954d78e442a43bb433f6eeb9bd9751890ed7d24a26b38dde926ac1d480c48fe","affectsGlobalScope":true},{"version":"d90ae624f69bfe1bfc9acc13b7605b61e529d92b52f0884f534d5d68b706fd0d","affectsGlobalScope":true},"d9923e41557d39d3ac181dc8b8204ad8cb64340b5f143105e6902b6c9d3f11b8",{"version":"0a413fc4229d4ba9ab89ca58f6737fe957766aa30f5dbee7b46b5021f0a201ef","affectsGlobalScope":true},{"version":"3e7416eefc61e1a810cb432251894d92dcd1bb10b8a797fbcedb512819fc5b64","affectsGlobalScope":true},{"version":"decf06ff995b2f3c6a610df1c6ebe1096ec999d3477dd9d4a86cda7ce3be0911","affectsGlobalScope":true},"a0b1b305ae962ebf4bfa4738437f39a6767540e34feff79cc67dcb9891a63a1b","1fe5d324108e4a3ef521585ac925b6cd229daf1333e2f91246568dd88fae583f",{"version":"d0c875fd9cfff920f5da9b5ff52234dbed81bfd247c21876e56762fc9b02baf5","affectsGlobalScope":true},"f64f7ba9359469d348daddc76211b96fadbec4c9bbf51050ef70d7f83c1874f0","8526107f7e19a6c264ce400535416f411edc913477a0a0e06cb065919ae2f19d","73194c24bb01018b88f7f90886f9d87caf6d9f5a03dee4294f20d3282e5f8afe","b529e1a572546c284f3e0b0bde4102709a872c10e7fb86b6c919e4d4fd03c7d9","83ae03444487c8b1b54529c3c4c32f223c5b50f77e50043d137a8ddc26cbe25d","6146070b6c358a4cab2e575826f27fb97fb6b88a4310659ce08f376a8ff0c43a","1ff6baa936c8013cd093057bb33c3382f4ffa1ba2eaaf95a13ffbe6beb3bd9e2","669030d21d5bdddd0b6b69ef3ec734d3cdab0f82fecf43a507cde52fbf294959","e490cc4e0cdf6a3b51329ef8fcfe69ec251eb2e43ffc06a5d55e9c1d6df6c624","e8976fd3d0e5186afe3288b865111b3d67d122f6d0458d62240f87d1540bd679","7a42cdba2feee4fd2b2eda5777ff8772deaf57366b232320d2928f9f81111f81","67e1de571ca9ae9165857a8e2682a9d120aec92c683122f30fe4f6f7f4293902",{"version":"a0b14429e5bcc2f6434cf91ea6a5b557133eccab533189c64828b07cf8106160","affectsGlobalScope":true},"527caa9124063565cd3e7f3b74c573ed8db54d3d67cd59a9577977d7f9c08ffa","0f1123ddf73ff94dfec1b00332a3d345303f53ebd44b98dfc6159dfa1f8b3719","b2af9a7d6b5a2def731667b3dc7f0ae50611ce4c165d59d772241eaab841b714","bba18394ec73302052b253117a8d21785d306519993e44cfdab888f641d20431",{"version":"817197fc90486aef8fecfa5d7d245a72c0d57eb16f09d5d166ce00acf51c0396","affectsGlobalScope":true},"e427b38c53df6980af1db47dd055b39c70dc26c32c8b757646a8e8d825e7f5c5","10efbe5cb3681540b30fc6beacf5441746efc474a4351a8a8ea0761e956e0f30","3a722edf01a953b1b8acbff6840230c9243b08632f2c9f87f23048eb072d7c05","d5acdd0ba08fbb694c9bb52b94eedbc214db3b5534beabd472c521d76bee5b77","5f52470f0cb9eb8ecb15579491fbd6de30f307fdf3ba46867c38694882780006","632dfd6a87f1443c3b82adbe3d5b2e1c1e0c3e1580af22c490874735b6215154","6fde9299b513aeecb51e4573507aae2008cd711c3737cb761262b944efb7c542","8301b85f1968ffbba44f06d59754e4698633f258afce9aca7d071494c13ea97c","1f9121597aa0c28f0fdf3227192975cc8188dee4e96f035c71abcf2be28960ee","f7bdba0b3aafff65a74dc1dda3f932e44f78bd45796742d4ddc2aff838ec51a7","03c61400806e0b8acaeacd47912e0916f66707ef7ced006192ca87378dbe0a07","7088a1ffd663e690d22017fa40174ba75cca9b069330255a7a158d424dc6d3a6","a1fa0260837849b7bb7d6f0c51728bde0bbaa06de04b006236a58ae1352013e0","8c8618a34124345e4a9e72f40b8ba8c83a2d1b0258475cf64132978ea04f2753","1cd24b96aeb692a7d416fea938645fee56b2d89e60028d058c5115e09e758f21","ba27d73b22e20d2dfe2afe32aa8d411293b647c1420cbe17abd635a5bae56a97","e01b329d9e875e1e3d74d35e442f37107233654a7765838a7d40bc06c073391f","2b7d88292907543e91080319a397f5421adfc426fd91c1cb7963738671b271a9","42616f5a1583ef1510ab126461b53edf639a4fbd4c5b924a51f3fc261ca8b675","f6d9b542c85c466bdd162fb24f75c4479ef5c7be42ecc56c6406ee3767cb8d2e","706262980b6ad7159ec0fdbeb93fe77e1a872af585b67a28836c405e700aadc1","eb182333a5a6a7019f18092ee4b5891373d857cf29d3101aa50d3ea5abcdb453","936a89bac4b3692a17021f31283c159d015e61f54aaba1b9090cb71330076b53","771f35f70060e4f3733c08b556b1f6cae278b7f1a2161b84f6b8e0b3869612c2","43cbbc9c8ede72a76d5f47a5c8d3801f1401041c93218e3ceb817ad0ff4172bb","55181c50982b8d1ed7cef464e0a950252d75514f60480e15be18e9e0a07e5656",{"version":"9632cbfc2b1d8c02d8178b37f3d90cb95ab50cc0c25e3c49918240d0b3e973e7","affectsGlobalScope":true},"da8f0510bba7dbced49284eff8c112e5c75361a610cdde84339876fdd833037a",{"version":"71be72855251ff35f793d395f5c92458cdc18ebc83e233a1030ccc6a56d7628e","affectsGlobalScope":true},"6c019d8aa21953ef0ef590267485a24e7842098708d91fc4017891de9bf328c1","6f73879760c5189d2b9e4f78a2138d7daa734fb881bdcbb96e7db55a896dd796",{"version":"418ee5b5d81f1b9281371e032d1463ef1265cdb2c34469bc282e9dc29d2b4f48","affectsGlobalScope":true},{"version":"13a1f29b2b065e893241483ac31310fc07858f1f6f405074992339cd70657592","affectsGlobalScope":true},{"version":"0378da097790cad26ef07ee82fe0fb34f81e3ee4e236b9b9e0771abe79a83d47","affectsGlobalScope":true},"d1c7e2876124c61ced32755985121d68968a7121b6a2efe960426391456df8d2","115a4d6922d7522db660509c245d197e7472c907a564162b9c0ad3e63a6ef687","3f76d6a2eb6fa7bf4618beee1e99c90ae92afe54c3aedc603c616e712311b5d2","245c226dde6efe84be4dc451dc8cc3a240cdfe46c2a9df7a04a554e45e64d1a9","806d787c708b8af00b495ade964651cf04d200890250acd95a3bb67f0cc10918","c0e4779d30b943df8d0b8626faa3e7e37053a46c04d64cc082fe445b8976c8a9","880198647a18eb31c71f1c168aac1011d7d12512eebfe1d7d5fc6b543ec7ba7f","30f1bd18c0a5086deb4ff76763b5c2d50bd8c212a839182504d86ba4d071d013","b3aba11e65d58861e4e1dc6fe533fd4af638c586a17a84754f1ae6ee377c2113","7f9a30a4b7eb59245acf8fd45d9620cf3822c3a404957eeb1eb4e10260e3c66d","7b5b853740a9f5d4ce416fe1da803ddbb076dd03f297ebc012a6d5f690a9de91","6a91e51afd339c24ea5d58885460b1173f771293de26a68b0e858b14a3af0792","0c9640c664d3687bffd99f72ff215e3abeec63c1aa7bf3943a91e7028dc6bd37","ce788dff8a0dd073cdabb6e716df901a4fb5f21de4261d9817780d9a74c67d29","c7286276c5ed2ce51557aa5b6dd50056b2a004c67a38155a4ea44e64920e6d37","54062e292923831ec0a760798fb374290426e6c82dcca20b8976079549f64822","3456f13e2faf8a06a1c91aed0334216670b694ea6ac3ccbd7b59a77c8ff1a1e3","5cb194506116b991a2a3df64af43ffbfd3a889b686903f88a38f6bbb80fd7fd1","34d6da219a9fbdf0cd002fd5c2093190afac3e81f0c855fe69f1b2aed70e890a","217d1a335dbfdbe9906cdca67de04a1648ce112828da764b1fd80ab4838a1fed","495162f178efc3bc7de5e5284582673e2adb2fa5d25b0f8c14387d96fafb9205",{"version":"78f15e75f0f6ed6b81bd179c173b4375c5c1ea43cede418e2704139253a0bfaf","affectsGlobalScope":true},"b2ee72443b3910f592fdac9a98ec5b11bec9b35f53b989e75373b78623d369db","2d27c14828a23d5d27d04a73bc39b9958e3654c79d8ddc462f8d4132a4a84105","1a6e57e0b2a854e4672f9b47be5b898ff88d99079135f82e02f74a1001b2ddaa","bd184839c4efa6e17f7f76c24a260c9d9e5a5e4e432448ea510fe7b138794329","3b5018329292ba22a9f23befe4df14eb6e83c95f0ec4c7a4a5c98df4ed8faeea","38f6b266d6a82ed1c4ec3de2d00cabc294e9c890a4561b5a23b5ad56caeaf7d6","5b07d19cf8bd6282d7f023d572d9df1a98f575753e56bbcb269cb011a7d13c9a",{"version":"794adf4a1102558f5e47acdf06930a06b0eff7d88a6f806c53bad5bbc7e32440","affectsGlobalScope":true},{"version":"789d8848146ba7feb8c33cd5f661ca750558a63942747212be95b4667f0ce225","affectsGlobalScope":true},"42fcf1eb0f8b466ace642e0ecf878719dc09cd0e6536803df0db8baac4048288","46a9eacc5a0dad53f08f3f2733eceeac196066b34bf3d2e0d62120487eceff9a","b13b6219ea0d816040a9294b3ae54e3872f73701eb888b07a5270901adaa79cf","04107a06d9a2c8ccb59dc1dfc8e103dea4bb8a986e47bc0779db95914f27e102",{"version":"254462093d987450eaf33d68d0fb669b9502dac9d5ce536ce22ecf1378b034b2","affectsGlobalScope":true},"ebc6362554b8a9f0faa1f4d57405958f7132febfd50129c601818667d0d4da06",{"version":"b645ffa41329d6b4d13e256591a2c9ab8bb3b6b4390a7f60c73244873c61a2a7","affectsGlobalScope":true},"8b81a2caad259f0dfb97a1cb80374049ce2b88c3cbb690f77bbe2e2bcb150686","7482d3f7fd8281a5bac72cc6aea80366f545c66103e01a796aefeec7918edf7e","db11b28500fcc73ba2a7bb67d76c1bffc203e22fb9c679100df19382a20c3646","d661d4c05c821f11fa810443ccc5a194f48125d964b1b29e0b8d223a2be16eb0","4a8bd9d876202ec16a14b487ecca5acf1eba1197fcbca3920064a798854c7753",{"version":"b9dcc65d3de65e78f03f680359fc09af7da038ea8b9809c566d530862709f5de","affectsGlobalScope":true},"32d4a2e6754681547c8033d34e5e112db9cfff3d5234d034c30f584dd69b46cb",{"version":"8a78b9fdf0283e21f2eafa46d495c6e5b5fb8b0beba66db03b25c513ec9d7b27","affectsGlobalScope":true},"b814a162621c6b26c8e2e16989f1969b1b985dc499597e6ee01bbc283d4ed0af","e101953453255dbdcc7fd4f45474d033a32b73232982185ea2e761a1cb89e26d","b1c610c6a933910c019dd5eab8effb726059b8ecb8123fc6a5035a342d8f23e4","e49d3fc90db8222736d97574a60dd88976a7e0ebff7ef0d6a07f905979ba9239","2c931f65f1bf91696939a1ecff577cdbb7ea014ea46af3092054d4b61d9c6fb4","c4da4f2d139d65061b268bd28a3e0ef31fe4ed18f1a57e1468a60c94fc0e67c1","c047ac006a4ed43f84fa17789484caceb3a0e7104206695837a0696c9835731e","b6f534c2e35077eecce9a9dc17149bfbcfe4c2ae263db5686cf0d6e952bbd9b5","f8529fb8104d111a46555273209885c750639a88a3347409975c44d9da00682a",{"version":"ab7af6a034be6c5f90db7798cf014031fe6e7ae40fe66fdf2c16dd2b956c4c91","affectsGlobalScope":true},{"version":"3a0bc19aa699cd926b0202c901352f607837b0cc56b1541bf8649d022954ac31","affectsGlobalScope":true},{"version":"4b8021711fd14fa5c2cf7e7adc1f17f7032f39874b6857ca4e2ffdd2794f29bb","affectsGlobalScope":true},"3183b7d595da6a04de09a59a9dcc47c8696a103f0057fad7cb6145c97458653d","121e7225a6bf54cf47eea126d58ea3d609f9e448b1d059cc96e82722c2f96689","fef3fb835fd814c98494f9b8973820ed45cc303c1a7188e39168a9594c9a59dc","b1a3ac115441d13a99c33a7ca591a77de19aaa4dd0ef05d560e91f84d0e6e01a","fe6401c76f99702d178981614334afe30f8a4242a75d5c2727ca59613de90787","e14bd2465efe1f9a7f5ca1400f332dde8935c73f7449662f25d8314f6940ab90","d4d5a3de86c36a7e2cd271f36e239d40b4893da4e2371cde78610c20407030dc","f7ea75af440b992d64d4e8a56bacd2d640544f305673ff7461c0e51e2c48f710","eac8451b53e926e31ed988f2b68c31c6f6b5bd721f39b6f4370ca3ce421bf396","84b28eecf83c13787a2466b5d4694f85b257a78af27fd32bf3913906d04e20d6","469672fcb648715c58bade2437b5be8614552908a342e17d0d6a326c31ea057a","22aa912f344d8ffb6c7723612bb0e17f403ea6c4384ed95de8fca445496bb8d4","c11c40eba7a4831b0d2d79af2ad28be4eb8f729b290ee53efaaa25ce0cd333c8","0517ac0428d267d36915f72014260db80b77030b00a95707f1c4b331be26f596","2e01dda3703d21465a64a845b4878b83e37d6ac84cf9a1f25149e193e42b621b",{"version":"6476f1945f1877aa63472962b6d71761b4f3c472eb179d1c14f07443d341562d","affectsGlobalScope":true},"8dfa8b086fe0a7aae2af0bd81ccecdb31b009bec1d804d4c2e9b1c0b8123197d",{"version":"3e08b8f051fda3665b92eace323d306b90d551fb7a7df1f489397d6a7211485e","affectsGlobalScope":true},{"version":"3d648fa39623950df430b9a01b58f63afcb47d60b11a1f29dcbfcaf08734bf3d","affectsGlobalScope":true},"2737e66a840883b195b5705a565e463802c683dec908ba10f31863a03d019e3d","062e3664245b0e453478152fb28941c3dd1db1c154afd032b3fdafb1f12f4921",{"version":"f1ed9dd3d08d2f9189522077d05681de19250c17c35ad71e7f4ae9ca11001f8b","affectsGlobalScope":true},{"version":"ae268e1642add289d4ab2463ef393df6f6e4357e85cc01048691da2e94e8d7ae","affectsGlobalScope":true},"896f8d716296890d8efe2327c12670333cc194156e4dc2a712114c8d774483c4",{"version":"7e536c56a4c2b9a3351fa8c6b5720f82b930b83fffdf973895c7afd973f92fdc","affectsGlobalScope":true},"15ab17fd3e954b3e35c8344a3bd1f3e2f752ebd5f555d6b98c9e3ec478b32987","7b710729e8b6a2e3c6dac224d036158d846790b93037167808cd18ffb874da94","df2d2b018b863230a59906fdc6c010da9cb226469f01844f58b5af560cb9c523","115a4d6922d7522db660509c245d197e7472c907a564162b9c0ad3e63a6ef687","1b581ccfdc5e774ab2e84df568a63e111443fdaf5965d1a5f1fae084cea45213","45f80fa95f85c2635e8268a5d615c69aad8ca86694ed202ac6c4e9ad8e58f8de","43362a0b967de5b0394917018162ebeb697bc098cd7a7600b5d0de3177a14b88","93ee5c4a0da24842d77cfd0689fbf8917799cdae77c3c22995d2dc6a2f79b9e8","ba13d4c56dc07360c1632b9ba7453348e2a2a0992dfe0b7673254b626e3cec4f","0390bafb2e3249b672765ce883a832d4f5308793f52154daf5183a5fb99d43c6","a68c2636a77b6a3fe844d8c7390ea57207ba19e899d46baf9a973d3b5713b870",{"version":"56fd39452b2d579e58e3f1e49f8b791ac2135ac5b6baadebb80aa4d6b0f047e8","affectsGlobalScope":true},{"version":"eb90987a186014ae9cfa8d6ff55b5579c90136fdfa29709c636e52fe5bced4a5","affectsGlobalScope":true},"0b9552b667390077ff6070d5e50cc7d53eeb807cede4678a4b42a907252d64a6","80ae221de1a4755fb8f297832fdad09f591fda17d229067776d5492cee1f326d","3ed92d889548cd59860a9363ca17cfa326c35e30e56aba92dbe3d168e8b75717","4f08f917f1776d9d51ab4b2a5b33b8fed76faf21f3e3f29037b8f16e6e5e9ccc","016c7054836ee23fab7d60b86f962ecbdb6a393414541ae5c83d2bb58a2e6168","a9f63a3949b540953d5496b12f557958920e32912ec60a8243ba4569a3b71351","e46f32e8aa8984a45071e8008f88584b1a62924feb7d0faa5e1c8fb626925155","7b199d24d0137551c8efe8179f527507529faff82c62411fae88e11cb4e5e703",{"version":"363a65daaa6d957efbb49f04c50b1137e68f1c24568221bdca14834bc0103eb8","affectsGlobalScope":true},{"version":"4525f2d827142e5e99885589e3e2af93936f83b8fbde35f6c80051e5ebaaabdb","affectsGlobalScope":true},"25120cc5b77f87056bb13b0c01a05168d6485323d5972feca20cea124a4f618f",{"version":"da0b2cf63dc9052c94cfdb14477e3f5995bb5b403c737fc8ab26a0aad7222db8","affectsGlobalScope":true},{"version":"fd45f5d7408b4ade5b812478e612b59801d371e4b8e467cf1b1aca46acd1564a","affectsGlobalScope":true},{"version":"b9241ecb5024beeaeb98fb558000dbc55e650576e572d194508f52807af6bcba","affectsGlobalScope":true},"e29267438b18703287cd3b9cd05627bec136ac5ea107bf9a5321205e0e46f203","b911176e7778c30f6549f86daae0353c53730eb0ee59b6476f1072cb51ab1af3","f8cc7ac396a3ea99a6959ddbaf883388260e035721216e5971af17db61f11f0b","895bedc6daf4f0da611480f24f65df818ea9e01404e4bf5927043dbf4eeed4d1","ea4facc7918e50e285a4419f7bc7ffdf978385899a3cf19ef7d7b782b896616d","8db893a4613484d4036337ffea6a5b675624518ad34597a8df255379802001ab","5828081db18ff2832ce9c56cc87f192bcc4df6378a03318775a40a775a824623","33b7db19877cf2f9306524371fcfc45dcb6436c8e905472ede7346c9f044bf20","b8eb76852bc6e72782541a2725580b1c3df02a0c96db570b0a7681567aeed598","6a7b38162c0cff2af6d2cbd4a98cfac6c0ea4fb1b5700c42f648de9b8c2e8e1f","19828d5df3be9b94598e5c25d783b936fcccaa226a2820bacee9ea94dc8aff2f","5d45955831c840d09b502ce6726a06435866b4736978e235a7d817ed45990df7","3bdf7ca46ef934ee671b3dd0e3d4cddcaecfe6146811b330743acdfb8e60f36c","8729ee70018ed080e16a420b8a912ff4b4ab3cbdca924b47cef6674715c10b47","efbab75b0f6371a4bf3f9e97863acffe2d76aad2ee5cf5d7666e82b2225fcd49","95f0df8e685a2c5cd1612b83d9a1937676557210d633e4a151e8670650c3b96d","e311e90ded1cd037cbece1bc6649eaa7b65f4346c94ae81ba5441a8f9df93fa3","8eb08fff3569e1b9eddb72e9541a21e9a88b0c069945e8618e9bc75074048249","d596c650714d80a93a2fe15dce31ed9a77c2f2b1b9f4540684eaf271f05e2691","8f9fb9a9d72997c334ca96106095da778555f81ac31f1d2a9534d187b94e8bf6","aea632713de6ee4a86e99873486c807d3104c2bf704acef8d9c2567d0d073301","1adb14a91196aa7104b1f3d108533771182dc7aaea5d636921bc0f812cfee5f5","8d90bb23d4e2a4708dbf507b721c1a63f3abd12d836e22e418011a5f37767665","8cb0d02bb611ea5e97884deb11d6177eb919f52703f0e8060d4f190c97bb3f6c","78880fa8d163b58c156843fda943cc029c80fac5fb769724125db8e884dce32d","7856bc6f351d5439a07d4b23950aa060ea972fd98cbc5add0ad94bfc815f4c4c","ce379fb42f8ba7812c2cb88b5a4d2d94c5c75f31c31e25d10073e38b8758bd62","9d3db8aef76e0766621b93a1144069623346b9cfccf538b67859141a9793d16d","13fb62b7b7affaf711211d4e0c57e9e29d87165561971cc55cda29e7f765c44f","8868c445f34ee81895103fd83307eadbe213cfb53bbc5cd0e7f063e4214c49b0","277990f7c3f5cbbf2abd201df1d68b0001ff6f024d75ca874d55c2c58dd6e179","a31dfa9913def0386f7b538677c519094e4db7ce12db36d4d80a89891ef1a48f","f4c0c7ee2e447f369b8768deed1e4dd40b338f7af33b6cc15c77c44ff68f572d","2f268bd768d2b35871af601db7f640c9e6a7a2364de2fd83177158e0f7b454dc","dd591496573e7e1d5ff32c4633d663c91aef86dad520568ef344ce08bba21218","a004a3b60f23fcfb36d04221b4bef155e11fd57293ba4f1c020a220fadf0fc85","4e145e72e5600a49fa27282d63bb9715b19343d8826f91be0f324af73bc25322","62f734f7517d2ca3bf02abddaf8abf7e3de258667a63e8258373658bbb9153b6","df99236666c99f3e5c22c886fc4dba8156fed038057f7f56c4c39a0c363cc66a","b4bce232891b663cc0768f737f595a83de80b74671db22b137570ef2dc6b86ef","781b566c3eccba1a2cafbb827fb6fc02d5147c89a40e11c7892057481a195270","c9befaf90879c27ee3f7f12afd15b4531fbbea9ec37d145b83807a67d9f55c82","8630f26d1038328e6b9da9c082f6fa911903bc638499baa6cfab002b5a70af96","73474d70a9b4f02771119085c4cd7562be4169e7973544c9541341ca2931aa3d","54da497c3b3b94fae91a66ed222e21411dc595a17f9e6bd229e233d0de732691","803da2f4e024efa2edc55c67d35c5240e7ae599baf9263b453acd02127a582e9","b8b070df71250096699ad55a106d161d403347ed335f72c5ae8485e5d858524d","a9716557f56781aef13d6d3c5dafc61236f64bfd48d462c4848a7eca25f924ff","3d15b5e24065431bf7831b8e84000c0e767d921135af86ef0b0c034f14df5d8f","a563202fc316d8926dc83759cec155d5c028a7828996cbd283470ac7e8c58727","e5c004f39619ebaaa2475b18e949e12e51ff629132f48d56608081e5f0195577","e6b7a14eb53f023f455f4513b6a560f004fa1ebf6cc298b479be796541e322e6","771bf8091a4e40be8f539648b5a0ff7ecba8f46e72fc16acc10466c4c1304524","cb66d1c49ad20e7246b73671f59acaaaac72c58b7e37faae69ae366fd6adf1d3","e5c1c52655dc3f8400a3406fd9da0c4888e6b28c29de33bee51f9eaeda290b4d","1e28ee6d718080b750621e18befe236487df6685b37c17958520aaf777b7aeff","8891345dbe1920b9ed3f446a87de27b5cd6b2053112f6ff3975a661f9a03ec34","a72e21b05b937630b97b1d36bb76b879bb243a021516aef10701775f2da7f872","4debe398f42800c1359d60396fc76aa4fa34a23a96b597672b5c284fd81c0158","a720d8028d38f2b94855967789252c6148957dcd24e280d193b78db00eb3a099","1b0818297187a33e2c24c39145b409e11624523d32364edc22bceaf1f4c86f1b","332e362ba8bd05237c661ba685b2c37e9cde5e0876cb81bf515d15623bdee74c","84648722d2b1f16c55cb68dbfaf18b913a13a78274641f7236eeb4d7088f6db8","f63d313c2673117608b3ed762ac07f618ee873bee3764406b06bcfcb5a713afe","2e2a2a0f7ef2a7587cfe40a96dbca31e8badb15a8a42bf042fe7a63abc9e2f27","2bb32fb3f0fe14c48170dcad3d2a501c1883516d4da9cbd0a2043d90c9789a7b","352532af4d27bdf545d9bb20f0c55758138327404bd86f0934edc7ded76be7e6","64d93f4a24f8a70b64658a7d9b9e96bd46ad498ad5dc9cdb9d52da547e77ff68","8a728de3047a1dadcb69595e74c3d75bc80a2c8165f8cf875ab610042a137fbe","3eafed0be4b194295bcde379e7d083779d0f27f31b715738a3beac49547dc613","7e74740cb7a937af187118ae4582fbe5d4d30b34e9cddec2bd7f7a865e7824ca","8cdf90b59995b9f7c728a28e7af5dc4431f08f3346e6c16af49f548461a3e0aa","1d472b3eedeeaab5418ea6563734fffc68c404feac91900633e7126bee346590","6cf7182d798892394143549a7b27ed27f7bcf1bf058535ec21cc03f39904bfb3","abe524377702be43d1600db4a5a940da5c68949e7ac034c4092851c235c38803","daf4418239ceadb20481bff0111fe102ee0f6f40daaa4ee1fdaca6d582906a26","8a5c5bc61338c6f2476eb98799459fd8c0c7a0fc20cbcd559bb016021da98111","644cf9d778fa319c8044aed7eeb05a3adb81a1a5b8372fdc9980fbdd6a61f78e","d2c6adc44948dbfdece6673941547b0454748e2846bb1bcba900ee06f782b01d","d80b7e2287ee54b23fe6698cb4e09b1dabc8e1a90fb368e301ac6fbc9ad412e2","924a87be1fd1b097c863b31f2cbc3c09eb85ec33044edde88325b028823f03e4",{"version":"7e5b8316e2977e8cc41f030cff4b7d8132c72fd8cce07d57580ab427cb3eb447","affectsGlobalScope":true},"816f825b072afd246eb3905cf51528d65e6fe51c12a1f8fb370c93bb0e031c9b","f6a64974d6fab49d27f8b31578a08662b9a7f607de3b5ec2d7c45b3466d914fd","a8e9d24cd3dc3bd95b34eb6edeac7525b7fdbe23b373554bdc3e91572b8079ee","1d5fd841722ce9aa05b9d602153c15914108bdaa8154bdd24eddadb8a3df586c","14788c10b66324b98feee7a2567eb30d1066e11506e54bf1215b369d70da4932","316785de2c0af9fbd9f2191904670e880bc3836671dd306236675515e481973a","070d805e34c4b9a7ce184aabb7da77dc60f2bdb662349cf7fc23a2a69d17de8d","092deae5b432b6b04f8b4951f1478c08862e832abd4477315dba6ea0c39f1d9e","27d668b912bf3fd0a4ddf3886a8b405eed97505fdc78a9f0b708f38e3e51655d","72654e8bed98873e19827d9a661b419dfd695dbc89fd2bb20f7609e3d16ebd50","66bdb366b92004ba3bf97df0502b68010f244174ee27f8c344d0f62cb2ac8f1e","ae41e04ff8c248ab719fe7958754e8d517add8f1c7abcc8d50214fd67c14194d","558008ff2f788e594beaa626dfcfb8d65db138f0236b2295a6140e80f7abd5d2",{"version":"6573e49f0f35a2fd56fd0bb27e8d949834b98a9298473f45e947553447dd3158","affectsGlobalScope":true},{"version":"e04ea44fae6ce4dc40d15b76c9a96c846425fff7cc11abce7a00b6b7367cbf65","affectsGlobalScope":true},{"version":"7526edb97536a6bba861f8c28f4d3ddd68ddd36b474ee6f4a4d3e7531211c25d","affectsGlobalScope":true},"3c499fc4aad3185e54006bdb0bd853f7dd780c61e805ab4a01a704fa40a3f778",{"version":"13f46aaf5530eb680aeebb990d0efc9b8be6e8de3b0e8e7e0419a4962c01ac55","affectsGlobalScope":true},"17477b7b77632178ce46a2fce7c66f4f0a117aa6ef8f4d4d92d3368c729403c9",{"version":"700d5c16f91eb843726008060aebf1a79902bd89bf6c032173ad8e59504bc7ea","affectsGlobalScope":true},"7a4182e3f8307e61eff58065c5a38eded7d9ec304969f97bef24b3cf92df6fcf",{"version":"b0b314030907c0badf21a107290223e97fe114f11d5e1deceea6f16cabd53745","affectsGlobalScope":true},"bdd74f4d3eb096bacc888670c8fde00697443b53d425ae09e8116cc54aeada91",{"version":"f659d54aa3496515d87ff35cd8205d160ca9d5a6eaf2965e69c4df2fa7270c2c","affectsGlobalScope":true},"e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",{"version":"f3e7a4075f7edc952560ec2254b453bfc8496d78e034768052347e088537694b","affectsGlobalScope":true},"8947b7adb40a06017867a5319ff04b550ddd8deea2a698b02c026e1b1c9d673f",{"version":"cc8e57cfe18cd11c3bab5157ec583cfe5d75eefefe4b9682e54b0055bf86159f","affectsGlobalScope":true},"75f6112942f6aba10b3e2de5371ec8d40a9ab9ab05c8eb8f98a7e8e9f220c8a2",{"version":"8a3b75fccc93851209da864abe53d968629fab3125981b6f47008ec63061eb39","affectsGlobalScope":true},"21eca4eb922da0be3e03c91a6095d459e907b96e896e87a4903c8de7fab81e10",{"version":"d6f55de9010fbefe991546d35da3f09ae0e47afae754cb8a4c867fd7e50dcec0","affectsGlobalScope":true},"4c9cc66b2a67160b3c16203bc1d95ebc8552d9e69c8ac33983679901342350e6",{"version":"1ce2f82236ecdd61ff4e476c96d83ce37d9f2a80601a627fe1d3048e8648f43c","affectsGlobalScope":true},"d14c44fdfbd6728a876c82346116f55799ab36fe3416a57c38592873f6ca289f",{"version":"592e99b73ae40c0e64ce44b3e28cea3d7149864f2f3cbc6ccb71f784373ade97","affectsGlobalScope":true},"6752a5cac85e950580080eb26a57d1ab780e276619a6f308d2cd034eb887aa5a",{"version":"8f8ebce0e991de85323524170fad48f0f29e473b6dd0166118e2c2c3ba52f9d6","affectsGlobalScope":true},"c627aec75d8c8b0d67e5d53bfea424c5320adba14f4bce1a3d9019172cb90e0a",{"version":"f877e78f5304ec3e183666aab8d5a1c42c3a617ff616d27e88cc6e0307641beb","affectsGlobalScope":true},"52d20eaf7b71d562ec1bce759fefbc6be2234e964a25f320313bdcd11e4c7a96",{"version":"4fc0006f46461bb20aac98aed6c0263c1836ef5e1bbf1ca268db4258ed6a965e","affectsGlobalScope":true},"bf6faf0053e821110fe22a402fb973121737d47f7a1644f9f6640fb9b2564975",{"version":"867954bf7772a2979c5c722ef216e432d0d8442e995e6018e89a159e08d5d183","affectsGlobalScope":true},"d2c363832b21d368b3339ded5da4dffb32dafd7f035f0114458637ff63336a03",{"version":"544f8c58d5e1b386997f5ae49c6a0453b10bd9c7034c5de51317c8ac8ea82e9a","affectsGlobalScope":true},"b95c6093224ea793f79007fdae1790210972edce3809b8cc5fd6687e5402e872",{"version":"ae9b62dd72bf086ccc808ba2e0d626d7d086281328fc2cf47030fd48b5eb7b16","affectsGlobalScope":true},"b03e600a48c41adfad25cda292a2bcd87963f7fce09f3561978482f9f6530fc4",{"version":"cc1bddca46e3993a368c85e6a3a37f143320b1c13e5bfe198186d7ed21205606","affectsGlobalScope":true},"34cb99d3f4d6e60c5776445e927c460158639eeb8fd480e181943e93685e1166",{"version":"c77843976650a6b19c00ed2ede800f57517b3895b2437d01efc623f576ef1473","affectsGlobalScope":true},"cdbc83f7ffd6ced2a9347d6616c41c5d30326f81902022ba8deb1ae3d4eb35ed",{"version":"5ebba285fdef0037c21fcbef6caad0e6cc9a36550a33b59f55f2d8d5746fc9b2","affectsGlobalScope":true},"85397e8169bdc706449ae59a849719349ecef1e26eef3e651a54bb2cc5ba8d65",{"version":"2b8dc33e6e5b898a5bca6ae330cd29307f718dca241f6a2789785a0ddfaa0895","affectsGlobalScope":true},"0cb3f58c4ad6c2eef5f7b40451a0281ae4cd5ab8cc3e5320fae84690ff500aa7",{"version":"dde8acfb7dd736b0d71c8657f1be28325fea52b48f8bdb7a03c700347a0e3504","affectsGlobalScope":true},"1c67f4f4abcd094bdeb01590394b11fe1b5784beafb7867327151e7ba96bcae4",{"version":"34c9c31b78d5b5ef568a565e11232decf3134f772325e7cd0e2128d0144ff1e5","affectsGlobalScope":true},"cc933b52ffb2b40c2fde19e0b625d2a603268560484401868289b7f278697c20",{"version":"60cc5b4f0a18127b33f8202d0d0fde56bc5699f4da1764b62ed770da2d5d44f1","affectsGlobalScope":true},"52ea53eb829f3974e6df31b647141373a81dcf2984999e8e0bba373959e97d1c",{"version":"d11fa2d42f762954eb4a07a0ab16b0a46aa6faf7b239f6cd1a8f5a38cb08edcd","affectsGlobalScope":true},"6a456f781a651f1448cec63a68f9d80b0be27b3f938809a091499cf4011de574",{"version":"781afd67249e2733eb65511694e19cdcdb3af496e5d8cdee0a80eba63557ff6e","affectsGlobalScope":true},"534f8e119cb864548aa2324c377ad949048598dd30c426f8da8b34e41c510405",{"version":"f3275e1f0e5852b1a50fd3669f6ad8e6e04db94693bcfb97d31851e63f8e301e","affectsGlobalScope":true},"21012c7a9eb67b1ead28ea6f96f615d6aed87408c11d7cbfc160eea4081b38ee",{"version":"8a6ecff784dafbdb121906a61009670121882523b646338196099d4f3b5761d8","affectsGlobalScope":true},"1d5f5827fdeb0d59f76a1ee6caf0804d5d3c260e60e465b0b62baea333199e62",{"version":"256bdff4c082d9f4e2303138f64c152c6bd7b9dbca3be565095b3f3d51e2ab36","affectsGlobalScope":true},"e54b9396195081999aaf2fa151809966fe298087ab8bc81e789931213be7c5ba",{"version":"e214a2a7769955cd4d4c29b74044036e4af6dca4ab9aaa2ed69286fcdf5d23b3","affectsGlobalScope":true},"b7389c085aea3ead2a5de80344332a034ca179cb5947ef59ab8a697f7c29140a",{"version":"25659b24ac2917dbfcbb61577d73077d819bd235e3e7112c76a16de8818c5fd6","affectsGlobalScope":true},"35307f141e8b2db7741387574632f3d7bf0bbb9a27602c1801fc90be4d131fc2",{"version":"7402e6ca4224d9c8cdd742afd0b656470ea6a5efe2229644418198715bb4b557","affectsGlobalScope":true},"2100b1985cd2bb2c4a0837ed6ddbd141783a4c6f01c7c3ac51c81e2235a13ba5",{"version":"242b00f3d86b322df41ed0bbea60ad286c033ac08d643b71989213403abcdf8a","affectsGlobalScope":true},"d35b5bda34cf06bc634ef85f4f7312a0bfaf8f873d59db88ea68cc525878a366",{"version":"4dc6e0aeb511a3538b6d6d13540496f06911941013643d81430075074634a375","affectsGlobalScope":true},"fda81b5f8570324354889e9761e9b00a55a60643ec0c696a8da7d9b51eba3c2e",{"version":"7ed57d9cb47c621d4ef4d4d11791fec970237884ff9ef7e806be86b2662343e8","affectsGlobalScope":true},"6762bc8285db5ec4ca014919eae07c806a6135501ebba342d43673f4ab80f75a",{"version":"5bd49ff5317b8099b386eb154d5f72eca807889a354bcee0dc23bdcd8154d224","affectsGlobalScope":true},"1d5156bc15078b5ae9a798c122c436ce40692d0b29d41b4dc5e6452119a76c0e",{"version":"bd449d8024fc6b067af5eac1e0feb830406f244b4c126f2c17e453091d4b1cb3","affectsGlobalScope":true},"e4e93a3f1680ff0725aab5f3a6ab166bd18006a9a6fbc26376d54f83474233eb",{"version":"dd5eab3bb4d13ecb8e4fdc930a58bc0dfd4825c5df8d4377524d01c7dc1380c5","affectsGlobalScope":true},"f011eacef91387abfde6dc4c363d7ffa3ce8ffc472bcbaeaba51b789f28bd1ef",{"version":"ceae66bbecbf62f0069b9514fae6da818974efb6a2d1c76ba5f1b58117c7e32e","affectsGlobalScope":true},"4101e45f397e911ce02ba7eceb8df6a8bd12bef625831e32df6af6deaf445350",{"version":"07a772cc9e01a1014a626275025b8af79535011420daa48a8b32bfe44588609c","affectsGlobalScope":true},"b5d0ad34c02203be4298ceb0e8b4b9cbc60360c9e61e44bb8e137e1c6acef3b7",{"version":"b5ba8cc21f51aa722217ae9f352104920ada8fc6247742c347ecd9b4ce2ffef1","affectsGlobalScope":true},"455d2321daecfef11d8c8239e174622538381d6cf46c87433d9df40a770535bf",{"version":"4d13cccdda804f10cecab5e99408e4108f5db47c2ad85845c838b8c0d4552e13","affectsGlobalScope":true},"c10947d77f28d0fe34224e8f7e1214a0bba856c9eaf4db1b4830f071fedb4d9a",{"version":"7ced457d6288fcb2fa3b64ddcaba92dbe7c539cc494ad303f64fc0a2ab72157d","affectsGlobalScope":true},"8f9e44dc3ce7b4d808f34db76f28c8d67fa6d7a0579bec6bf09db3537a3588f1",{"version":"e43efe2e9817e572702de60bb11a60c1af4243b7304f0eb767b96a7a0760f7af","affectsGlobalScope":true},"c04859b7e76b1abbc7ecc5c1c16c855b8b526e337a7982c8d13c397804386d4c",{"version":"725128203f84341790bab6555e2c343db6e1108161f69d7650a96b141a3153be","affectsGlobalScope":true},"c7cc27f7342962767a1794e7b6a2194cebeb6821c26d4a9b0b910d33216071f8",{"version":"947bf6ad14731368d6d6c25d87a9858e7437a183a99f1b67a8f1850f41f8cedd","affectsGlobalScope":true},"8eda6e4644c03f941c57061e33cef31cfde1503caadb095d0eb60704f573adee",{"version":"0538a53133eebb69d3007755def262464317adcf2ce95f1648482a0550ffc854","affectsGlobalScope":true},"4f4cac2852bf2884ab3b2a565022db3373d7ef8b81eb3484295707fbd2363e37",{"version":"7a204f04caa4d1dff5d7afbfb3fcbbe4a2eb6b254f4cd1e3bdcfe96bb3399c0b","affectsGlobalScope":true},"4a5259be4d6c85a4cd49745fb1d29d510a4a855e84261ad77d0df8585808292c",{"version":"220f860f55d18691bedf54ba7df667e0f1a7f0eed11485622111478b0ab46517","affectsGlobalScope":true},"3bee701deb7e118ea775daf8355be548d8b87ddf705fe575120a14dcace0468a",{"version":"9c473a989218576ad80b55ea7f75c6a265e20b67872a04acb9fb347a0c48b1a0","affectsGlobalScope":true},"bf7fc4f1fa20f81f3a8467bcbed0b74983d41b2616e6e4ab61587fa842979d28",{"version":"20b41a2f0d37e930d7b52095422bea2090ab08f9b8fcdce269518fd9f8c59a21","affectsGlobalScope":true},"dbac1f0434cde478156c9cbf705a28efca34759c45e618af88eff368dd09721d",{"version":"0f864a43fa6819d8659e94d861cecf2317b43a35af2a344bd552bb3407d7f7ec","affectsGlobalScope":true},"855391e91f3f1d3e5ff0677dbd7354861f33a264dc9bcd6814be9eec3c75dc96",{"version":"ebb2f05e6d17d9c9aa635e2befe083da4be0b8a62e47e7cc7992c20055fac4f0","affectsGlobalScope":true},"aee945b0aace269d555904ab638d1e6c377ce2ad35ab1b6a82f481a26ef84330",{"version":"9fb8ef1b9085ff4d56739d826dc889a75d1fefa08f6081f360bff66ac8dd6c8d","affectsGlobalScope":true},"d9d44786804e9bf2bddcc62adf7384f0a92f27bac091de5098c689e685bbe17e",{"version":"e1425c8355feaaca104f9d816dce78025aa46b81945726fb398b97530eee6b71","affectsGlobalScope":true},"eae663da2201b45295aa8e88a326cab843f490bda1b3b9b12cc91d25f2b62778",{"version":"42c6b2370c371581bfa91568611dae8d640c5d64939a460c99d311a918729332","affectsGlobalScope":true},"590155b280f2902ebb42a991e9f4817ddf6558e5eb197deb3a693f5e0fc79bd9",{"version":"867b000c7a948de02761982c138124ad05344d5f8cb5a7bf087e45f60ff38e7c","affectsGlobalScope":true},"22f681c95782179fcc779ee940f4f810048fb3ce60c089fa3903c13b3e092f95",{"version":"02c22afdab9f51039e120327499536ac95e56803ceb6db68e55ad8751d25f599","affectsGlobalScope":true},"e9e9e16cad091365ef4ac67945713cade5b1fece819f69df074bf8b8623f8b78",{"version":"37129ad43dd9666177894b0f3ce63bba752dc3577a916aa7fe2baa105f863de3","affectsGlobalScope":true},"01364e0e44e63be62244368f1e6f9a340e95c662ebb81f6875e676f969cc52bc",{"version":"31f709dc6793c847f5768128e46c00813c8270f7efdb2a67b19edceb0d11f353","affectsGlobalScope":true},"6c04df817a89fd711e8c84f0fe888706aab8735dbe7f2533e200afbec2ee495f",{"version":"018847821d07559c56b0709a12e6ffaa0d93170e73c60ee9f108211d8a71ec97","affectsGlobalScope":true},"17dd17a89a9fac4f0a0de8f40af8bc9aab9707111e445e52ae05bfe774ac7bd8",{"version":"7832e8fe1841bee70f9a5c04943c5af1b1d4040ac6ff43472aeb1d43c692a957","affectsGlobalScope":true},"e4b23a4b3f0a4929ec2a4cea441e07df881f9bdae6a9fc027eb2e602518f65f1",{"version":"013853836ed002be194bc921b75e49246d15c44f72e9409273d4f78f2053fc8f","affectsGlobalScope":true},"0e9a7364eaf09801cbb8cf0118441d5f7f011fc0060c60191587526c448974c4",{"version":"e08392a815b5a4a729d5f8628e3ed0d2402f83ed76b20c1bf551d454f59d3d16","affectsGlobalScope":true},"047f4e7ce8c15a34e6f5ed72a7c4c675d56e58c0e15220c54b9c9b182a3a888f",{"version":"5768572c8e94e5e604730716ac9ffe4e6abecbc6720930f067f5b799538f7991","affectsGlobalScope":true},"087b18cc2f9aa5a02201a9b47691f4ca91dc7b5f7b26587d05f576435a71df5f",{"version":"a66b1e872740efbfde3bc205646e623b5daebd60c493222614c083c3ffd1aec1","affectsGlobalScope":true},"d0984177c1dc95545541f477fb0df1fb76e7454a943c98ed208dc0da2ff096b2",{"version":"f366ca25885ab7c99fc71a54843420be31df1469f8556c37d24f72e4037cb601","affectsGlobalScope":true},"a05b412a93ba43d2d6e9c81718dea87a42c7e4f9e8b1efbaafee03a94eaf4b7a",{"version":"163cc945edad3584b23de3879dbad7b538d4de3a6c51cc28ae4115caee70ce21","affectsGlobalScope":true},"916e25422aad85365d2d98e9176bfdae7eee59ae8d7036d79610c305fe3322d0",{"version":"d604893d4e88daade0087033797bbafc2916c66a6908da92e37c67f0bad608db","affectsGlobalScope":true},"1756a8d31627b1a7eea08ae74ab348c3b9b311a7b86683583c73a09f30a2bb75",{"version":"dc265f24d2ddad98f081eb76d1a25acfb29e18f569899b75f40b99865a5d9e3b","affectsGlobalScope":true},"26a2700863203c2c0bf1dbab144d182b4608db68c11c38b692110e5dc19de8b0",{"version":"8c139b169259645bc50a1d0fb860837434c7c5933f891fd44266eb6dd35da072","affectsGlobalScope":true},"46faa2ce0d71cf2e0cac1dd1aa277988504715ce9dd89fba0fd5ae1b7036377c",{"version":"41ffc155348dd4993bc58ee901923f5ade9f44bc3b4d5da14012a8ded17c0edd","affectsGlobalScope":true},"a2d9f3ffc5a3fc79e9bb0d5635ce409e830478df392c4233eef1f1b3d85535cd",{"version":"3e8e0655ed5a570a77ea9c46df87eeca341eed30a19d111070cf6b55512694e8","affectsGlobalScope":true},"f04e8e078f6555aa519de47b8f2b51e7b37f63265f99328f450ee0fe74c12b97","9fdb680426991c1c59b101c7f006e4963247c2a91b2750f48e63f9f6278a772c",{"version":"cc4c74d1c56e83aa22e2933bfabd9b0f9222aadc4b939c11f330c1ed6d6a52ca","affectsGlobalScope":true},"b0672e739a3d2875447236285ec9b3693a85f19d2f5017529e3692a3b158803d",{"version":"8a2e0eab2b49688f0a67d4da942f8fd4c208776631ba3f583f1b2de9dfebbe6c","affectsGlobalScope":true},"ed807fdf710a88e953d410b7971cad71aae21c0aff856657960e09ded50b5775",{"version":"f6266ada92f0c4e677eb3fbf88039a8779327370f499690bf9720d6f7ad5f199","affectsGlobalScope":true},"c03bcada0b059d1f0e83cabf6e8ca6ba0bfe3dece1641e9f80b29b8f6c9bcede",{"version":"f2eac49e9caa2240956e525024bf37132eae37ac50e66f6c9f3d6294a54c654c","affectsGlobalScope":true},"ace629691abf97429c0afef8112cc0c070189ff2d12caee88e8913bdd2aaad25",{"version":"99a71914dd3eb5d2f037f80c3e13ba3caff0c3247d89a3f61a7493663c41b7ea","affectsGlobalScope":true},"25a12a35aeee9c92a4d7516c6197037fc98eee0c7f1d4c53ef8180ffc82cb476",{"version":"b4646ac5ca017c2bb22a1120b4506855f1cef649979bf5a25edbead95a8ea866","affectsGlobalScope":true},"54d94aeec7e46e1dab62270c203f7907ca62e4aaa48c6cdcfed81d0cd4da08f3",{"version":"f9585ff1e49e800c03414267219537635369fe9d0886a84b88a905d4bcfff998","affectsGlobalScope":true},"03181d99adbd00cb0b1bab6387829cebf635a0fe3f7461d094310effd54ca7af","f280aeceb876ec38168b19809629cbffb3f7a26ac1ef326b64294a307c57261b",{"version":"1ff9449d1efdebef55b0ba13fe7f04b697c264e73ec05f41f7633dd057468b2d","affectsGlobalScope":true},"275093c8de5268c39e47072f6b4892e11358729eebd3c11f884060a248e30d93",{"version":"7c160037704eee2460c7de4a60f3379da37180db9a196071290137286542b956","affectsGlobalScope":true},"78c8b42462fba315c6537cf728f8d67ad8e1270868e6c0f289dd80677f1fa2e9",{"version":"4681d15a4d7642278bf103db7cd45cc5fe0e8bde5ea0d2be4d5948186a9f4851","affectsGlobalScope":true},"91eb719bcc811a5fb6af041cb0364ac0993591b5bf2f45580b4bb55ddfec41e2","05d7cf6a50e4262ca228218029301e1cdc4770633440293e06a822cb3b0ef923",{"version":"78402a74c2c1fc42b4d1ffbad45f2041327af5929222a264c44be2e23f26b76a","affectsGlobalScope":true},"cc93c43bc9895982441107582b3ecf8ab24a51d624c844a8c7333d2590c929e2",{"version":"c5d44fe7fb9b8f715327414c83fa0d335f703d3fe9f1045a047141bfd113caec","affectsGlobalScope":true},"f8b42b35100812c99430f7b8ce848cb630c33e35cc10db082e85c808c1757554",{"version":"ba28f83668cca1ad073188b0c2d86843f9e34f24c5279f2f7ba182ff051370a4","affectsGlobalScope":true},"349b276c58b9442936b049d5495e087aef7573ad9923d74c4fbb5690c2f42a2e",{"version":"ad8c67f8ddd4c3fcd5f3d90c3612f02b3e9479acafab240b651369292bb2b87a","affectsGlobalScope":true},"1954f24747d14471a5b42bd2ad022c563813a45a7d40ba172fc2e89f465503e2",{"version":"05bbb3d4f0f6ca8774de1a1cc8ba1267fffcc0dd4e9fc3c3478ee2f05824d75d","affectsGlobalScope":true},"52cd63ca2640be169c043b352573f2990b28ba028bae123a88970dd9b8404dc9",{"version":"154145d73e775ab80176a196c8da84bfc3827e177b9f4c74ddfac9c075b5b454","affectsGlobalScope":true},"89d80fcd9316e1cfad0b51c524a01da25f31dfcf669a4a558be0eb4c4d035c34",{"version":"177f63e11e00775d040f45f8847afdb578b1cac7ab3410a29afe9b8be07720f0","affectsGlobalScope":true},"37e69b0edd29cbe19be0685d44b180f7baf0bd74239f9ac42940f8a73f267e36",{"version":"afba2e7ffca47f1d37670963b0481eb35983a6e7d043c321b3cfa2723cab93c9","affectsGlobalScope":true},"bb146d5c2867f91eea113d7c91579da67d7d1e7e03eb48261fdbb0dfb0c04d36",{"version":"90b95d16bd0207bb5f6fedf65e5f6dba5a11910ce5b9ffc3955a902e5a8a8bd5","affectsGlobalScope":true},"3698fee6ae409b528a07581f542d5d69e588892f577e9ccdb32a4101e816e435",{"version":"26fc7c5e17d3bcc56ed060c8fb46c6afde9bc8b9dbf24f1c6bdfecca2228dac8","affectsGlobalScope":true},"46fd8192176411dac41055bdb1fdad11cfe58cdce62ccd68acff09391028d23f",{"version":"22791df15401d21a4d62fc958f3683e5edc9b5b727530c5475b766b363d87452","affectsGlobalScope":true},"b152da720b9df12994b65390bb47bbb1d7682a3b240a30f416b59c8fc6bc4e94","cefffd616954d7b8f99cba34f7b28e832a1712b4e05ac568812345d9ce779540",{"version":"a365952b62dfc98d143e8b12f6dcc848588c4a3a98a0ae5bf17cbd49ceb39791","affectsGlobalScope":true},"af0b1194c18e39526067d571da465fea6db530bca633d7f4b105c3953c7ee807",{"version":"b58e47c6ff296797df7cec7d3f64adef335e969e91d5643a427bf922218ce4ca","affectsGlobalScope":true},"76cbd2a57dc22777438abd25e19005b0c04e4c070adca8bbc54b2e0d038b9e79","4aaf6fd05956c617cc5083b7636da3c559e1062b1cadba1055882e037f57e94c","171ad16fb81daf3fd71d8637a9a1db19b8e97107922e8446d9b37e2fafd3d500",{"version":"d4ce8dfc241ebea15e02f240290653075986daf19cf176c3ce8393911773ac1b","affectsGlobalScope":true},{"version":"52cd0384675a9fa39b785398b899e825b4d8ef0baff718ec2dd331b686e56814","affectsGlobalScope":true},{"version":"2eea0af6c75c00b1e8f9745455888e19302cbeeadde0215b53335ca721110b6a","affectsGlobalScope":true},{"version":"64f9b52124ff239ae01e9bdf31fd8f445603e58015f2712c851ee86edf53de2f","affectsGlobalScope":true},{"version":"769c459185e07f5b15c8d6ebc0e4fec7e7b584fd5c281f81324f79dd7a06e69c","affectsGlobalScope":true},{"version":"c947df743f2fd638bd995252d7883b54bfef0dbad641f085cc0223705dfd190e","affectsGlobalScope":true},"db78f3b8c08924f96c472319f34b5773daa85ff79faa217865dafef15ea57ffb","8ae46c432d6a66b15bce817f02d26231cf6e75d9690ae55e6a85278eb8242d21","293fd9de252226e1a22a1fc6f10b9fc31e76c068deed3ee44423b9c9d500adac","7e3b90edc53b175aaa02342867cbe38d436fa2fee2beaa8ddc2764beda383076","ba846f204e8f43eb15d8cd004290ac6969fc8c2775d5409c3dd659f8d0af840a","afed96028b1e72b00079757225d1b2a756c2bfd2872a3fe1fef87aeb4b253db4",{"version":"9aa9daaf59acf4036d5dd7865311471adb5bfda049ee96905111677666b7bb3a","affectsGlobalScope":true},"ff5a16ce08431fae07230367d151e3c92aa6899bc9a05669492a51666f11ceb5","526904beb2843034196e50156b58a5001ba5b87c5bb4e7ec04f539e6819f204e","602ea333af6cfcdc72f0985c8acdf3a67764949fc726788bf1fab77faeb2ee92","bdfb17c9f096b8af12c3487f54f80f8f57b7a75016245b8c5c8aea8085cf46c4","21c80bf05f7aca35d89be1682210a5c47c76a9981ce24902704e900d15d9568d","b491739c41ea6e732c828fcb091228e7915bb624632677db6f7898a5c823f19c","b343bc823ac319bc8315ba4a778a4eedca39456fac07d2a17003946fe8426f91","3cced7d4e05434c1ff1cfe03e4afcc6f9a017cfdd49ac498d5e69228a94ccf85","9909399eee275dde0aa21795154ae59a527f69e54935e2149fdf6c3a93b0099a","a10ea35c9b53af350a984c82b42fbb2fb0968f401474ca9929dabf75b8f4a8f0","13892a291557bd6e7a5c36aaa153838562e8341612bc32c938393bf126ffe029","43693dd218d6e16927c03525418b0d189a3fe89baddd39a5e48ed62d2b6b5b6d","ef0bd685f0f544daa62da30d4c3caec58a649a05dc0820ca3ba89a5a223715c2","e773b5c356a9ee2b89f117eceea5a37605bde8332b1c3be0f9e5cfa77a94d44e","4832b45760a9da0450afbf680c1a2e4ed822d4a58c4671ef3a519200115eb385","fae67be8c932d280bf35c1688d432f19b4a06df0f4f8aee5e8b38c9cf12176d0","2c89002fd9d62fd2a2b5064de15138bfd5f98272638f9cd17eb32d0d8d90d985","d40142a12db909fab26b650acd4dc0e02b25a78a2ed6deca8b02181d71bea2c7","1660987e5b97ce43a306b1435597ab0af5e7f591779e72fa63228b3cd3027299","aaac2660f552141f1d563bff7426bed2a2a2bd89bd21ad2eb52541e102032992","487d3050411036efb04a593144b895b171d6778f717a9ba1550351f4f7ef04b2","a43cb0714d897c5aada3bbf8857232afa1247a8a30a318fee329483ede52d3e8","33e031bef80897b7c16a8e6ef0b6eb49054541e52cf63226ca4ea4b96c11ac00","36f36406ef67f9e365277b98d3f49d1b5a30073711cb693de44c32cc663bcdc1","a492550daaa01d5e22204e9c5e9174093eb9057c018f21b14dc88d82bd46c7c4","03513294d9760a0dc55f4a4cd59501b373ffaeb35819d0c3660e2cafe15fbb32","5bb3c84a979c101e71440aa06a320cd6dd38696508cd807a41c70fcc991ad8b8","a06338d61ea9d3d2937288688a4f8782c12b65708e08b57a623a44b9a0b4093d","6a35bbeec426b686897094193136ea6ddd9c8a1c3aca046835a8115d377885a7","f3f9c035ab3a016446574fa3642e2e1078bdb5e38c0cdb1c27efd4d1894870b1","473956ae54483591b18aab5a7b9aff5f7421ebb3f62917a828fc67de9c12affe","4e3b9dc1e673017353f76c6d728cbaebadfa7491654ee4b58fa2106b09e56e26","1ca9d725d6c2e0c593d5b362c337e35332fee5a0e4404ad0d9ff425cd5fee87f","32466f96ad3fbccf2c303abef85925abc446ee41ecd94f8bd3b4a6ac2dc74c78","a2031250f891ed261cd1fa2c7d6b89588294337c8870753536b8d794e061aeb0","dcb365dcc3030197225ce8c787ae2ab9b467cb013efc1add6661f3b753e1b1c9","698638535d67033ebf9109591166a4fe2450188fbe48244af039da29d227e260","ff2b9645aea76628f48bde91951df8686ac1cea6dfbd217b3d83ed012b0c50c3","18922dab338cae8ccf97aa6d2b4893370b9dddeaa80fa980f19c1e34d1ebb715","4e6f09d72051ab5241824a91cc351e89df72b68937edeb277276d15e0fc04c68","053bf789c8418fdf882e4bee834abe790883070dc2de61e8244252e845d3fb46","d977d10b470cccc2119d315163f4af1b8c2a42ecc0db36d2f38ba293de3115fa","57143e7e8e6942a22c7e7e2e2f5f54404f9e335ef9ca59ad175099824cb44b9a","2d5d8eb8b3b6e2536f00339d19f1fe40b5418a7cca171a632aee86c044539617","6e51934f64efb14af2ea7a910d5136a19534cb24724ec02da729db002ffc7195","76f2bd7c5ecfc3f35bc0e542a6e00ecad9d8a9ede38b70eec68a0fb9a47aa1d5","e0b07cc0d9f2875240804c9d692ed154c7b170775c547bf0928e1f7db9fd7a87","cf2eb57062061163731cad59e701e0478418eb96d3c2020c6b97978e1fef74bd","2ef86e1cc570517baa0a30dbed83c2d27296ce79801e5245aa48b1989d2395c2","41eb65fee79e641006603668cd3f9d87995b53c45cf4b0f12f8c97b5b0669f7f","39e792ffdc58142bbe711d30781da7841d542ba2d2c44ce79bc7d78c4f26ce28","2d2d9131fbfddedbac9122e92c034869f7c698a3311cf134affdec0f5b5af008","ba665abc1932fad4cbbb1e06dee5f0ee34881740bc97e7f66e2f2fb07ca27e45","e48145eafa783f930e9ef7d687d070c7eb993d1549faf6ba979c491c0f798d39","6ab54adc3ed772c9665fb0f17404f8dc107a5ce1eaef193c42e8c11b390d27e2","5a3455d13f86d07001a41bdfc3b758860ebe17a6e9533ec3127a1c0381f6842a","e46cd8132216567b3c6cc497ea07522e1222eb3f9484b758a65ee0852e582b44","7b057d10c9bfab5d6a0def9b2910189a7220ab7331c413caf4c99897fce63f5d","88fc304f89cd236b4da5da0ad31592b8fb976358e22162229508b29a18872094","d8b3fb1b45a3abde4f9e053986d4e998a1c57d0e8ca2f824be8f1ce02512004c","473ceb2c9fba3564e94ed02125f3e0b58425d584fda7ae384c743520676d6cac","56efe5c550ecc09de2fbfdd95377864113249a38acb5eebc4cd867d281938143","8c737d9a92a1bda19b3c083cda2acf002835d16049bbd6659d2a39eac8792047","032e571a9e69afd1b505de958bf94b1cc657bb728fa27f3003a9679418d4b8d7","d78e12a8ffedaf77d9c70e83325da315de7a93873ba653ebc0b7d23d2936b937","73d47f0145c8030b6a6094d565d4380081e1d189371e58a3e9673c29eb63dfff"],"root":[1328,1332,1333,1399],"options":{"inlineSources":true,"module":99,"noEmitOnError":false,"noImplicitAny":false,"noImplicitThis":true,"outDir":"../../../../dist/dev/.uvue/app-android","rootDir":"../../../../dist/dev/.tsc/app-android","skipLibCheck":true,"sourceMap":true,"strict":true,"target":99,"tsBuildInfoFile":"./.tsbuildInfo","useDefineForClassFields":false},"fileIdsList":[[46,48,50,1322,1323,1324],[1107,1121,1318,1321,1323,1324,1325,1326],[1034,1040],[1106],[1027,1028,1029,1030,1031,1032,1033,1034,1035,1036,1037,1038,1039,1040,1041,1042,1043,1044,1045,1046,1047,1048,1049,1050,1051,1052,1053,1054,1055,1056,1057,1058,1059,1060,1061,1062,1063,1064,1065,1066,1067,1068,1069,1070,1071,1072,1073,1074,1075,1076,1077,1078,1079,1080,1081,1082,1083,1084,1085,1086,1087,1088,1089,1090,1091,1092,1093,1094,1095,1096,1097,1098,1099,1100,1101,1102,1103,1104,1105],[1029,1030,1031,1032,1033,1035,1037,1039,1041],[1079],[1040,1044],[1081],[1100],[1036],[1041],[1035,1040,1051],[1040,1049],[1029,1030,1031,1032,1033,1037,1040,1041,1049,1050],[1080],[1040],[1049,1050,1051,1096],[1033,1041,1082,1085],[1028,1033,1038,1042,1049,1077,1078,1082,1083],[1038,1040],[1084],[1042],[1032,1040],[1040,1041],[1040,1051],[1040,1049,1050,1051],[1044],[46,48,50,1039,1322,1323],[1320],[1319],[1122,1123,1268,1283,1290,1313,1315,1317],[1316],[1314],[1125,1127,1129,1131,1133,1135,1137,1139,1141,1143,1145,1147,1149,1151,1153,1155,1157,1159,1161,1163,1165,1167,1169,1171,1173,1175,1177,1179,1181,1183,1185,1187,1189,1191,1193,1195,1197,1199,1201,1203,1205,1207,1209,1211,1213,1215,1217,1219,1221,1223,1225,1227,1229,1231,1233,1235,1237,1239,1241,1243,1245,1247,1249,1251,1253,1255,1257,1259,1261,1263,1265,1267],[1124],[1126],[1128],[1130],[1134],[1136],[1138],[1140],[1142],[1144],[1146],[1148],[1150],[1152],[1154],[1156],[1158],[1160],[1162],[1164],[1166],[1168],[1170],[1172],[1174],[1176],[1178],[1180],[1182],[1184],[1186],[1188],[1190],[1192],[1194],[1196],[1198],[1200],[1202],[1204],[1206],[1208],[1210],[1212],[1214],[1216],[1218],[1220],[1222],[1224],[1226],[1228],[1230],[1232],[1234],[1236],[1238],[1240],[1242],[1244],[1246],[1248],[1250],[1252],[1254],[1256],[1258],[1260],[1262],[1264],[1266],[1270,1272,1274,1276,1278,1280,1282],[1269],[1271],[1273],[1275],[1277],[1279],[1281],[1285,1287,1289],[1284],[640,914],[1286],[1288],[1292,1294,1296,1298,1300,1302,1304,1306,1308,1310,1312],[1311],[1299],[1295],[1293],[1309],[1301],[1297],[1303],[1305],[1291],[1307],[1044,1051],[1120],[1108,1109,1110,1111,1112,1113,1114,1115,1116,1117,1118,1119],[1051],[1044,1051,1104],[51,1022,1023,1024,1025],[1021],[914],[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],[1334],[46,48,50,1323,1324],[44],[44,45,46,48],[41,48,49,50],[42],[41,46,48,1323,1324],[45,46,47,50,1323,1324],[29,30,31,32,33,34,35,36,37,38,39],[33],[36],[33,35],[54,466,483,484,486],[54,130,218,466,709,714,715],[466,716],[230,466,709,713,716,737,818],[466,717,737,818],[54,130,466,716],[466],[200,466,665,818,914,1000,1004,1005,1006,1007,1009],[466,547,691,692,914],[54,200,466,665,818],[466,995,1006],[54,77,156,200,230,428,451,466,467,468,472,476,480,533,547,640,650,658,662,665,671,689,691,694,695,698,721,725,747,776,812,818,837,850,851,863,876,913,914,915,920,922,923,925,926,927,930,932,934,937,942,943,944,947,948,949,951,953,958,961,980,982,983,991,992,996,997,998,999,1003,1010,1011,1020],[466,658,850,851,946,948,952],[466,480,1021],[466,480,483,484,486,671,860,863],[54,200,451,466,472,480,547,658,659,694,695,716,737,747,818,851,863,876,914,920,922,925,941,951,982,985,986,991,1021],[284,466,519],[466,483,485,486],[230,451,466,472,480,984,986,992,993,994,995],[200,466],[466,480,818,914,992,996],[156,200,466,818,992],[451,466,472,480,989,990],[54,466,480,989],[54,466,480,483,484,486,504,863,875,876,914,935,936],[284,466,538],[466,480,863,937],[54,200,230,466,483,484,486,545,959,960],[54,200,451,466,483,484,486,830,937],[146,230,466,486,585,603,818,914,950],[466,480,863,914,915,937,1021],[156,428,466,1012,1013,1014,1015,1016,1017,1019],[466,480,1012,1013],[466,480,1012],[466,480,1012,1013,1018],[200,466,480,483,484,486],[200,466,483,484,486],[466,914,1021],[212,288,466,843,914,1341,1342,1352,1353,1354,1367,1373],[466,1352],[54,466,483,484,486,1349,1350],[466,1348],[54,466,483,484,486,504,843,914,1339,1340,1343,1347,1351],[230,466,843,1342,1352],[466,1343,1345,1346],[87,153,230,466,483,484,486,843,1344,1346],[466,483,484,486,843,1345],[230,466,843,1342,1344,1345,1352],[466,1344,1345,1346,1352],[230,466,483,484,486,843,1345],[230,466,914,1352,1374,1375,1376],[230,466,1341,1352],[466,1342],[65,466,1339],[65,67,68,466,1352],[466,1356],[54,146,230,466,478,483,484,486,1361],[466,1340,1360,1362],[466,483,484,486,1355],[466,1359,1362],[466,1363],[466,483,484,486,1365],[466,1366],[466,504,1356,1357,1359,1362,1364,1366],[230,466,937,1369,1372],[466,483,484,486,1358],[466,1359],[230,466,1371],[146,230,466,478,1340],[54,466,483,484,486,1352,1370],[466,483,484,486,1368],[466,1369],[54,230,466,483,484,486],[54,466,483,484,486,914],[466,473,480,863,909,914],[466,480],[200,466,483,484,486,671,724,828,859,863],[200,466,671,827,863,914],[200,466,476,483,484,486],[466,658],[466,850],[54,62,130,466,483,484,486,914],[54,218,451,466,472,480,578,581,658,671,776,837,841,847,848,849,851,854,914],[54,466,480,578,671],[64,218,466,480,578,581,671,776,837,838,854,855],[153,283,466,480,483,484,486,671],[54,67,68,218,229,230,466,479,480,578,581,640,671,776,831,832,833,835,837,838,839,840,854,855,856,858,914],[200,466,830],[54,87,115,150,153,212,466,477,483,484,486,852,853],[54,68,119,200,229,230,245,428,449,466,480,503,504,534,547,579,580,582,640,658,659,660,661,662,665,671,773,844,849,850,859,863,875,876,881,896,901,902,907,908,910,913,915],[466,849],[54,68,119,229,230,245,428,449,466,480,503,504,534,579,580,582,640,658,659,662,665,671,773,844,849,850,859,863,875,876,881,896,901,902,907,908,910,913,914,915,945],[54,58,130,200,212,218,245,466,480,483,484,486,545,547,659,669,671,859,860,862,896,914,915],[466,483,484,486,914],[78,177,212,466,483,484,486,502,671,846,859,863,879,880],[54,466,671],[466,538],[54,466,483,484,486,504,863,873,874,875,914],[466,480,863,876],[54,451,466,472,914,987,988],[466,989],[54,466,989],[54,466,483,484,486,652],[212,466,483,484,486,502,845,861],[200,212,466,483,484,486,502,666,842,843,896,914],[54,127,466,844,896],[466,483,484,486],[230,466,483,484,486],[466,483,666,844],[466,483,484,486,865],[466,483,484,486,871],[466,483,484,486,666],[54,200,466,483,484,486],[466,483,484,486,667,844,848,862,864,865,866,867,868,869,870,871],[77,200,230,428,466,504,640,668,876,886,887,889,890,891,892,893],[54,466,483,484,486,885],[466,886],[200,466,483,484,486,589,640,888],[200,466,589,640,889],[65,67,68,230,428,466,476,540,876,889],[200,466,483,484,486,640,671,863,875],[200,212,466,483,484,486,640,671],[200,466,480,483,546,548,665,896],[54,127,466,666,896],[77,200,212,230,428,466,480,535,536,537,539,540,541,542,543,545,548,658,659,665,667,668,844,848,862,863,865,867,868,872,875,876,877,878,881,882,884,894,895,915],[466,483,484,486,915],[230,466],[466,483,484,846],[200,466,483,484,486,666,896],[466,483,484,486,502,845,846,847],[200,466,483,484,486,502,665,848,862,868,881,883,896],[54,127,466,884,896],[466,483,484,486,502,845],[466,483,484,486,870],[65,466,472,480,483,484,486,578,579,580],[64,68,466,548,581],[466,483,484,486,659,662],[54,62,266,466,483,484,486,590],[466,581],[230,466,655],[64,65,466,578,653,654,914],[54,68,200,466,480,547,548,581,582,618,619,629,651,656,657,658,660,661,665],[284,404,466],[659,661,665],[64,200,466,618,657,659,660,665],[64,466,547],[466,473,915],[146,212,466,911,912],[212,466],[466,913],[466,483,486,839],[466,483,484,486,857],[466,480,839,858],[229,466,504,671],[65,230,466,480,671,834,835,836,859],[466,907],[65,466],[466,837,901],[54,146,172,174,230,266,449,466,776,837,854,898,901,902,904,905,906],[466,837,897,900,907],[466,901,902,903],[466,901,902,904],[466,898],[466,899],[466,578,899],[67,252,466,483,484,486,492,603,612,623,627,628,629,630,638,639,650],[466,628,638,640],[466,606,607,640],[200,466,545,585,603,604,610,612,613,620,621,622,624,625,630,640,641,643,648,649],[54,466],[54,466,631,632,633,634,635,637],[466,632,638],[54,160,466,636,638],[68,156,466,544,545,547,549,608,610,626,642,643,650,657,659,660,662,663,664],[156,466,665],[466,659,662,665],[466,483,484,486,494,504,610,640,643,660,665,671,829,914],[466,665],[54,260,449,466,585,590,591,612],[466,613,614],[466,613,615],[466,483,484,486,640],[54,466,483,484,486,545],[54,451,466,585,602],[252,257,466,585,623],[68,466,612,650],[466,545,585,612,626,640,650],[466,545,604],[200,266,466,545,590,591,592,593,594,595,596,604,605,607,608,609,610,611,618],[200,208,230,267,270,278,336,337,338,443,466,585,597,598,599,600,601,603],[466,650],[200,466,545,585,603,604,610,612,613,621,622,624,630,640,641,643,648,650],[54,466,483,484,486,544],[54,466,483,484,486,545,604,625],[466,545,606,607,608,610,640,646],[466,545,603,612,642,644,647],[466,607,623,645],[466,603,606],[466,504,781,782],[466,783],[284,466],[466,545,594],[54,449,466,582,584,617],[449,466,472,582,583,618],[466,615,616,618],[64,466,483,484,486],[230,466,511,513,516],[64,466,515],[146,230,466,514],[466,511,513,515],[466,483,484,486,512],[466,513],[414,466,488],[466,488],[466,488,508],[230,466,488,489,490,491,492,504,505,507,509],[64,288,466,483,484,486],[466,506],[54,58,62,78,212,229,266,466,586,587,588],[466,589],[54,200,466,480,483,484,486,640,671,970],[200,466,480,640,671,971],[54,200,212,466,483,484,486,640,971,972],[200,230,466,480,504,533,914,937,969,973,976,977,978,979],[200,230,466,480,969,973,976],[466,483,484,486,526],[200,230,466,480,483,484,486,975],[200,466,480,483,484,486,974],[200,466,480,975],[54,62,212,230,449,466,483,484,486,670],[466,671],[54,212,466,476],[54,58,130,200,218,245,466,473,474,475,476,477,478,479,483,484,486],[466,775],[466,484,486,523,524],[466,523,525],[54,156,466,494,495,502,503],[466,494],[466,470,471,472,483],[466,473],[54,266,466,483,484,486,589],[466,498,501,502],[67,68,466],[54,156,466,480,483,484,486,493,504],[466,472,496,497],[466,472],[54,466,473,483,484,486,494,504],[54,283,466],[54,58,126,140,146,176,218,230,245,284,466,471,472,473,474,476,478,479,480,481,482],[466,483,484,485],[245,466,483,484],[54,466,483],[65,449,466,472,483,484,486,504,550,551,559,577],[285,466],[54,466,483,484,486,843],[54,67,68,130,466,475,483,484,486],[466,480,483,484,486,504],[466,484,486,522],[466,523],[466,523,526,527],[466,525,527,528],[54,466,824,825],[200,466,826],[54,200,466],[466,820],[466,818,819,820,821],[466,612],[466,547,604,914],[156,466,737,818,914],[54,130,230,466,545,547,709,716,737,818,914,938,939,940],[466,545,941],[466,941],[466,737,927,941],[283,284,466],[283,284,404,466],[54,135,139,146,212,229,466],[54,130,466],[54,62,86,466],[200,466,629],[200,466,483,484,486,688],[466,689],[54,200,230,288,466,480,483,484,486,545,678,679,681,682,683,684,685,818],[466,680],[466,681],[466,479],[146,466,483,484,486,626,686],[230,466,480,686],[200,230,466,486,686,818],[54,200,466,483,484,486,545,590,626,686],[54,200,466,818,922,923,924,925],[466,920,922,926],[466,545,818,923,926],[466,818,914,918,920,921],[130,466,547,710,726,727,729,914],[466,728],[466,709],[466,547,690,710,728,818,914],[466,603],[466,545,626,761,765,767],[54,466,483,484,486,818],[466,480,483,484,486,812,813],[466,480,812,814],[64,200,230,466,544,733,734,814,818],[466,480,483,484,486,671,860],[200,466,665,694,818,922],[54,466,582,658,659,662,914,946],[77,428,466,545,629,638,696,705,770,771,772],[54,230,466,544,545,604,703],[466,544,545,604,704],[466,816],[54,466,483,484,486,604],[54,466,483,484,486,724,860],[230,466,483,484,486,487,510,517,521,528,529,530],[466,484,486,531],[200,212,230,466,480,483,484,486,502,590,798,799],[77,119,200,428,466,480,504,533,585,776,799,801,802,803,804,805,806,807,809,810],[466,483,484,486,671,724],[466,805],[230,466,476,483,484,486,808],[230,466,476,809],[466,799],[54,466,483,484,486,518,520,533],[466,519],[54,466,468,469,483,484,486,518,521,532],[466,533],[54,466,533],[466,547,737,818,914,933,934,981],[466,547,818,914],[466,547,818,914,933],[200,466,533,863,915,921],[466,914,922],[200,466,610,643,660,665,694,818,863,916,917,919,921],[466,920],[466,483,484,486,532,603,719,720],[466,789,818],[54,466,483,484,486,640,659,914],[54,466,483,484,486,696],[77,156,466,545,776,785],[466,545,696,784],[466,531],[200,466,665,818,920,922],[466,483,484,486,545,650,780,783],[404,466],[466,483,484,486,762,763,764,767],[466,765],[65,77,428,466,483,484,486,492,545,626,762,765,766],[466,545,650,784,965,966,968],[466,967],[156,466,966,967],[229,466,483,484,486,673],[229,466,674],[126,200,229,466,480,483,484,486,672,676,677,823,826],[146,466,480,827],[200,332,466,480,483,484,486,590,674,675],[200,332,466,480,590,674,676],[466,480,483,484,486],[466,677,818,822],[466,545,684,721,818],[466,483,484,486,722],[54,200,466,480,483,484,486,794],[200,466,480,795],[54,466,483,484,486,589],[466,818],[54,212,466,483,484,486,733,795,796],[466,733,795,797],[54,77,146,156,200,218,229,230,428,466,468,469,473,478,480,504,533,545,547,549,603,610,612,626,640,643,647,650,658,659,660,661,665,686,687,689,695,696,698,700,707,708,711,718,721,723,725,728,732,733,738,740,741,742,743,744,745,746,747,748,749,750,751,752,753,754,755,756,757,758,759,760,768,769,773,779,786,787,788,789,790,792,793,797,800,811,815,817,860,914,923,926],[466,480,686,687,689,737,818],[245,466,483,484,486,739],[466,707,818],[466,721,818],[466,694,695,818],[466,725,818],[466,533,818],[77,146,200,218,229,230,466,480,533,545,547,626,658,686,689,691,692,693,696,698,699,700,707,708,711,712,717,718,721,723,725,729,734,735,736,818,914,923,926],[466,547,690,914],[466,547,691,914],[466,691,818],[466,480,545,689,695,696,698,818,923,926],[200,466,480,590,603,731,732,733],[230,466,730],[466,731],[200,230,466,473,480,504,532,533,658,661,665,671,691,698,721,768,786,818,914,927,941,942,944,963,964,968,980,982],[230,466,533,689,721,818,920,922,923,926,930,943],[466,962,983],[466,545],[54,466,483,484,486,791],[466,792],[54,466,544,545,701,702,704,705,706],[466,700,708,710],[466,544],[230,466,700,707,711],[466,777],[466,710,774,776,778],[466,779],[77,119,428,466,736,773,818,928,929,930,931],[200,466,473,483,484,486,691],[466,545,707],[54,200,466,737,818,836],[200,466,547,737,914,954],[466,737,818,1008],[200,466,547,665,721,737,745,914,922,1001,1002],[466,547,691,692,914,1000],[466,697],[466,957],[466,956],[288,333,466,818,955],[428,449,480,504,660,665,863,881,910,914,1378,1379,1380,1381,1382,1383,1384,1385,1386,1387,1388,1389],[140],[428],[55],[64,466],[54,58,62,63,69,230,249,250,267,443,446,447,448,466],[68,424,449,466,472],[67,424,449,466,472],[67,466],[65,67,466],[65,66,466],[54,65,67,200,201,266,267,280,449,466],[54,67,200,201,266,267,449,450,466],[65,253,254,450,466],[65,66,200,201,466],[54,58,62,466],[199,466],[52,53,54,55,56,57,58,68,69,70,73,76,233,234,235,465],[68,69,244,466],[230,282,283,466],[283,404,466],[54,62,86,200,466],[231,233,466],[232,466],[230,232,233,466],[77,78,128,466],[58,466],[55,56,69,466],[254,466],[55,56,466],[55,466],[52,53,54,55,75,466],[52,53,55,57,71,72,74,466],[52,54,55,71,72,466],[53,56,466],[52,54,55,56,75,466],[52,55,56,234,466],[52,466],[54,58,466],[54,58,62,199,200,201,466],[54,146,156,245,282,283,466,499,500],[283,466,501],[58,281,282,451,466],[60,466,553],[54,60,65,212,466,553,554,558,563],[54,58,466,552],[54,230,244,466,553],[54,59,60,466],[54,60,65,212,466,553,554,566,568,577],[54,61,65,67,68,212,466,553,576],[466,564],[466,565],[54,58,62,69,466],[54,58,61,63,68,466],[54,62,251,252,254,255,256,257,258,259,466],[414,466],[54,212,260,337,338,339,425,426,427,430,443,466],[415,417,466],[54,65,127,146,229,283,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364,365,366,367,368,369,370,371,372,373,374,375,376,377,378,379,380,381,387,388,400,410,413,466],[54,60,260,416,418,423,466,554,557,559,560,562,575],[212,260,337,338,340,415,416,417,419,421,422,423,425,443,466],[64,414,424,466],[260,417,466],[466,552,553,562],[466,552,553,560,561],[54,60,212,414,466,554],[466,569,570],[417,423,466,575],[415,416,466,575],[260,414,466],[260,415,466],[260,418,466],[54,414,421,466,555,572,573],[54,466,555,574],[65,77,212,466,572],[54,60,466,554,560,567,575,576],[54,60,260,416,418,423,466,554,560,575,577],[414,420,466],[54,466,555,572,573,574],[466,555,572],[414,466,556,557,563,568,571,576],[54,62,199,200,201,251,252,253,466],[54,62,145,212,254,260,266,466],[54,62,251,252,466],[54,334,466],[54,62,271,333,466],[439,466],[243,466],[439,440,466],[65,78,129,433,466],[65,129,212,272,437,438,441,443,466],[54,279,285,335,466],[54,62,63,78,129,200,208,230,267,268,269,270,272,273,274,275,276,277,278,336,337,338,442,449,466],[443,466],[54,63,67,68,146,212,230,277,337,338,419,424,430,431,432,433,434,435,436,442,443,466],[272,273,274,276,466],[230,275,466],[65,271,276,466],[252,260,466],[237,238,465,466],[54,58,246,248,456,466],[54,58,78,230,458,466],[54,58,459,461,466],[58,69,457,462,466],[465,466],[54,58,236,466],[58,237,244,466],[54,242,466],[237,243,245,463,464,466],[54,68,126,135,139,146,212,229,244,452,455,466],[247,466],[54,58,459,460,466],[54,146,212,304,307,466],[54,305,466],[54,58,130,305,306,308,309,310,466],[304,466],[54,146,290,316,321,466],[54,62,127,286,287,289,291,293,294,299,303,314,315,321,330,466],[54,62,127,286,287,289,291,293,294,298,299,300,314,317,321,330,333,466],[54,62,146,212,230,266,290,292,293,295,298,300,302,303,315,316,317,318,320,333,466],[54,230,286,287,289,316,321,466],[54,62,127,286,287,289,291,292,293,294,298,299,300,314,318,321,330,333,466],[266,286,291,292,293,294,295,299,466],[58,146,230,290,292,293,298,300,302,303,315,316,317,318,320,322,323,324,327,331,332,333,466],[54,288,298,319,333,466],[54,58,62,200,230,286,287,289,466],[200,201,212,266,290,291,293,294,298,310,311,312,313,321,466],[54,212,266,466],[54,58,62,200,286,287,289,291,292,293,294,298,299,300,320,328,332,466],[288,298,320,333,466],[54,58,180,200,286,287,289,291,292,293,294,298,299,300,301,303,314,315,316,318,320,321,322,325,326,328,329,330,332,333,466],[54,58,200,286,287,289,291,292,293,294,298,299,300,301,314,316,317,318,320,326,327,328,330,332,333,466],[54,58,62,200,286,287,289,291,292,293,294,298,299,300,314,320,327,329,331,333,466],[54,58,62,127,200,286,287,289,291,292,293,294,298,299,300,301,314,320,326,327,329,330,331,332,333,466],[54,58,62,200,286,287,289,291,292,293,294,298,299,300,314,320,327,328,330,333,466],[54,58,200,230,286,287,289,315,321,325,327,466],[291,292,294,466],[286,466],[230,286,289,466],[146,266,286,289,290,292,293,466],[293,466],[286,288,466],[54,58,291,466],[54,58,62,288,300,331,333,466],[54,58,230,288,296,300,331,333,466],[54,58,200,286,287,289,291,292,293,294,298,299,300,301,314,316,317,318,320,326,327,328,330,331,333,466],[54,58,146,212,266,293,295,297,300,466],[54,58,62,146,286,291,292,293,294,297,298,299,466],[54,78,229,466],[54,78,131,215,229,230,466],[54,136,137,146,212,229,466],[54,58,134,466],[54,131,212,229,466],[54,58,77,78,127,128,130,172,177,215,216,217,229,230,466],[54,62,78,79,80,81,82,83,84,85,87,115,127,128,133,146,153,176,177,180,200,201,203,207,208,212,213,214,218,228,230,466],[54,123,124,125,126,466],[54,172,174,466],[405,466],[156,466],[54,156,229,230,271,427,428,429,466],[271,466],[54,58,62,130,333,466],[54,244,466],[116,466],[78,466],[54,126,466],[127,135,466],[126,466],[54,58,126,130,135,138,139,146,212,229,466],[54,58,78,128,130,132,212,229,466],[54,58,126,130,135,139,146,212,229,244,453,466],[119,466],[77,466],[54,135,139,140,146,212,229,466],[58,128,130,133,212,229,466],[54,78,127,128,172,229,466],[54,78,466],[54,58,130,212,229,230,261,262,263,264,265,466],[266,466],[54,146,230,466],[119,121,466],[54,126,127,129,134,135,139,140,141,145,208,212,229,230,466],[54,127,466],[54,78,213,466],[54,77,126,155,156,177,180,466],[54,116,155,156,187,189,466],[54,119,155,156,193,199,466],[54,121,155,156,163,183,466],[54,78,149,151,154,466],[54,77,115,116,152,466],[54,77,119,152,153,466],[54,77,121,150,152,466],[54,67,68,212,244,281,450,451,452,454,466],[58,183,189,199,466],[54,78,128,129,133,208,210,211,229,466],[54,127,146,212,229,466],[54,127,128,212,466],[77,117,118,120,122,127,466],[54,77,116,117,128,466],[54,77,117,119,128,466],[54,77,117,121,128,466],[54,128,466],[64,78,128,156,466],[126,139,155,173,174,212,466],[78,116,118,128,139,149,155,157,158,159,160,161,179,180,183,184,185,186,187,188,190,199,466],[116,189,466],[78,119,120,128,139,147,148,154,155,176,179,180,183,189,190,191,192,193,194,195,196,197,198,466],[119,199,466],[78,121,122,128,139,151,155,162,163,164,165,166,167,168,169,170,179,180,181,182,189,190,199,466],[121,183,466],[54,77,123,124,125,126,127,135,139,155,171,172,174,175,176,177,178,179,183,189,199,230,466],[54,77,180,466],[54,58,78,127,128,130,132,209,213,229,466],[54,58,212,239,240,241,466],[54,78,153,223,466],[54,387,466],[54,382,383,385,386,466],[387,466],[54,383,384,387,466],[54,383,385,387,466],[54,230,449,466],[78,205,208,444,445,446,449,466],[444,449,466],[449,466],[206,466],[58,204,205,207,466],[62,226,466],[62,227,466],[54,78,129,222,223,224,466],[205,225,466],[54,62,153,219,221,225,227,466],[205,228,466],[62,220,466],[62,221,466],[54,62,78,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,127,129,133,146,200,201,203,207,212,213,229,230,466],[54,388,407,408,466],[54,388,409,466],[54,283,388,400,401,402,403,406,409,466],[54,388,400,410,466],[54,283,388,411,412,466],[54,413,466],[54,391,466],[54,390,466],[54,393,394,395,397,466],[54,391,392,396,398,466],[390,391,396,397],[399,466],[54,399,466],[54,283,388,389,392,398,466],[46,48,50,1323,1324,1335,1336,1398],[1337,1338,1395,1396,1397],[1337,1338,1393],[503,504,896,914,1337,1343,1347,1352,1369,1371,1372,1374,1377,1390,1392],[843,1337,1343,1345,1346,1392,1393],[1337,1392,1393,1394],[843,1337,1343,1344,1345,1346,1347,1391,1393],[1337],[863,881,914,1329,1330,1331],[1330],[1332]],"referencedMap":[[1323,1],[1327,2],[1035,3],[1107,4],[1106,5],[1040,6],[1080,7],[1103,8],[1082,9],[1101,10],[1037,11],[1036,12],[1099,13],[1044,12],[1078,14],[1051,15],[1081,16],[1041,17],[1097,18],[1095,12],[1094,12],[1093,12],[1092,12],[1091,12],[1090,12],[1089,12],[1088,12],[1087,19],[1084,20],[1086,12],[1039,21],[1042,12],[1085,22],[1077,23],[1076,12],[1074,12],[1073,12],[1072,24],[1071,12],[1070,12],[1069,12],[1068,12],[1067,25],[1066,12],[1065,12],[1064,12],[1063,12],[1061,26],[1062,12],[1059,12],[1058,12],[1057,12],[1060,27],[1056,12],[1055,17],[1054,28],[1053,28],[1052,26],[1048,28],[1047,28],[1046,28],[1045,28],[1043,23],[1324,29],[1321,30],[1320,31],[1318,32],[1317,33],[1315,34],[1268,35],[1125,36],[1127,37],[1129,38],[1131,39],[1135,40],[1137,41],[1139,42],[1141,43],[1143,44],[1145,45],[1147,46],[1149,47],[1151,48],[1153,49],[1155,50],[1157,51],[1159,52],[1161,53],[1163,54],[1165,55],[1167,56],[1169,57],[1171,58],[1173,59],[1175,60],[1177,61],[1179,62],[1181,63],[1183,64],[1185,65],[1187,66],[1189,67],[1191,68],[1193,69],[1195,70],[1197,71],[1199,72],[1201,73],[1203,74],[1205,75],[1207,76],[1209,77],[1211,78],[1213,79],[1215,80],[1217,81],[1219,82],[1221,83],[1223,84],[1225,85],[1227,86],[1229,87],[1231,88],[1233,89],[1235,90],[1237,91],[1239,92],[1241,93],[1243,94],[1245,95],[1247,96],[1249,97],[1251,98],[1253,99],[1255,100],[1257,101],[1259,102],[1261,103],[1263,104],[1265,105],[1267,106],[1283,107],[1270,108],[1272,109],[1274,110],[1276,111],[1278,112],[1280,113],[1282,114],[1290,115],[1285,116],[1284,117],[1287,118],[1289,119],[1313,120],[1312,121],[1300,122],[1296,123],[1294,124],[1310,125],[1302,126],[1298,127],[1304,128],[1306,129],[1292,130],[1308,131],[1108,132],[1121,133],[1120,134],[1114,132],[1115,132],[1109,132],[1110,132],[1111,132],[1112,132],[1113,132],[1117,135],[1118,136],[1116,135],[1026,137],[1022,138],[1023,139],[28,140],[1335,141],[47,142],[45,143],[46,144],[1328,145],[43,146],[50,147],[48,148],[40,149],[35,150],[34,150],[37,151],[36,152],[39,152],[839,153],[716,154],[714,155],[715,155],[717,156],[713,157],[769,158],[709,159],[1010,160],[1000,161],[1004,159],[1005,159],[1006,162],[1007,163],[1021,164],[467,159],[953,165],[948,166],[952,166],[949,167],[992,168],[985,169],[986,170],[996,171],[984,172],[993,173],[994,159],[995,174],[991,175],[990,176],[937,177],[935,178],[936,179],[961,180],[998,153],[959,181],[951,182],[950,159],[1011,183],[1020,184],[1014,185],[1015,186],[1016,185],[1017,185],[1019,187],[1018,188],[1013,189],[1012,190],[1374,191],[1353,192],[1351,193],[1349,194],[1348,159],[1350,159],[1352,195],[1343,196],[1347,197],[1345,198],[1346,199],[1375,200],[1376,201],[1344,202],[1377,203],[1342,204],[1341,205],[1354,206],[1339,207],[1357,208],[1362,209],[1361,210],[1356,211],[1355,208],[1363,212],[1364,213],[1366,214],[1365,215],[1367,216],[1373,217],[1359,218],[1358,219],[1372,220],[1370,221],[1371,222],[1369,223],[1368,224],[1360,225],[849,226],[910,227],[909,228],[860,229],[828,230],[724,231],[850,232],[851,233],[915,234],[855,235],[841,236],[856,237],[838,238],[859,239],[831,240],[854,241],[914,242],[534,159],[945,243],[946,244],[863,245],[669,246],[881,247],[879,248],[880,249],[876,250],[873,251],[874,178],[989,252],[987,253],[988,254],[812,153],[652,153],[653,255],[862,256],[861,159],[844,257],[842,258],[869,259],[895,260],[845,261],[864,259],[866,262],[865,259],[877,263],[867,264],[882,265],[872,266],[894,267],[886,268],[885,269],[887,259],[889,270],[888,271],[890,272],[891,159],[892,273],[893,274],[666,275],[546,276],[896,277],[535,159],[536,278],[537,159],[539,249],[540,279],[541,159],[542,259],[543,159],[847,280],[878,281],[667,281],[848,282],[884,283],[883,284],[868,285],[870,153],[871,286],[668,153],[581,287],[582,288],[660,289],[658,290],[654,291],[656,292],[655,293],[659,294],[619,295],[662,296],[661,297],[548,298],[908,299],[913,300],[911,301],[912,302],[832,153],[840,303],[858,304],[857,305],[833,159],[834,159],[835,306],[837,307],[902,308],[836,159],[898,309],[897,310],[907,311],[901,312],[904,313],[903,314],[899,315],[900,316],[906,317],[905,159],[640,318],[664,319],[645,320],[650,321],[623,322],[608,159],[638,323],[633,324],[637,325],[636,322],[665,326],[549,327],[663,328],[830,329],[829,330],[649,159],[613,331],[615,332],[614,333],[616,322],[583,322],[639,334],[544,335],[609,159],[603,336],[624,337],[651,338],[641,339],[642,340],[612,341],[591,159],[594,322],[604,342],[601,159],[600,159],[605,159],[630,343],[696,153],[644,344],[545,345],[585,335],[626,346],[647,347],[648,348],[646,349],[607,350],[783,351],[781,352],[782,353],[622,354],[618,355],[584,356],[617,357],[611,159],[530,159],[772,153],[492,358],[511,153],[517,359],[516,360],[515,361],[514,362],[513,363],[512,364],[488,159],[505,365],[508,366],[509,367],[490,159],[510,368],[489,366],[766,369],[506,366],[507,370],[589,371],[587,372],[526,153],[971,373],[970,374],[973,375],[972,259],[980,376],[977,377],[969,378],[978,153],[976,379],[975,380],[974,381],[671,382],[670,383],[475,384],[1329,159],[480,385],[776,386],[775,159],[525,387],[524,388],[504,389],[495,390],[473,391],[470,392],[471,392],[590,393],[503,394],[491,395],[494,396],[498,397],[496,159],[497,398],[493,399],[999,400],[483,401],[486,402],[485,403],[484,404],[578,405],[550,406],[551,406],[1340,407],[846,259],[476,408],[979,409],[875,153],[527,153],[523,410],[522,411],[528,412],[529,413],[798,159],[826,414],[824,415],[825,416],[821,417],[822,418],[819,159],[820,419],[940,420],[927,421],[941,422],[938,423],[939,424],[942,425],[538,426],[519,427],[481,428],[547,159],[629,322],[787,429],[502,159],[760,322],[960,430],[479,322],[474,153],[478,429],[482,429],[657,431],[739,259],[689,432],[788,433],[686,434],[678,265],[679,159],[681,435],[680,436],[682,437],[683,159],[684,438],[687,439],[688,440],[685,441],[926,442],[923,443],[924,444],[919,445],[918,159],[728,446],[729,447],[726,159],[710,448],[735,449],[690,159],[727,450],[768,451],[761,159],[733,452],[732,265],[814,453],[813,454],[815,455],[789,456],[695,457],[694,159],[947,458],[773,459],[770,153],[771,153],[704,460],[703,461],[816,259],[817,462],[706,463],[997,259],[725,464],[962,159],[531,465],[487,159],[532,466],[801,189],[803,189],[800,467],[807,189],[804,259],[805,159],[811,468],[810,469],[806,470],[799,189],[809,471],[808,472],[802,473],[521,474],[518,159],[520,475],[533,476],[468,477],[469,478],[982,479],[933,480],[934,481],[981,159],[922,482],[925,483],[920,484],[916,485],[917,485],[721,486],[719,159],[720,322],[790,487],[718,488],[705,489],[786,490],[785,491],[943,492],[921,493],[784,494],[780,495],[765,496],[763,497],[767,498],[764,159],[762,159],[967,499],[965,495],[966,500],[968,501],[674,502],[673,503],[827,504],[672,505],[676,506],[675,507],[677,508],[823,509],[759,510],[723,511],[795,512],[794,513],[722,514],[793,515],[797,516],[796,517],[818,518],[738,519],[740,520],[741,159],[742,521],[743,515],[744,522],[745,515],[746,515],[747,523],[748,524],[749,515],[750,522],[751,522],[752,525],[753,515],[754,515],[755,515],[756,159],[757,522],[758,525],[737,526],[691,527],[692,528],[693,515],[736,529],[712,330],[699,530],[734,531],[731,532],[730,533],[983,534],[944,535],[963,536],[964,537],[792,538],[791,539],[707,540],[701,159],[702,159],[711,541],[700,542],[708,543],[777,542],[778,544],[779,545],[774,546],[932,547],[928,495],[929,495],[930,548],[931,549],[1008,550],[955,551],[954,161],[1009,552],[1003,553],[1001,554],[1002,485],[697,159],[698,555],[958,556],[957,557],[956,558],[1390,559],[1387,560],[1388,561],[1389,562],[65,563],[449,564],[249,159],[250,159],[472,159],[580,565],[579,566],[280,567],[66,159],[68,568],[285,426],[67,569],[281,570],[451,571],[452,572],[58,159],[450,573],[55,322],[201,172],[64,159],[853,574],[477,430],[200,575],[466,576],[245,577],[130,159],[62,322],[115,430],[284,578],[87,430],[405,579],[153,580],[232,581],[233,582],[231,583],[129,584],[150,580],[86,585],[54,322],[70,586],[253,587],[71,588],[56,589],[76,590],[75,591],[73,592],[57,593],[72,159],[234,590],[74,594],[235,595],[52,159],[53,596],[156,159],[404,426],[852,430],[282,597],[309,598],[501,599],[500,600],[283,601],[278,159],[558,602],[559,603],[553,604],[552,605],[557,159],[61,606],[567,607],[577,608],[60,585],[565,609],[566,610],[554,159],[564,322],[63,611],[69,612],[252,322],[260,613],[251,159],[426,614],[431,615],[418,616],[414,617],[341,159],[342,159],[343,159],[344,159],[345,159],[346,159],[347,159],[348,159],[349,159],[350,159],[351,159],[352,159],[353,159],[354,159],[355,159],[356,159],[357,159],[358,159],[359,159],[360,159],[361,159],[362,159],[363,159],[364,159],[365,159],[366,159],[367,159],[368,159],[369,159],[370,159],[371,159],[372,159],[373,159],[374,159],[375,159],[376,159],[377,159],[378,159],[379,159],[380,159],[381,159],[339,400],[563,618],[424,619],[340,159],[425,620],[423,621],[420,614],[561,622],[562,623],[560,624],[571,625],[569,626],[570,627],[415,628],[416,629],[419,630],[574,631],[573,632],[555,633],[568,634],[576,635],[421,636],[575,637],[556,638],[572,639],[417,628],[254,640],[267,641],[256,642],[335,643],[338,159],[334,644],[440,645],[439,646],[441,647],[436,159],[434,648],[433,322],[435,322],[442,649],[336,650],[337,159],[443,651],[269,159],[268,159],[438,652],[437,653],[275,654],[273,159],[274,159],[276,655],[272,656],[255,642],[258,642],[259,642],[422,657],[257,642],[239,658],[457,659],[246,585],[459,660],[458,585],[462,661],[463,662],[238,663],[236,322],[247,585],[237,664],[464,665],[243,666],[240,159],[241,159],[465,667],[456,668],[248,669],[461,670],[308,671],[304,597],[307,429],[306,672],[311,673],[305,674],[310,322],[324,675],[316,676],[318,677],[321,678],[315,679],[317,680],[303,681],[325,682],[320,683],[288,684],[314,685],[313,686],[333,687],[319,688],[327,689],[331,690],[330,691],[328,692],[329,693],[322,694],[286,159],[293,695],[299,696],[287,697],[291,698],[294,699],[289,700],[292,701],[296,702],[297,703],[332,704],[298,705],[300,706],[131,707],[216,708],[138,709],[136,710],[137,710],[132,711],[218,712],[229,713],[80,159],[81,159],[82,159],[83,159],[79,159],[84,159],[85,159],[127,714],[395,715],[429,159],[406,716],[428,717],[430,718],[427,719],[460,720],[453,721],[159,722],[244,723],[139,322],[135,724],[174,725],[77,322],[161,159],[116,159],[158,159],[188,159],[187,159],[184,159],[186,159],[160,159],[126,322],[191,159],[119,159],[176,159],[195,159],[193,159],[196,159],[197,159],[148,159],[164,159],[121,159],[170,159],[166,159],[163,159],[168,159],[169,159],[181,159],[185,322],[192,322],[182,322],[177,322],[155,159],[123,322],[124,322],[125,322],[172,726],[140,727],[133,728],[454,729],[198,730],[78,731],[141,732],[211,733],[230,734],[215,735],[266,736],[261,737],[265,738],[167,739],[146,740],[134,741],[209,742],[178,743],[190,744],[194,745],[165,746],[152,747],[149,748],[154,749],[151,750],[455,751],[214,752],[217,159],[212,753],[145,754],[213,755],[128,756],[118,757],[120,758],[122,759],[117,760],[179,761],[175,762],[189,763],[157,764],[199,765],[147,766],[183,767],[162,768],[180,769],[171,770],[210,771],[843,574],[242,772],[203,735],[224,773],[388,774],[387,775],[382,776],[385,777],[384,778],[383,159],[386,159],[448,779],[447,780],[445,781],[444,782],[205,159],[223,159],[207,783],[206,784],[204,585],[227,785],[226,786],[225,787],[222,788],[228,789],[219,790],[221,791],[220,792],[208,793],[89,159],[90,159],[91,159],[92,159],[93,159],[94,159],[95,159],[96,159],[97,159],[98,159],[99,159],[100,159],[101,159],[102,159],[103,159],[104,159],[105,159],[106,159],[107,159],[108,159],[109,159],[88,159],[110,159],[111,159],[112,159],[113,159],[114,159],[409,794],[407,795],[408,159],[410,796],[401,797],[402,159],[403,159],[413,798],[411,799],[389,159],[392,800],[391,801],[396,802],[397,803],[393,159],[398,804],[394,159],[390,800],[400,805],[412,806],[399,807],[1399,808],[1398,809],[1394,810],[1393,811],[1396,812],[1395,813],[1392,814],[1338,815],[1332,816],[1331,817],[1333,818]],"exportedModulesMap":[[1323,1],[1327,2],[1035,3],[1107,4],[1106,5],[1040,6],[1080,7],[1103,8],[1082,9],[1101,10],[1037,11],[1036,12],[1099,13],[1044,12],[1078,14],[1051,15],[1081,16],[1041,17],[1097,18],[1095,12],[1094,12],[1093,12],[1092,12],[1091,12],[1090,12],[1089,12],[1088,12],[1087,19],[1084,20],[1086,12],[1039,21],[1042,12],[1085,22],[1077,23],[1076,12],[1074,12],[1073,12],[1072,24],[1071,12],[1070,12],[1069,12],[1068,12],[1067,25],[1066,12],[1065,12],[1064,12],[1063,12],[1061,26],[1062,12],[1059,12],[1058,12],[1057,12],[1060,27],[1056,12],[1055,17],[1054,28],[1053,28],[1052,26],[1048,28],[1047,28],[1046,28],[1045,28],[1043,23],[1324,29],[1321,30],[1320,31],[1318,32],[1317,33],[1315,34],[1268,35],[1125,36],[1127,37],[1129,38],[1131,39],[1135,40],[1137,41],[1139,42],[1141,43],[1143,44],[1145,45],[1147,46],[1149,47],[1151,48],[1153,49],[1155,50],[1157,51],[1159,52],[1161,53],[1163,54],[1165,55],[1167,56],[1169,57],[1171,58],[1173,59],[1175,60],[1177,61],[1179,62],[1181,63],[1183,64],[1185,65],[1187,66],[1189,67],[1191,68],[1193,69],[1195,70],[1197,71],[1199,72],[1201,73],[1203,74],[1205,75],[1207,76],[1209,77],[1211,78],[1213,79],[1215,80],[1217,81],[1219,82],[1221,83],[1223,84],[1225,85],[1227,86],[1229,87],[1231,88],[1233,89],[1235,90],[1237,91],[1239,92],[1241,93],[1243,94],[1245,95],[1247,96],[1249,97],[1251,98],[1253,99],[1255,100],[1257,101],[1259,102],[1261,103],[1263,104],[1265,105],[1267,106],[1283,107],[1270,108],[1272,109],[1274,110],[1276,111],[1278,112],[1280,113],[1282,114],[1290,115],[1285,116],[1284,117],[1287,118],[1289,119],[1313,120],[1312,121],[1300,122],[1296,123],[1294,124],[1310,125],[1302,126],[1298,127],[1304,128],[1306,129],[1292,130],[1308,131],[1108,132],[1121,133],[1120,134],[1114,132],[1115,132],[1109,132],[1110,132],[1111,132],[1112,132],[1113,132],[1117,135],[1118,136],[1116,135],[1026,137],[1022,138],[1023,139],[28,140],[1335,141],[47,142],[45,143],[46,144],[1328,145],[43,146],[50,147],[48,148],[40,149],[35,150],[34,150],[37,151],[36,152],[39,152],[839,153],[716,154],[714,155],[715,155],[717,156],[713,157],[769,158],[709,159],[1010,160],[1000,161],[1004,159],[1005,159],[1006,162],[1007,163],[1021,164],[467,159],[953,165],[948,166],[952,166],[949,167],[992,168],[985,169],[986,170],[996,171],[984,172],[993,173],[994,159],[995,174],[991,175],[990,176],[937,177],[935,178],[936,179],[961,180],[998,153],[959,181],[951,182],[950,159],[1011,183],[1020,184],[1014,185],[1015,186],[1016,185],[1017,185],[1019,187],[1018,188],[1013,189],[1012,190],[1374,191],[1353,192],[1351,193],[1349,194],[1348,159],[1350,159],[1352,195],[1343,196],[1347,197],[1345,198],[1346,199],[1375,200],[1376,201],[1344,202],[1377,203],[1342,204],[1341,205],[1354,206],[1339,207],[1357,208],[1362,209],[1361,210],[1356,211],[1355,208],[1363,212],[1364,213],[1366,214],[1365,215],[1367,216],[1373,217],[1359,218],[1358,219],[1372,220],[1370,221],[1371,222],[1369,223],[1368,224],[1360,225],[849,226],[910,227],[909,228],[860,229],[828,230],[724,231],[850,232],[851,233],[915,234],[855,235],[841,236],[856,237],[838,238],[859,239],[831,240],[854,241],[914,242],[534,159],[945,243],[946,244],[863,245],[669,246],[881,247],[879,248],[880,249],[876,250],[873,251],[874,178],[989,252],[987,253],[988,254],[812,153],[652,153],[653,255],[862,256],[861,159],[844,257],[842,258],[869,259],[895,260],[845,261],[864,259],[866,262],[865,259],[877,263],[867,264],[882,265],[872,266],[894,267],[886,268],[885,269],[887,259],[889,270],[888,271],[890,272],[891,159],[892,273],[893,274],[666,275],[546,276],[896,277],[535,159],[536,278],[537,159],[539,249],[540,279],[541,159],[542,259],[543,159],[847,280],[878,281],[667,281],[848,282],[884,283],[883,284],[868,285],[870,153],[871,286],[668,153],[581,287],[582,288],[660,289],[658,290],[654,291],[656,292],[655,293],[659,294],[619,295],[662,296],[661,297],[548,298],[908,299],[913,300],[911,301],[912,302],[832,153],[840,303],[858,304],[857,305],[833,159],[834,159],[835,306],[837,307],[902,308],[836,159],[898,309],[897,310],[907,311],[901,312],[904,313],[903,314],[899,315],[900,316],[906,317],[905,159],[640,318],[664,319],[645,320],[650,321],[623,322],[608,159],[638,323],[633,324],[637,325],[636,322],[665,326],[549,327],[663,328],[830,329],[829,330],[649,159],[613,331],[615,332],[614,333],[616,322],[583,322],[639,334],[544,335],[609,159],[603,336],[624,337],[651,338],[641,339],[642,340],[612,341],[591,159],[594,322],[604,342],[601,159],[600,159],[605,159],[630,343],[696,153],[644,344],[545,345],[585,335],[626,346],[647,347],[648,348],[646,349],[607,350],[783,351],[781,352],[782,353],[622,354],[618,355],[584,356],[617,357],[611,159],[530,159],[772,153],[492,358],[511,153],[517,359],[516,360],[515,361],[514,362],[513,363],[512,364],[488,159],[505,365],[508,366],[509,367],[490,159],[510,368],[489,366],[766,369],[506,366],[507,370],[589,371],[587,372],[526,153],[971,373],[970,374],[973,375],[972,259],[980,376],[977,377],[969,378],[978,153],[976,379],[975,380],[974,381],[671,382],[670,383],[475,384],[1329,159],[480,385],[776,386],[775,159],[525,387],[524,388],[504,389],[495,390],[473,391],[470,392],[471,392],[590,393],[503,394],[491,395],[494,396],[498,397],[496,159],[497,398],[493,399],[999,400],[483,401],[486,402],[485,403],[484,404],[578,405],[550,406],[551,406],[1340,407],[846,259],[476,408],[979,409],[875,153],[527,153],[523,410],[522,411],[528,412],[529,413],[798,159],[826,414],[824,415],[825,416],[821,417],[822,418],[819,159],[820,419],[940,420],[927,421],[941,422],[938,423],[939,424],[942,425],[538,426],[519,427],[481,428],[547,159],[629,322],[787,429],[502,159],[760,322],[960,430],[479,322],[474,153],[478,429],[482,429],[657,431],[739,259],[689,432],[788,433],[686,434],[678,265],[679,159],[681,435],[680,436],[682,437],[683,159],[684,438],[687,439],[688,440],[685,441],[926,442],[923,443],[924,444],[919,445],[918,159],[728,446],[729,447],[726,159],[710,448],[735,449],[690,159],[727,450],[768,451],[761,159],[733,452],[732,265],[814,453],[813,454],[815,455],[789,456],[695,457],[694,159],[947,458],[773,459],[770,153],[771,153],[704,460],[703,461],[816,259],[817,462],[706,463],[997,259],[725,464],[962,159],[531,465],[487,159],[532,466],[801,189],[803,189],[800,467],[807,189],[804,259],[805,159],[811,468],[810,469],[806,470],[799,189],[809,471],[808,472],[802,473],[521,474],[518,159],[520,475],[533,476],[468,477],[469,478],[982,479],[933,480],[934,481],[981,159],[922,482],[925,483],[920,484],[916,485],[917,485],[721,486],[719,159],[720,322],[790,487],[718,488],[705,489],[786,490],[785,491],[943,492],[921,493],[784,494],[780,495],[765,496],[763,497],[767,498],[764,159],[762,159],[967,499],[965,495],[966,500],[968,501],[674,502],[673,503],[827,504],[672,505],[676,506],[675,507],[677,508],[823,509],[759,510],[723,511],[795,512],[794,513],[722,514],[793,515],[797,516],[796,517],[818,518],[738,519],[740,520],[741,159],[742,521],[743,515],[744,522],[745,515],[746,515],[747,523],[748,524],[749,515],[750,522],[751,522],[752,525],[753,515],[754,515],[755,515],[756,159],[757,522],[758,525],[737,526],[691,527],[692,528],[693,515],[736,529],[712,330],[699,530],[734,531],[731,532],[730,533],[983,534],[944,535],[963,536],[964,537],[792,538],[791,539],[707,540],[701,159],[702,159],[711,541],[700,542],[708,543],[777,542],[778,544],[779,545],[774,546],[932,547],[928,495],[929,495],[930,548],[931,549],[1008,550],[955,551],[954,161],[1009,552],[1003,553],[1001,554],[1002,485],[697,159],[698,555],[958,556],[957,557],[956,558],[1390,559],[1387,560],[1388,561],[1389,562],[65,563],[449,564],[249,159],[250,159],[472,159],[580,565],[579,566],[280,567],[66,159],[68,568],[285,426],[67,569],[281,570],[451,571],[452,572],[58,159],[450,573],[55,322],[201,172],[64,159],[853,574],[477,430],[200,575],[466,576],[245,577],[130,159],[62,322],[115,430],[284,578],[87,430],[405,579],[153,580],[232,581],[233,582],[231,583],[129,584],[150,580],[86,585],[54,322],[70,586],[253,587],[71,588],[56,589],[76,590],[75,591],[73,592],[57,593],[72,159],[234,590],[74,594],[235,595],[52,159],[53,596],[156,159],[404,426],[852,430],[282,597],[309,598],[501,599],[500,600],[283,601],[278,159],[558,602],[559,603],[553,604],[552,605],[557,159],[61,606],[567,607],[577,608],[60,585],[565,609],[566,610],[554,159],[564,322],[63,611],[69,612],[252,322],[260,613],[251,159],[426,614],[431,615],[418,616],[414,617],[341,159],[342,159],[343,159],[344,159],[345,159],[346,159],[347,159],[348,159],[349,159],[350,159],[351,159],[352,159],[353,159],[354,159],[355,159],[356,159],[357,159],[358,159],[359,159],[360,159],[361,159],[362,159],[363,159],[364,159],[365,159],[366,159],[367,159],[368,159],[369,159],[370,159],[371,159],[372,159],[373,159],[374,159],[375,159],[376,159],[377,159],[378,159],[379,159],[380,159],[381,159],[339,400],[563,618],[424,619],[340,159],[425,620],[423,621],[420,614],[561,622],[562,623],[560,624],[571,625],[569,626],[570,627],[415,628],[416,629],[419,630],[574,631],[573,632],[555,633],[568,634],[576,635],[421,636],[575,637],[556,638],[572,639],[417,628],[254,640],[267,641],[256,642],[335,643],[338,159],[334,644],[440,645],[439,646],[441,647],[436,159],[434,648],[433,322],[435,322],[442,649],[336,650],[337,159],[443,651],[269,159],[268,159],[438,652],[437,653],[275,654],[273,159],[274,159],[276,655],[272,656],[255,642],[258,642],[259,642],[422,657],[257,642],[239,658],[457,659],[246,585],[459,660],[458,585],[462,661],[463,662],[238,663],[236,322],[247,585],[237,664],[464,665],[243,666],[240,159],[241,159],[465,667],[456,668],[248,669],[461,670],[308,671],[304,597],[307,429],[306,672],[311,673],[305,674],[310,322],[324,675],[316,676],[318,677],[321,678],[315,679],[317,680],[303,681],[325,682],[320,683],[288,684],[314,685],[313,686],[333,687],[319,688],[327,689],[331,690],[330,691],[328,692],[329,693],[322,694],[286,159],[293,695],[299,696],[287,697],[291,698],[294,699],[289,700],[292,701],[296,702],[297,703],[332,704],[298,705],[300,706],[131,707],[216,708],[138,709],[136,710],[137,710],[132,711],[218,712],[229,713],[80,159],[81,159],[82,159],[83,159],[79,159],[84,159],[85,159],[127,714],[395,715],[429,159],[406,716],[428,717],[430,718],[427,719],[460,720],[453,721],[159,722],[244,723],[139,322],[135,724],[174,725],[77,322],[161,159],[116,159],[158,159],[188,159],[187,159],[184,159],[186,159],[160,159],[126,322],[191,159],[119,159],[176,159],[195,159],[193,159],[196,159],[197,159],[148,159],[164,159],[121,159],[170,159],[166,159],[163,159],[168,159],[169,159],[181,159],[185,322],[192,322],[182,322],[177,322],[155,159],[123,322],[124,322],[125,322],[172,726],[140,727],[133,728],[454,729],[198,730],[78,731],[141,732],[211,733],[230,734],[215,735],[266,736],[261,737],[265,738],[167,739],[146,740],[134,741],[209,742],[178,743],[190,744],[194,745],[165,746],[152,747],[149,748],[154,749],[151,750],[455,751],[214,752],[217,159],[212,753],[145,754],[213,755],[128,756],[118,757],[120,758],[122,759],[117,760],[179,761],[175,762],[189,763],[157,764],[199,765],[147,766],[183,767],[162,768],[180,769],[171,770],[210,771],[843,574],[242,772],[203,735],[224,773],[388,774],[387,775],[382,776],[385,777],[384,778],[383,159],[386,159],[448,779],[447,780],[445,781],[444,782],[205,159],[223,159],[207,783],[206,784],[204,585],[227,785],[226,786],[225,787],[222,788],[228,789],[219,790],[221,791],[220,792],[208,793],[89,159],[90,159],[91,159],[92,159],[93,159],[94,159],[95,159],[96,159],[97,159],[98,159],[99,159],[100,159],[101,159],[102,159],[103,159],[104,159],[105,159],[106,159],[107,159],[108,159],[109,159],[88,159],[110,159],[111,159],[112,159],[113,159],[114,159],[409,794],[407,795],[408,159],[410,796],[401,797],[402,159],[403,159],[413,798],[411,799],[389,159],[392,800],[391,801],[396,802],[397,803],[393,159],[398,804],[394,159],[390,800],[400,805],[412,806],[399,807],[1399,808],[1398,809],[1394,810],[1393,811],[1396,812],[1395,813],[1392,814],[1338,815],[1332,816],[1331,817]],"semanticDiagnosticsPerFile":[31,35,32,33,34,37,36,38,39,30]},"version":"5.2.2"} \ No newline at end of file diff --git a/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.jar b/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.jar new file mode 100644 index 0000000..07d4c4a Binary files /dev/null and b/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.jar differ diff --git a/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt.map b/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt.map new file mode 100644 index 0000000..268dc98 --- /dev/null +++ b/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt.map @@ -0,0 +1 @@ +{"version":3,"sources":["uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts","uni_modules/uni-getbatteryinfo/utssdk/interface.uts","uni_modules/uni-getbatteryinfo/utssdk/unierror.uts"],"sourcesContent":["import Context from \"android.content.Context\";\r\nimport BatteryManager from \"android.os.BatteryManager\";\r\n\r\nimport { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts'\r\nimport IntentFilter from 'android.content.IntentFilter';\r\nimport Intent from 'android.content.Intent';\r\n\r\nimport { GetBatteryInfoFailImpl } from '../unierror';\r\n\r\n/**\r\n * 异步获取电量\r\n */\r\nexport const getBatteryInfo : GetBatteryInfo = function (options : GetBatteryInfoOptions) {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoSuccess = {\r\n errMsg: 'getBatteryInfo:ok',\r\n level,\r\n isCharging: isCharging\r\n }\r\n options.success?.(res)\r\n options.complete?.(res)\r\n } else {\r\n let res = new GetBatteryInfoFailImpl(1001);\r\n options.fail?.(res)\r\n options.complete?.(res)\r\n }\r\n}\r\n\r\n/**\r\n * 同步获取电量\r\n */\r\nexport const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoResult = {\r\n level: level,\r\n isCharging: isCharging\r\n };\r\n return res;\r\n }\r\n else {\r\n /**\r\n * 无有效上下文\r\n */\r\n const res : GetBatteryInfoResult = {\r\n level: -1,\r\n isCharging: false\r\n };\r\n return res;\r\n }\r\n}\r\n","export type GetBatteryInfoSuccess = {\n\terrMsg : string,\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\nexport type GetBatteryInfoOptions = {\n\t/**\n\t\t* 接口调用结束的回调函数(调用成功、失败都会执行)\n\t\t*/\n\tsuccess ?: (res : GetBatteryInfoSuccess) => void\n\t/**\n\t\t* 接口调用失败的回调函数\n\t\t*/\n\tfail ?: (res : UniError) => void\n\t/**\n\t\t* 接口调用成功的回调\n\t\t*/\n\tcomplete ?: (res : any) => void\n}\n\nexport type GetBatteryInfoResult = {\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\n/**\n * 错误码\n * - 1001 getAppContext is null\n */\nexport type GetBatteryInfoErrorCode = 1001 ;\n/**\n * GetBatteryInfo 的错误回调参数\n */\nexport interface GetBatteryInfoFail extends IUniError {\n errCode : GetBatteryInfoErrorCode\n};\n\n/**\n* 获取电量信息\n* @param {GetBatteryInfoOptions} options\n*\n*\n* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html\n* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22\n* @since 3.6.11\n*\n* @assert () => success({errCode: 0, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:ok\", level: 60, isCharging: false })\n* @assert () => fail({errCode: 1001, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:fail getAppContext is null\" })\n*/\nexport type GetBatteryInfo = (options : GetBatteryInfoOptions) => void\n\n\nexport type GetBatteryInfoSync = () => GetBatteryInfoResult\n\ninterface Uni {\n\n\t/**\n\t * 获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @param {GetBatteryInfoOptions} options\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo({\n\t *\t\tsuccess(res) {\n\t *\t\t\tconsole.log(res);\n\t *\t\t}\n\t * })\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfo (options : GetBatteryInfoOptions) : void,\n\t/**\n\t * 同步获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo()\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfoSync():GetBatteryInfoResult\n\n}\n","import { GetBatteryInfoErrorCode, GetBatteryInfoFail } from \"./interface.uts\"\r\n/**\r\n * 错误主题\r\n */\r\nexport const UniErrorSubject = 'uni-getBatteryInfo';\r\n\r\n\r\n/**\r\n * 错误信息\r\n * @UniError\r\n */\r\nexport const UniErrors : Map = new Map([\r\n /**\r\n * 错误码及对应的错误信息\r\n */\r\n [1001, 'getBatteryInfo:fail getAppContext is null'],\r\n]);\r\n\r\n\r\n/**\r\n * 错误对象实现\r\n */\r\nexport class GetBatteryInfoFailImpl extends UniError implements GetBatteryInfoFail {\r\n\r\n /**\r\n * 错误对象构造函数\r\n */\r\n constructor(errCode : GetBatteryInfoErrorCode) {\r\n super();\r\n this.errSubject = UniErrorSubject;\r\n this.errCode = errCode;\r\n this.errMsg = UniErrors[errCode] ?? \"\";\r\n }\r\n}"],"names":[],"mappings":";;AAAA,OAAoB,uBAAyB,AAAC;AAK9C,OAAmB,sBAAwB,AAAC;AAD5C,OAAyB,4BAA8B,AAAC;AAHxD,OAA2B,yBAA2B,AAAC;;;;;;;;;;;;;;;ACDnB,WAAxB;IACX;qBAAS,MAAM,CAAC;IAIhB;oBAAQ,MAAM,CAAC;IAIf;yBAAa,OAAO,SAAA;;AAGe,WAAxB;IAIX,oBAAY,KAAM,0BAA0B,IAAI,UAAA;IAIhD,iBAAS,KAAM,aAAa,IAAI,UAAA;IAIhC,qBAAa,KAAM,GAAG,KAAK,IAAI,UAAA;;AAGG,WAAvB;IAIX;oBAAQ,MAAM,CAAC;IAIf;yBAAa,OAAO,SAAA;;UAOT,0BAA0B,MAAI;UAIzB,qBAA2B;iBAC1C,SAAU;;UAeA,kBAAkB,SAAU,0BAA0B,IAAI;UAG1D,2BAA2B;AC7DhC,IAAM,kBAAkB;AAOxB,IAAM,WAAY,6BAA6B,MAAM,IAAI,AAAI,IAAI;IAItE;AAAC,YAAI;QAAE;KAA4C;CACpD;AAMK,WAAO,yBAA+B;IAK1C,YAAY,gCAAiC,IAC3C,KAAK,GADsC;QAE3C,IAAI,CAAC,UAAU,GAAG;QAClB,IAAI,CAAC,OAAO,GAAG;QACf,IAAI,CAAC,MAAM,GAAG,SAAS,CAAC,QAAQ,IAAI;IACtC;;AFpBK,IAAM,iCAAkC,IAAU,8BAA+B,EAAA;IACtF,IAAM,UAAU,WAAW,aAAa;IACxC,IAAI,WAAW,IAAI,EAAE;QACnB,IAAM,UAAU,QAAQ,gBAAgB,CACtC,QAAQ,eAAe,EACxB,EAAA,CAAI;QACL,IAAM,QAAQ,QAAQ,cAAc,CAClC,eAAe,yBAAyB;QAG1C,IAAI,UAAU,AAAI,aAAa,OAAO,sBAAsB;QAC5D,IAAI,gBAAgB,QAAQ,gBAAgB,CAAC,IAAI,EAAE;QACnD,IAAI,SAAS,eAAe,YAAY,eAAe,YAAY,EAAE,CAAC,CAAC;QACvE,IAAI,aAAa,UAAU,eAAe,uBAAuB,IAAI,UAAU,eAAe,mBAAmB;QAEjH,IAAM,4BACJ,SAAQ,qBACR,QAAA,OACA,aAAY;QAEd,QAAQ,OAAO,SAAG;QAClB,QAAQ,QAAQ,SAAG;WACd;QACL,IAAI,MAAM,uBAA2B,IAAI;QACzC,QAAQ,IAAI,SAAG;QACf,QAAQ,QAAQ,SAAG;;AAEvB;AAKO,IAAM,yCAA0C,4BAAkC;IACvF,IAAM,UAAU,WAAW,aAAa;IACxC,IAAI,WAAW,IAAI,EAAE;QACnB,IAAM,UAAU,QAAQ,gBAAgB,CACtC,QAAQ,eAAe,EACxB,EAAA,CAAI;QACL,IAAM,QAAQ,QAAQ,cAAc,CAClC,eAAe,yBAAyB;QAG1C,IAAI,UAAU,AAAI,aAAa,OAAO,sBAAsB;QAC5D,IAAI,gBAAgB,QAAQ,gBAAgB,CAAC,IAAI,EAAE;QACnD,IAAI,SAAS,eAAe,YAAY,eAAe,YAAY,EAAE,CAAC,CAAC;QACvE,IAAI,aAAa,UAAU,eAAe,uBAAuB,IAAI,UAAU,eAAe,mBAAmB;QAEjH,IAAM,2BACJ,QAAO,OACP,aAAY;QAEd,OAAO;WAEJ;QAIH,IAAM,2BACJ,QAAO,CAAC,CAAC,EACT,aAAY,KAAK;QAEnB,OAAO;;AAEX"} \ No newline at end of file diff --git a/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/manifest.json b/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/manifest.json new file mode 100644 index 0000000..ad73e81 --- /dev/null +++ b/unpackage/cache/uts_custom_android/app-android/uts/uni_modules/uni-getbatteryinfo/manifest.json @@ -0,0 +1,23 @@ +{ + "version": "1", + "env": { + "compilerVersion": "4.76" + }, + "files": { + "utssdk/app-android/index.uts": { + "md5": "bb3ba318e763ca6ed5e3ffc574a257e9" + }, + "utssdk/interface.uts": { + "md5": "f13b23e886417c7ba57341f166a9b040" + }, + "utssdk/unierror.uts": { + "md5": "be4f1c26edb5bfaca87c6421de7b69e6" + }, + "package.json": { + "md5": "336d8ba1f84c649674e243926ee5007b" + }, + "utssdk/app-android/config.json": { + "md5": "49e34dad9b85d9ddf183e599555456fa" + } + } +} \ No newline at end of file diff --git a/unpackage/cache/uts_custom_android/uniapp-x-uts.json b/unpackage/cache/uts_custom_android/uniapp-x-uts.json new file mode 100644 index 0000000..d3ede54 --- /dev/null +++ b/unpackage/cache/uts_custom_android/uniapp-x-uts.json @@ -0,0 +1 @@ +{"duts":["uni-actionSheet","uni-theme","uni-getSystemInfo","uni-base64ToArrayBuffer","uni-arrayBufferToBase64","uni-crash","uni-storage","uni-dialogPage","uni-event","uni-exit","uni-form","uni-getAccessibilityInfo","uni-getAppAuthorizeSetting","uni-getAppBaseInfo","uni-getDeviceInfo","uni-getElementById","uni-getSystemSetting","uni-modal","uni-openAppAuthorizeSetting","uni-privacy","uni-progress","uni-prompt","uni-rpx2px","uni-rich-text"]} \ No newline at end of file diff --git a/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/classes.dex b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/classes.dex new file mode 100644 index 0000000..55d93fb Binary files /dev/null and b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/classes.dex differ diff --git a/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.jar b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.jar new file mode 100644 index 0000000..5bf586b Binary files /dev/null and b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.jar differ diff --git a/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt new file mode 100644 index 0000000..4323a4f --- /dev/null +++ b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt @@ -0,0 +1,109 @@ +@file:Suppress("UNCHECKED_CAST", "USELESS_CAST", "INAPPLICABLE_JVM_NAME", "UNUSED_ANONYMOUS_PARAMETER", "NAME_SHADOWING", "UNNECESSARY_NOT_NULL_ASSERTION") +package uts.sdk.modules.uniGetbatteryinfo +import android.content.Context +import android.content.Intent +import android.content.IntentFilter +import android.os.BatteryManager +import io.dcloud.uniapp.* +import io.dcloud.uniapp.extapi.* +import io.dcloud.uniapp.framework.* +import io.dcloud.uniapp.runtime.* +import io.dcloud.uniapp.vue.* +import io.dcloud.uniapp.vue.shared.* +import io.dcloud.unicloud.* +import io.dcloud.uts.* +import io.dcloud.uts.Map +import io.dcloud.uts.Set +import io.dcloud.uts.UTSAndroid +import kotlinx.coroutines.CoroutineScope +import kotlinx.coroutines.Deferred +import kotlinx.coroutines.Dispatchers +import kotlinx.coroutines.async +open class GetBatteryInfoSuccess ( + @JsonNotNull + open var errMsg: String, + @JsonNotNull + open var level: Number, + @JsonNotNull + open var isCharging: Boolean = false, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoSuccess", "uni_modules/uni-getbatteryinfo/utssdk/interface.uts", 1, 13) + } +} +open class GetBatteryInfoOptions ( + open var success: ((res: GetBatteryInfoSuccess) -> Unit)? = null, + open var fail: ((res: UniError) -> Unit)? = null, + open var complete: ((res: Any) -> Unit)? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoOptions", "uni_modules/uni-getbatteryinfo/utssdk/interface.uts", 12, 13) + } +} +open class GetBatteryInfoResult ( + @JsonNotNull + open var level: Number, + @JsonNotNull + open var isCharging: Boolean = false, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoResult", "uni_modules/uni-getbatteryinfo/utssdk/interface.uts", 26, 13) + } +} +typealias GetBatteryInfoErrorCode = Number +interface GetBatteryInfoFail : IUniError { + override var errCode: GetBatteryInfoErrorCode +} +typealias GetBatteryInfo = (options: GetBatteryInfoOptions) -> Unit +typealias GetBatteryInfoSync = () -> GetBatteryInfoResult +val UniErrorSubject = "uni-getBatteryInfo" +val UniErrors: Map = Map(_uA( + _uA( + 1001, + "getBatteryInfo:fail getAppContext is null" + ) +)) +open class GetBatteryInfoFailImpl : UniError, GetBatteryInfoFail, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoFailImpl", "uni_modules/uni-getbatteryinfo/utssdk/unierror.uts", 19, 14) + } + constructor(errCode: GetBatteryInfoErrorCode) : super() { + this.errSubject = UniErrorSubject + this.errCode = errCode + this.errMsg = UniErrors[errCode] ?: "" + } +} +val getBatteryInfo: GetBatteryInfo = fun(options: GetBatteryInfoOptions) { + val context = UTSAndroid.getAppContext() + if (context != null) { + val manager = context.getSystemService(Context.BATTERY_SERVICE) as BatteryManager + val level = manager.getIntProperty(BatteryManager.BATTERY_PROPERTY_CAPACITY) + var ifilter = IntentFilter(Intent.ACTION_BATTERY_CHANGED) + var batteryStatus = context.registerReceiver(null, ifilter) + var status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1) + var isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL + val res = GetBatteryInfoSuccess(errMsg = "getBatteryInfo:ok", level = level, isCharging = isCharging) + options.success?.invoke(res) + options.complete?.invoke(res) + } else { + var res = GetBatteryInfoFailImpl(1001) + options.fail?.invoke(res) + options.complete?.invoke(res) + } +} +val getBatteryInfoSync: GetBatteryInfoSync = fun(): GetBatteryInfoResult { + val context = UTSAndroid.getAppContext() + if (context != null) { + val manager = context.getSystemService(Context.BATTERY_SERVICE) as BatteryManager + val level = manager.getIntProperty(BatteryManager.BATTERY_PROPERTY_CAPACITY) + var ifilter = IntentFilter(Intent.ACTION_BATTERY_CHANGED) + var batteryStatus = context.registerReceiver(null, ifilter) + var status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1) + var isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL + val res = GetBatteryInfoResult(level = level, isCharging = isCharging) + return res + } else { + val res = GetBatteryInfoResult(level = -1, isCharging = false) + return res + } +} diff --git a/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt.map b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt.map new file mode 100644 index 0000000..d8430f2 --- /dev/null +++ b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/index.kt.map @@ -0,0 +1 @@ +{"version":3,"sources":["uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts","uni_modules/uni-getbatteryinfo/utssdk/interface.uts","uni_modules/uni-getbatteryinfo/utssdk/unierror.uts"],"sourcesContent":["import Context from \"android.content.Context\";\r\nimport BatteryManager from \"android.os.BatteryManager\";\r\n\r\nimport { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts'\r\nimport IntentFilter from 'android.content.IntentFilter';\r\nimport Intent from 'android.content.Intent';\r\n\r\nimport { GetBatteryInfoFailImpl } from '../unierror';\r\n\r\n/**\r\n * 异步获取电量\r\n */\r\nexport const getBatteryInfo : GetBatteryInfo = function (options : GetBatteryInfoOptions) {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoSuccess = {\r\n errMsg: 'getBatteryInfo:ok',\r\n level,\r\n isCharging: isCharging\r\n }\r\n options.success?.(res)\r\n options.complete?.(res)\r\n } else {\r\n let res = new GetBatteryInfoFailImpl(1001);\r\n options.fail?.(res)\r\n options.complete?.(res)\r\n }\r\n}\r\n\r\n/**\r\n * 同步获取电量\r\n */\r\nexport const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoResult = {\r\n level: level,\r\n isCharging: isCharging\r\n };\r\n return res;\r\n }\r\n else {\r\n /**\r\n * 无有效上下文\r\n */\r\n const res : GetBatteryInfoResult = {\r\n level: -1,\r\n isCharging: false\r\n };\r\n return res;\r\n }\r\n}\r\n","export type GetBatteryInfoSuccess = {\n\terrMsg : string,\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\nexport type GetBatteryInfoOptions = {\n\t/**\n\t\t* 接口调用结束的回调函数(调用成功、失败都会执行)\n\t\t*/\n\tsuccess ?: (res : GetBatteryInfoSuccess) => void\n\t/**\n\t\t* 接口调用失败的回调函数\n\t\t*/\n\tfail ?: (res : UniError) => void\n\t/**\n\t\t* 接口调用成功的回调\n\t\t*/\n\tcomplete ?: (res : any) => void\n}\n\nexport type GetBatteryInfoResult = {\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\n/**\n * 错误码\n * - 1001 getAppContext is null\n */\nexport type GetBatteryInfoErrorCode = 1001 ;\n/**\n * GetBatteryInfo 的错误回调参数\n */\nexport interface GetBatteryInfoFail extends IUniError {\n errCode : GetBatteryInfoErrorCode\n};\n\n/**\n* 获取电量信息\n* @param {GetBatteryInfoOptions} options\n*\n*\n* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html\n* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22\n* @since 3.6.11\n*\n* @assert () => success({errCode: 0, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:ok\", level: 60, isCharging: false })\n* @assert () => fail({errCode: 1001, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:fail getAppContext is null\" })\n*/\nexport type GetBatteryInfo = (options : GetBatteryInfoOptions) => void\n\n\nexport type GetBatteryInfoSync = () => GetBatteryInfoResult\n\ninterface Uni {\n\n\t/**\n\t * 获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @param {GetBatteryInfoOptions} options\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo({\n\t *\t\tsuccess(res) {\n\t *\t\t\t__f__('log','at uni_modules/uni-getbatteryinfo/utssdk/interface.uts:78',res);\n\t *\t\t}\n\t * })\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfo (options : GetBatteryInfoOptions) : void,\n\t/**\n\t * 同步获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo()\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfoSync():GetBatteryInfoResult\n\n}\n","import { GetBatteryInfoErrorCode, GetBatteryInfoFail } from \"./interface.uts\"\r\n/**\r\n * 错误主题\r\n */\r\nexport const UniErrorSubject = 'uni-getBatteryInfo';\r\n\r\n\r\n/**\r\n * 错误信息\r\n * @UniError\r\n */\r\nexport const UniErrors : Map = new Map([\r\n /**\r\n * 错误码及对应的错误信息\r\n */\r\n [1001, 'getBatteryInfo:fail getAppContext is null'],\r\n]);\r\n\r\n\r\n/**\r\n * 错误对象实现\r\n */\r\nexport class GetBatteryInfoFailImpl extends UniError implements GetBatteryInfoFail {\r\n\r\n /**\r\n * 错误对象构造函数\r\n */\r\n constructor(errCode : GetBatteryInfoErrorCode) {\r\n super();\r\n this.errSubject = UniErrorSubject;\r\n this.errCode = errCode;\r\n this.errMsg = UniErrors[errCode] ?? \"\";\r\n }\r\n}"],"names":[],"mappings":";;AAAA,OAAoB,uBAAyB,AAAC;AAK9C,OAAmB,sBAAwB,AAAC;AAD5C,OAAyB,4BAA8B,AAAC;AAHxD,OAA2B,yBAA2B,AAAC;;;;;;;;;;;;;;;;ACDnB,WAAxB;IACX;qBAAS,MAAM,CAAC;IAIhB;oBAAQ,MAAM,CAAC;IAIf;yBAAa,OAAO,SAAA;;;;;;AAGe,WAAxB;IAIX,oBAAY,KAAM,0BAA0B,IAAI,UAAA;IAIhD,iBAAS,KAAM,aAAa,IAAI,UAAA;IAIhC,qBAAa,KAAM,GAAG,KAAK,IAAI,UAAA;;;;;;AAGG,WAAvB;IAIX;oBAAQ,MAAM,CAAC;IAIf;yBAAa,OAAO,SAAA;;;;;;UAOT,0BAA0B,MAAI;UAIzB,qBAA2B;iBAC1C,SAAU;;UAeA,kBAAkB,SAAU,0BAA0B,IAAI;UAG1D,2BAA2B;AC7DhC,IAAM,kBAAkB;AAOxB,IAAM,WAAY,6BAA6B,MAAM,IAAI,AAAI,IAAI;IAItE;AAAC,YAAI;QAAE;KAA4C;CACpD;AAMK,WAAO,yBAA+B;;;;IAK1C,YAAY,gCAAiC,IAC3C,KAAK,GADsC;QAE3C,IAAI,CAAC,UAAU,GAAG;QAClB,IAAI,CAAC,OAAO,GAAG;QACf,IAAI,CAAC,MAAM,GAAG,SAAS,CAAC,QAAQ,IAAI;IACtC;;AFpBK,IAAM,iCAAkC,IAAU,8BAA+B,EAAA;IACtF,IAAM,UAAU,WAAW,aAAa;IACxC,IAAI,WAAW,IAAI,EAAE;QACnB,IAAM,UAAU,QAAQ,gBAAgB,CACtC,QAAQ,eAAe,EACxB,EAAA,CAAI;QACL,IAAM,QAAQ,QAAQ,cAAc,CAClC,eAAe,yBAAyB;QAG1C,IAAI,UAAU,AAAI,aAAa,OAAO,sBAAsB;QAC5D,IAAI,gBAAgB,QAAQ,gBAAgB,CAAC,IAAI,EAAE;QACnD,IAAI,SAAS,eAAe,YAAY,eAAe,YAAY,EAAE,CAAC,CAAC;QACvE,IAAI,aAAa,UAAU,eAAe,uBAAuB,IAAI,UAAU,eAAe,mBAAmB;QAEjH,IAAM,4BACJ,SAAQ,qBACR,QAAA,OACA,aAAY;QAEd,QAAQ,OAAO,SAAG;QAClB,QAAQ,QAAQ,SAAG;WACd;QACL,IAAI,MAAM,uBAA2B,IAAI;QACzC,QAAQ,IAAI,SAAG;QACf,QAAQ,QAAQ,SAAG;;AAEvB;AAKO,IAAM,yCAA0C,4BAAkC;IACvF,IAAM,UAAU,WAAW,aAAa;IACxC,IAAI,WAAW,IAAI,EAAE;QACnB,IAAM,UAAU,QAAQ,gBAAgB,CACtC,QAAQ,eAAe,EACxB,EAAA,CAAI;QACL,IAAM,QAAQ,QAAQ,cAAc,CAClC,eAAe,yBAAyB;QAG1C,IAAI,UAAU,AAAI,aAAa,OAAO,sBAAsB;QAC5D,IAAI,gBAAgB,QAAQ,gBAAgB,CAAC,IAAI,EAAE;QACnD,IAAI,SAAS,eAAe,YAAY,eAAe,YAAY,EAAE,CAAC,CAAC;QACvE,IAAI,aAAa,UAAU,eAAe,uBAAuB,IAAI,UAAU,eAAe,mBAAmB;QAEjH,IAAM,2BACJ,QAAO,OACP,aAAY;QAEd,OAAO;WAEJ;QAIH,IAAM,2BACJ,QAAO,CAAC,CAAC,EACT,aAAY,KAAK;QAEnB,OAAO;;AAEX"} \ No newline at end of file diff --git a/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/manifest.json b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/manifest.json new file mode 100644 index 0000000..ad73e81 --- /dev/null +++ b/unpackage/cache/uts_standard_android/app-android/uts/uni_modules/uni-getbatteryinfo/manifest.json @@ -0,0 +1,23 @@ +{ + "version": "1", + "env": { + "compilerVersion": "4.76" + }, + "files": { + "utssdk/app-android/index.uts": { + "md5": "bb3ba318e763ca6ed5e3ffc574a257e9" + }, + "utssdk/interface.uts": { + "md5": "f13b23e886417c7ba57341f166a9b040" + }, + "utssdk/unierror.uts": { + "md5": "be4f1c26edb5bfaca87c6421de7b69e6" + }, + "package.json": { + "md5": "336d8ba1f84c649674e243926ee5007b" + }, + "utssdk/app-android/config.json": { + "md5": "49e34dad9b85d9ddf183e599555456fa" + } + } +} \ No newline at end of file diff --git a/unpackage/debug/android_debug.apk b/unpackage/debug/android_debug.apk new file mode 100644 index 0000000..8eff95e Binary files /dev/null and b/unpackage/debug/android_debug.apk differ diff --git a/unpackage/dist/dev/.sourcemap/app/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.kt.map b/unpackage/dist/dev/.sourcemap/app/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.kt.map new file mode 100644 index 0000000..d8430f2 --- /dev/null +++ b/unpackage/dist/dev/.sourcemap/app/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.kt.map @@ -0,0 +1 @@ +{"version":3,"sources":["uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts","uni_modules/uni-getbatteryinfo/utssdk/interface.uts","uni_modules/uni-getbatteryinfo/utssdk/unierror.uts"],"sourcesContent":["import Context from \"android.content.Context\";\r\nimport BatteryManager from \"android.os.BatteryManager\";\r\n\r\nimport { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts'\r\nimport IntentFilter from 'android.content.IntentFilter';\r\nimport Intent from 'android.content.Intent';\r\n\r\nimport { GetBatteryInfoFailImpl } from '../unierror';\r\n\r\n/**\r\n * 异步获取电量\r\n */\r\nexport const getBatteryInfo : GetBatteryInfo = function (options : GetBatteryInfoOptions) {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoSuccess = {\r\n errMsg: 'getBatteryInfo:ok',\r\n level,\r\n isCharging: isCharging\r\n }\r\n options.success?.(res)\r\n options.complete?.(res)\r\n } else {\r\n let res = new GetBatteryInfoFailImpl(1001);\r\n options.fail?.(res)\r\n options.complete?.(res)\r\n }\r\n}\r\n\r\n/**\r\n * 同步获取电量\r\n */\r\nexport const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoResult = {\r\n level: level,\r\n isCharging: isCharging\r\n };\r\n return res;\r\n }\r\n else {\r\n /**\r\n * 无有效上下文\r\n */\r\n const res : GetBatteryInfoResult = {\r\n level: -1,\r\n isCharging: false\r\n };\r\n return res;\r\n }\r\n}\r\n","export type GetBatteryInfoSuccess = {\n\terrMsg : string,\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\nexport type GetBatteryInfoOptions = {\n\t/**\n\t\t* 接口调用结束的回调函数(调用成功、失败都会执行)\n\t\t*/\n\tsuccess ?: (res : GetBatteryInfoSuccess) => void\n\t/**\n\t\t* 接口调用失败的回调函数\n\t\t*/\n\tfail ?: (res : UniError) => void\n\t/**\n\t\t* 接口调用成功的回调\n\t\t*/\n\tcomplete ?: (res : any) => void\n}\n\nexport type GetBatteryInfoResult = {\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\n/**\n * 错误码\n * - 1001 getAppContext is null\n */\nexport type GetBatteryInfoErrorCode = 1001 ;\n/**\n * GetBatteryInfo 的错误回调参数\n */\nexport interface GetBatteryInfoFail extends IUniError {\n errCode : GetBatteryInfoErrorCode\n};\n\n/**\n* 获取电量信息\n* @param {GetBatteryInfoOptions} options\n*\n*\n* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html\n* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22\n* @since 3.6.11\n*\n* @assert () => success({errCode: 0, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:ok\", level: 60, isCharging: false })\n* @assert () => fail({errCode: 1001, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:fail getAppContext is null\" })\n*/\nexport type GetBatteryInfo = (options : GetBatteryInfoOptions) => void\n\n\nexport type GetBatteryInfoSync = () => GetBatteryInfoResult\n\ninterface Uni {\n\n\t/**\n\t * 获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @param {GetBatteryInfoOptions} options\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo({\n\t *\t\tsuccess(res) {\n\t *\t\t\t__f__('log','at uni_modules/uni-getbatteryinfo/utssdk/interface.uts:78',res);\n\t *\t\t}\n\t * })\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfo (options : GetBatteryInfoOptions) : void,\n\t/**\n\t * 同步获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo()\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfoSync():GetBatteryInfoResult\n\n}\n","import { GetBatteryInfoErrorCode, GetBatteryInfoFail } from \"./interface.uts\"\r\n/**\r\n * 错误主题\r\n */\r\nexport const UniErrorSubject = 'uni-getBatteryInfo';\r\n\r\n\r\n/**\r\n * 错误信息\r\n * @UniError\r\n */\r\nexport const UniErrors : Map = new Map([\r\n /**\r\n * 错误码及对应的错误信息\r\n */\r\n [1001, 'getBatteryInfo:fail getAppContext is null'],\r\n]);\r\n\r\n\r\n/**\r\n * 错误对象实现\r\n */\r\nexport class GetBatteryInfoFailImpl extends UniError implements GetBatteryInfoFail {\r\n\r\n /**\r\n * 错误对象构造函数\r\n */\r\n constructor(errCode : GetBatteryInfoErrorCode) {\r\n super();\r\n this.errSubject = UniErrorSubject;\r\n this.errCode = errCode;\r\n this.errMsg = UniErrors[errCode] ?? \"\";\r\n }\r\n}"],"names":[],"mappings":";;AAAA,OAAoB,uBAAyB,AAAC;AAK9C,OAAmB,sBAAwB,AAAC;AAD5C,OAAyB,4BAA8B,AAAC;AAHxD,OAA2B,yBAA2B,AAAC;;;;;;;;;;;;;;;;ACDnB,WAAxB;IACX;qBAAS,MAAM,CAAC;IAIhB;oBAAQ,MAAM,CAAC;IAIf;yBAAa,OAAO,SAAA;;;;;;AAGe,WAAxB;IAIX,oBAAY,KAAM,0BAA0B,IAAI,UAAA;IAIhD,iBAAS,KAAM,aAAa,IAAI,UAAA;IAIhC,qBAAa,KAAM,GAAG,KAAK,IAAI,UAAA;;;;;;AAGG,WAAvB;IAIX;oBAAQ,MAAM,CAAC;IAIf;yBAAa,OAAO,SAAA;;;;;;UAOT,0BAA0B,MAAI;UAIzB,qBAA2B;iBAC1C,SAAU;;UAeA,kBAAkB,SAAU,0BAA0B,IAAI;UAG1D,2BAA2B;AC7DhC,IAAM,kBAAkB;AAOxB,IAAM,WAAY,6BAA6B,MAAM,IAAI,AAAI,IAAI;IAItE;AAAC,YAAI;QAAE;KAA4C;CACpD;AAMK,WAAO,yBAA+B;;;;IAK1C,YAAY,gCAAiC,IAC3C,KAAK,GADsC;QAE3C,IAAI,CAAC,UAAU,GAAG;QAClB,IAAI,CAAC,OAAO,GAAG;QACf,IAAI,CAAC,MAAM,GAAG,SAAS,CAAC,QAAQ,IAAI;IACtC;;AFpBK,IAAM,iCAAkC,IAAU,8BAA+B,EAAA;IACtF,IAAM,UAAU,WAAW,aAAa;IACxC,IAAI,WAAW,IAAI,EAAE;QACnB,IAAM,UAAU,QAAQ,gBAAgB,CACtC,QAAQ,eAAe,EACxB,EAAA,CAAI;QACL,IAAM,QAAQ,QAAQ,cAAc,CAClC,eAAe,yBAAyB;QAG1C,IAAI,UAAU,AAAI,aAAa,OAAO,sBAAsB;QAC5D,IAAI,gBAAgB,QAAQ,gBAAgB,CAAC,IAAI,EAAE;QACnD,IAAI,SAAS,eAAe,YAAY,eAAe,YAAY,EAAE,CAAC,CAAC;QACvE,IAAI,aAAa,UAAU,eAAe,uBAAuB,IAAI,UAAU,eAAe,mBAAmB;QAEjH,IAAM,4BACJ,SAAQ,qBACR,QAAA,OACA,aAAY;QAEd,QAAQ,OAAO,SAAG;QAClB,QAAQ,QAAQ,SAAG;WACd;QACL,IAAI,MAAM,uBAA2B,IAAI;QACzC,QAAQ,IAAI,SAAG;QACf,QAAQ,QAAQ,SAAG;;AAEvB;AAKO,IAAM,yCAA0C,4BAAkC;IACvF,IAAM,UAAU,WAAW,aAAa;IACxC,IAAI,WAAW,IAAI,EAAE;QACnB,IAAM,UAAU,QAAQ,gBAAgB,CACtC,QAAQ,eAAe,EACxB,EAAA,CAAI;QACL,IAAM,QAAQ,QAAQ,cAAc,CAClC,eAAe,yBAAyB;QAG1C,IAAI,UAAU,AAAI,aAAa,OAAO,sBAAsB;QAC5D,IAAI,gBAAgB,QAAQ,gBAAgB,CAAC,IAAI,EAAE;QACnD,IAAI,SAAS,eAAe,YAAY,eAAe,YAAY,EAAE,CAAC,CAAC;QACvE,IAAI,aAAa,UAAU,eAAe,uBAAuB,IAAI,UAAU,eAAe,mBAAmB;QAEjH,IAAM,2BACJ,QAAO,OACP,aAAY;QAEd,OAAO;WAEJ;QAIH,IAAM,2BACJ,QAAO,CAAC,CAAC,EACT,aAAY,KAAK;QAEnB,OAAO;;AAEX"} \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/App.uvue.ts b/unpackage/dist/dev/.tsc/app-android/App.uvue.ts new file mode 100644 index 0000000..1264768 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/App.uvue.ts @@ -0,0 +1,44 @@ + + + // import { initTables } from './ak/sqlite.uts' + + + +let firstBackTime = 0 +const __sfc__ = defineApp({ + onLaunch: function () { + console.log('App Launch', " at App.uvue:10") + // initTables(); + + }, + onShow: function () { + console.log('App Show', " at App.uvue:15") + }, + onHide: function () { + console.log('App Hide', " at App.uvue:18") + }, + + onLastPageBackPress: function () { + console.log('App LastPageBackPress', " at App.uvue:22") + if (firstBackTime == 0) { + uni.showToast({ + title: '再按一次退出应用', + position: 'bottom', + }) + firstBackTime = Date.now() + setTimeout(() => { + firstBackTime = 0 + }, 2000) + } else if (Date.now() - firstBackTime < 2000) { + firstBackTime = Date.now() + uni.exit() + } + }, + + onExit: function () { + console.log('App Exit', " at App.uvue:39") + }, + }) + +export default __sfc__ +const GenAppStyles = [_uM([["uni-row", _pS(_uM([["flexDirection", "row"]]))], ["uni-column", _pS(_uM([["flexDirection", "column"]]))]])] diff --git a/unpackage/dist/dev/.tsc/app-android/App.uvue.ts.map b/unpackage/dist/dev/.tsc/app-android/App.uvue.ts.map new file mode 100644 index 0000000..b2284fe --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/App.uvue.ts.map @@ -0,0 +1 @@ +{"version":3,"sources":["App.uvue"],"names":[],"mappings":"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","file":"App.uvue","sourceRoot":"","sourcesContent":["\r\n\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/ak/PermissionManager.uts.ts b/unpackage/dist/dev/.tsc/app-android/ak/PermissionManager.uts.ts new file mode 100644 index 0000000..bd64e23 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/ak/PermissionManager.uts.ts @@ -0,0 +1,366 @@ +/** + * PermissionManager.uts + * + * Utility class for managing Android permissions throughout the app + * Handles requesting permissions, checking status, and directing users to settings + */ + +/** + * Common permission types that can be requested + */ +export enum PermissionType { + BLUETOOTH = 'bluetooth', + LOCATION = 'location', + STORAGE = 'storage', + CAMERA = 'camera', + MICROPHONE = 'microphone', + NOTIFICATIONS = 'notifications', + CALENDAR = 'calendar', + CONTACTS = 'contacts', + SENSORS = 'sensors' +} + +/** + * Result of a permission request + */ +type PermissionResult = { + granted: boolean; + grantedPermissions: string[]; + deniedPermissions: string[]; +} + +/** + * Manages permission requests and checks throughout the app + */ +export class PermissionManager { + /** + * Maps permission types to the actual Android permission strings + */ + private static getPermissionsForType(type: PermissionType): string[] { + switch (type) { + case PermissionType.BLUETOOTH: + return [ + 'android.permission.BLUETOOTH_SCAN', + 'android.permission.BLUETOOTH_CONNECT', + 'android.permission.BLUETOOTH_ADVERTISE' + ]; + case PermissionType.LOCATION: + return [ + 'android.permission.ACCESS_FINE_LOCATION', + 'android.permission.ACCESS_COARSE_LOCATION' + ]; + case PermissionType.STORAGE: + return [ + 'android.permission.READ_EXTERNAL_STORAGE', + 'android.permission.WRITE_EXTERNAL_STORAGE' + ]; + case PermissionType.CAMERA: + return ['android.permission.CAMERA']; + case PermissionType.MICROPHONE: + return ['android.permission.RECORD_AUDIO']; + case PermissionType.NOTIFICATIONS: + return ['android.permission.POST_NOTIFICATIONS']; + case PermissionType.CALENDAR: + return [ + 'android.permission.READ_CALENDAR', + 'android.permission.WRITE_CALENDAR' + ]; + case PermissionType.CONTACTS: + return [ + 'android.permission.READ_CONTACTS', + 'android.permission.WRITE_CONTACTS' + ]; + case PermissionType.SENSORS: + return ['android.permission.BODY_SENSORS']; + default: + return []; + } + } + + /** + * Get appropriate display name for a permission type + */ + private static getPermissionDisplayName(type: PermissionType): string { + switch (type) { + case PermissionType.BLUETOOTH: + return '蓝牙'; + case PermissionType.LOCATION: + return '位置'; + case PermissionType.STORAGE: + return '存储'; + case PermissionType.CAMERA: + return '相机'; + case PermissionType.MICROPHONE: + return '麦克风'; + case PermissionType.NOTIFICATIONS: + return '通知'; + case PermissionType.CALENDAR: + return '日历'; + case PermissionType.CONTACTS: + return '联系人'; + case PermissionType.SENSORS: + return '身体传感器'; + default: + return '未知权限'; + } + } + + /** + * Check if a permission is granted + * @param type The permission type to check + * @returns True if the permission is granted, false otherwise + */ + static isPermissionGranted(type: PermissionType): boolean { + + try { + const permissions = this.getPermissionsForType(type); + const activity = UTSAndroid.getUniActivity(); + + if (activity == null || permissions.length === 0) { + return false; + } + + // Check each permission in the group + for (const permission of permissions) { + if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) { + return false; + } + } + + return true; + } catch (e) { + __f__('error','at ak/PermissionManager.uts:132',`Error checking ${type} permission:`, e); + return false; + } + + + + + + } + + /** + * Request a permission from the user + * @param type The permission type to request + * @param callback Function to call with the result of the permission request + * @param showRationale Whether to show a rationale dialog if permission was previously denied + */ + static requestPermission( + type: PermissionType, + callback: (result: PermissionResult) => void, + showRationale: boolean = true + ): void { + + try { + const permissions = this.getPermissionsForType(type); + const activity = UTSAndroid.getUniActivity(); + + if (activity == null || permissions.length === 0) { + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: permissions + }); + return; + } + + // Check if already granted + let allGranted = true; + for (const permission of permissions) { + if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) { + allGranted = false; + break; + } + } + + if (allGranted) { + callback({ + granted: true, + grantedPermissions: permissions, + deniedPermissions: [] + }); + return; + } + + // Request the permissions + UTSAndroid.requestSystemPermission( + activity, + permissions, + (granted: boolean, grantedPermissions: string[]) => { + if (granted) { + callback({ + granted: true, + grantedPermissions: grantedPermissions, + deniedPermissions: [] + }); + } else if (showRationale) { + // Show rationale dialog + this.showPermissionRationale(type, callback); + } else { + // Just report the denial + callback({ + granted: false, + grantedPermissions: grantedPermissions, + deniedPermissions: this.getDeniedPermissions(permissions, grantedPermissions) + }); + } + }, + (denied: boolean, deniedPermissions: string[]) => { + callback({ + granted: false, + grantedPermissions: this.getGrantedPermissions(permissions, deniedPermissions), + deniedPermissions: deniedPermissions + }); + } + ); + } catch (e) { + __f__('error','at ak/PermissionManager.uts:217',`Error requesting ${type} permission:`, e); + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + }); + } + + + + + + + + + + + } + + /** + * Show a rationale dialog explaining why the permission is needed + */ + private static showPermissionRationale( + type: PermissionType, + callback: (result: PermissionResult) => void + ): void { + const permissionName = this.getPermissionDisplayName(type); + + uni.showModal({ + title: '权限申请', + content: `需要${permissionName}权限才能使用相关功能`, + confirmText: '去设置', + cancelText: '取消', + success: (result) => { + if (result.confirm) { + this.openAppSettings(); + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + }); + } else { + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + }); + } + } + }); + } + + /** + * Open the app settings page + */ + static openAppSettings(): void { + + try { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const intent = new android.content.Intent(); + intent.setAction("android.settings.APPLICATION_DETAILS_SETTINGS"); + const uri = android.net.Uri.fromParts("package", context.getPackageName(), null); + intent.setData(uri); + intent.addFlags(android.content.Intent.FLAG_ACTIVITY_NEW_TASK); + context.startActivity(intent); + } + } catch (e) { + __f__('error','at ak/PermissionManager.uts:285','Failed to open app settings', e); + uni.showToast({ + title: '请手动前往系统设置修改应用权限', + icon: 'none', + duration: 3000 + }); + } + + + + + + + + + + } + + /** + * Helper to get the list of granted permissions + */ + private static getGrantedPermissions(allPermissions: string[], deniedPermissions: string[]): string[] { + return allPermissions.filter(p => !deniedPermissions.includes(p)); + } + + /** + * Helper to get the list of denied permissions + */ + private static getDeniedPermissions(allPermissions: string[], grantedPermissions: string[]): string[] { + return allPermissions.filter(p => !grantedPermissions.includes(p)); + } + + /** + * Request multiple permission types at once + * @param types Array of permission types to request + * @param callback Function to call when all permissions have been processed + */ + static requestMultiplePermissions( + types: PermissionType[], + callback: (results: Map) => void + ): void { + if (types.length === 0) { + callback(new Map()); + return; + } + + const results = new Map(); + let remaining = types.length; + + for (const type of types) { + this.requestPermission( + type, + (result) => { + results.set(type, result); + remaining--; + + if (remaining === 0) { + callback(results); + } + }, + true + ); + } + } + + /** + * Convenience method to request Bluetooth permissions + * @param callback Function to call after the permission request + */ + static requestBluetoothPermissions(callback: (granted: boolean) => void): void { + this.requestPermission(PermissionType.BLUETOOTH, (result) => { + // For Bluetooth, we also need location permissions on Android + if (result.granted) { + this.requestPermission(PermissionType.LOCATION, (locationResult) => { + callback(locationResult.granted); + }); + } else { + callback(false); + } + }); + } +} \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/main.uts.ts b/unpackage/dist/dev/.tsc/app-android/main.uts.ts new file mode 100644 index 0000000..4dff2f6 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/main.uts.ts @@ -0,0 +1,41 @@ +import 'F:/HBuilderX/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/index.ts';import App from './App.uvue' + +import { createSSRApp } from 'vue' +export function createApp() { + const app = createSSRApp(App) + return { + app + } +} +export function main(app: IApp) { + definePageRoutes(); + defineAppConfig(); + (createApp()['app'] as VueApp).mount(app, GenUniApp()); +} + +export class UniAppConfig extends io.dcloud.uniapp.appframe.AppConfig { + override name: string = "akbleserver" + override appid: string = "__UNI__95B2570" + override versionName: string = "1.0.1" + override versionCode: string = "101" + override uniCompilerVersion: string = "4.76" + + constructor() { super() } +} + +import GenPagesAkbletestClass from './pages/akbletest.uvue' +function definePageRoutes() { +__uniRoutes.push({ path: "pages/akbletest", component: GenPagesAkbletestClass, meta: { isQuit: true } as UniPageMeta, style: _uM([["navigationBarTitleText","akble"]]) } as UniPageRoute) +} +const __uniTabBar: Map | null = null +const __uniLaunchPage: Map = _uM([["url","pages/akbletest"],["style",_uM([["navigationBarTitleText","akble"]])]]) +function defineAppConfig(){ + __uniConfig.entryPagePath = '/pages/akbletest' + __uniConfig.globalStyle = _uM([["navigationBarTextStyle","black"],["navigationBarTitleText","体测训练"],["navigationBarBackgroundColor","#F8F8F8"],["backgroundColor","#F8F8F8"]]) + __uniConfig.getTabBarConfig = ():Map | null => null + __uniConfig.tabBar = __uniConfig.getTabBarConfig() + __uniConfig.conditionUrl = '' + __uniConfig.uniIdRouter = _uM() + + __uniConfig.ready = true +} diff --git a/unpackage/dist/dev/.tsc/app-android/node-modules/@dcloudio/uni-console/src/runtime/app/index.ts b/unpackage/dist/dev/.tsc/app-android/node-modules/@dcloudio/uni-console/src/runtime/app/index.ts new file mode 100644 index 0000000..fe1773e --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/node-modules/@dcloudio/uni-console/src/runtime/app/index.ts @@ -0,0 +1,34 @@ +import { initRuntimeSocket } from './socket' + +export function initRuntimeSocketService(): Promise { + const hosts: string = process.env.UNI_SOCKET_HOSTS + const port: string = process.env.UNI_SOCKET_PORT + const id: string = process.env.UNI_SOCKET_ID + if (hosts == '' || port == '' || id == '') return Promise.resolve(false) + let socketTask: SocketTask | null = null + __registerWebViewUniConsole( + (): string => { + return process.env.UNI_CONSOLE_WEBVIEW_EVAL_JS_CODE + }, + (data: string) => { + socketTask?.send({ + data, + } as SendSocketMessageOptions) + } + ) + return Promise.resolve() + .then((): Promise => { + return initRuntimeSocket(hosts, port, id).then((socket): boolean => { + if (socket == null) { + return false + } + socketTask = socket + return true + }) + }) + .catch((): boolean => { + return false + }) +} + +initRuntimeSocketService() diff --git a/unpackage/dist/dev/.tsc/app-android/node-modules/@dcloudio/uni-console/src/runtime/app/socket.ts b/unpackage/dist/dev/.tsc/app-android/node-modules/@dcloudio/uni-console/src/runtime/app/socket.ts new file mode 100644 index 0000000..8d4da95 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/node-modules/@dcloudio/uni-console/src/runtime/app/socket.ts @@ -0,0 +1,61 @@ +/// +// 之所以又写了一份,是因为外层的socket,connectSocket的时候必须传入multiple:true +// 但是android又不能传入,目前代码里又不能写条件编译之类的。 +export function initRuntimeSocket( + hosts: string, + port: string, + id: string +): Promise { + if (hosts == '' || port == '' || id == '') return Promise.resolve(null) + return hosts + .split(',') + .reduce>( + ( + promise: Promise, + host: string + ): Promise => { + return promise.then((socket): Promise => { + if (socket != null) return Promise.resolve(socket) + return tryConnectSocket(host, port, id) + }) + }, + Promise.resolve(null) + ) +} + +const SOCKET_TIMEOUT = 500 +function tryConnectSocket( + host: string, + port: string, + id: string +): Promise { + return new Promise((resolve, reject) => { + const socket = uni.connectSocket({ + url: `ws://${host}:${port}/${id}`, + fail() { + resolve(null) + }, + }) + const timer = setTimeout(() => { + // @ts-expect-error + socket.close({ + code: 1006, + reason: 'connect timeout', + } as CloseSocketOptions) + resolve(null) + }, SOCKET_TIMEOUT) + + socket.onOpen((e) => { + clearTimeout(timer) + resolve(socket) + }) + socket.onClose((e) => { + clearTimeout(timer) + resolve(null) + }) + socket.onError((e) => { + clearTimeout(timer) + resolve(null) + }) + }) +} diff --git a/unpackage/dist/dev/.tsc/app-android/output.js b/unpackage/dist/dev/.tsc/app-android/output.js new file mode 100644 index 0000000..e225c3f --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/output.js @@ -0,0 +1,21 @@ +'use strict'; + +require('android.content.Context'); +require('android.bluetooth.BluetoothAdapter'); +require('android.bluetooth.BluetoothManager'); +require('android.bluetooth.BluetoothDevice'); +require('android.bluetooth.BluetoothGatt'); +require('android.bluetooth.BluetoothGattCallback'); +require('android.bluetooth.le.ScanCallback'); +require('android.bluetooth.le.ScanResult'); +require('android.bluetooth.le.ScanSettings'); +require('android.os.Handler'); +require('android.os.Looper'); +require('androidx.core.content.ContextCompat'); +require('android.content.pm.PackageManager'); +require('android.bluetooth.BluetoothGattService'); +require('android.bluetooth.BluetoothGattCharacteristic'); +require('android.bluetooth.BluetoothGattDescriptor'); +require('java.util.UUID'); +require('vue'); + diff --git a/unpackage/dist/dev/.tsc/app-android/pages/akbletest.uvue.ts b/unpackage/dist/dev/.tsc/app-android/pages/akbletest.uvue.ts new file mode 100644 index 0000000..7ddb614 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/pages/akbletest.uvue.ts @@ -0,0 +1,782 @@ + + import { BluetoothService } from '@/uni_modules/ak-sbsrv/utssdk/interface.uts' + // Platform-specific entrypoint: import the platform index per build target to avoid bundler including Android-only code in web builds + + import { bluetoothService } from '@/uni_modules/ak-sbsrv/utssdk/app-android/index.uts' + + + + + import type { BleDevice, BleService, BleCharacteristic } from '@/uni_modules/ak-sbsrv/utssdk/interface.uts' + import { ProtocolHandler } from '@/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts' + + + import { dfuManager } from '@/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts' + + import { PermissionManager } from '@/ak/PermissionManager.uts' + type ShowingCharacteristicsFor = { __$originalPosition?: UTSSourceMapPosition<"ShowingCharacteristicsFor", "pages/akbletest.uvue", 107, 7>; + deviceId : string, + serviceId : string + } + + const __sfc__ = defineComponent({ + data() { + return { + scanning: false, + connecting: false, + disconnecting: false, + devices: [] as BleDevice[], + connectedIds: [] as string[], + logs: [] as string[], + showingServicesFor: '', + services: [] as BleService[], + showingCharacteristicsFor: { deviceId: '', serviceId: '' } as ShowingCharacteristicsFor, + characteristics: [] as BleCharacteristic[], + // 新增协议相关参数 + protocolDeviceId: '', + protocolServiceId: '', + protocolWriteCharId: '', + protocolNotifyCharId: '', + // protocol handler instances/cache + protocolHandlerMap: new Map(), + protocolHandler: null as ProtocolHandler | null, + // optional services input (comma-separated UUIDs) + optionalServicesInput: '', + // presets for common BLE services (label -> UUID). 'custom' allows free-form input. + presetOptions: [ + { label: '无', value: '' }, + { label: 'Battery Service (180F)', value: '0000180f-0000-1000-8000-00805f9b34fb' }, + { label: 'Device Information (180A)', value: '0000180a-0000-1000-8000-00805f9b34fb' }, + { label: 'Generic Attribute (1801)', value: '00001801-0000-1000-8000-00805f9b34fb' }, + { label: 'Nordic DFU', value: '00001530-1212-efde-1523-785feabcd123' }, + { label: 'Nordic UART (NUS)', value: '6e400001-b5a3-f393-e0a9-e50e24dcca9e' }, + { label: '自定义', value: 'custom' } + ], + presetSelected: '', + // map of characteristicId -> boolean (is currently subscribed) + notifyingMap: new Map(), + } + }, + mounted() { + PermissionManager.requestBluetoothPermissions((granted : boolean) => { + if (!granted) { + uni.showToast({ title: '请授权蓝牙和定位权限', icon: 'none' }); + } + + + }); + this.log('页面 mounted: 初始化事件监听和蓝牙权限请求完成') + // deviceFound - only accept devices whose name starts with 'CF' or 'BCL' + bluetoothService.on('deviceFound', (payload) => { + try { + // this.log('[event] deviceFound -> ' + this._fmt(payload)) + // console.log('[event] deviceFound -> ' + this._fmt(payload)) + // payload can be UTSJSONObject-like or plain object. Normalize. + let rawDevice = payload?.device; + if (rawDevice == null) { + this.log('[event] deviceFound - payload.device is null, ignoring'); + return; + } + + // extract name + let name : string | null = rawDevice.name; + + if (name == null) { + this.log('[event] deviceFound - 无名称,忽略: ' + this._fmt(rawDevice as any)) + return; + } + + const n = name as string; + if (!(n.startsWith('CF') || n.startsWith('BCL'))) { + this.log('[event] deviceFound - 名称不匹配前缀,忽略: ' + n) + return; + } + + const exists = this.devices.some(d => d != null && d.name == n); + + if (!exists) { + // rawDevice is non-null here per earlier guard + this.devices.push(rawDevice as BleDevice); + const deviceIdStr = (rawDevice.deviceId != null) ? rawDevice.deviceId : ''; + this.log('发现设备: ' + n + ' (' + deviceIdStr + ')'); + } else { + const deviceIdStr = (rawDevice.deviceId != null) ? rawDevice.deviceId : ''; + this.log('发现重复设备: ' + n + ' (' + deviceIdStr + ')') + } + } catch (err) { + this.log('[error] deviceFound handler error: ' + getErrorMessage(err)) + console.log(err, " at pages/akbletest.uvue:198") + } + }) + + // scanFinished + bluetoothService.on('scanFinished', (payload) => { + try { + this.scanning = false + this.log('[event] scanFinished -> ' + this._fmt(payload)) + } catch (err) { + this.log('[error] scanFinished handler error: ' + getErrorMessage(err)) + } + }) + + // connectionStateChanged + bluetoothService.on('connectionStateChanged', (payload) => { + try { + this.log('[event] connectionStateChanged -> ' + this._fmt(payload)) + if (payload != null) { + const device = payload.device + const state = payload.state + this.log(`设备 ${device?.deviceId} 连接状态变为: ${state}`) + // maintain connectedIds + if (state == 2) { + if (device != null && device.deviceId != null && !this.connectedIds.includes(device.deviceId)) { + this.connectedIds.push(device.deviceId) + this.log(`已记录已连接设备: ${device.deviceId}`) + } + } else if (state == 0) { + if (device != null && device.deviceId != null) { + this.connectedIds = this.connectedIds.filter(id => id !== device.deviceId) + this.log(`已移除已断开设备: ${device.deviceId}`) + } + } + } + } catch (err) { + this.log('[error] connectionStateChanged handler error: ' + getErrorMessage(err)) + } + }) + }, + methods: { + async startDfuFlow(deviceId : string, staticFilePath : string = '') { + if (staticFilePath != null && staticFilePath !== '') { + this.log('DFU 开始: 使用内置固件文件 ' + staticFilePath) + } else { + this.log('DFU 开始: 请选择固件文件') + } + try { + let chosenPath : string | null = null + let fileName : string | null = null + if (staticFilePath != null && staticFilePath !== '') { + // Use the app's bundled static file path + chosenPath = staticFilePath.replace(/^\/+/, '') + const tmpName = staticFilePath.split(/[\/]/).pop() + fileName = (tmpName != null && tmpName !== '') ? tmpName : staticFilePath + } else { + const res = await new Promise((resolve, reject) => { + uni.chooseFile({ count: 1, success: (r) => resolve(r), fail: (e) => reject(e) }) + }) + console.log(res, " at pages/akbletest.uvue:257") + // Generator-friendly: avoid property iteration or bracket indexing. + // Serialize and regex-match common file fields (path/uri/tempFilePath/name). + try { + const s = (() => { try { return JSON.stringify(res); } catch (e) { return ''; } })() + const m = s.match(/"(?:path|uri|tempFilePath|temp_file_path|tempFilePath|name)"\s*:\s*"([^"]+)"/i) + if (m != null && m.length >= 2) { + const capturedCandidate : string | null = (m[1] != null ? m[1] : null) + const captured : string = capturedCandidate != null ? capturedCandidate : '' + if (captured !== '') { + chosenPath = captured + const toTest : string = captured + if (!(/^[a-zA-Z]:\\|^\\\//.test(toTest) || /:\/\//.test(toTest))) { + const m2 = s.match(/"(?:path|uri|tempFilePath|temp_file_path|tempFilePath)"\s*:\s*"([^"]+)"/i) + if (m2 != null && m2.length >= 2 && m2[1] != null) { + const pathCandidate : string = m2[1] != null ? ('' + m2[1]) : '' + if (pathCandidate !== '') chosenPath = pathCandidate + } + } + } + } + const nameMatch = s.match(/"name"\s*:\s*"([^"]+)"/i) + if (nameMatch != null && nameMatch.length >= 2 && nameMatch[1] != null) { + const nm : string = nameMatch[1] != null ? ('' + nameMatch[1]) : '' + if (nm !== '') fileName = nm + } + } catch (err) { /* ignore */ } + } + if (chosenPath == null || chosenPath == '') { + this.log('未选择文件') + return + } + // filePath is non-null and non-empty here + const fpStr : string = chosenPath as string + const lastSeg = fpStr.split(/[\/]/).pop(); + const displayName = (fileName != null && fileName !== '') ? fileName : (lastSeg != null && lastSeg !== '' ? lastSeg : fpStr) + this.log('已选文件: ' + displayName + ' 路径: ' + fpStr) + const bytes = await this._readFileAsUint8Array(fpStr) + this.log('固件读取完成, 大小: ' + bytes.length) + try { + await dfuManager.startDfu(deviceId, bytes, { + useNordic: false, + onProgress: (p : number) => this.log('DFU 进度: ' + p + '%'), + onLog: (s : string) => this.log('DFU: ' + s), + controlTimeout: 30000 + }) + this.log('DFU 完成') + } catch (e) { + this.log('DFU 失败: ' + getErrorMessage(e)) + } + } catch (e) { + console.log('选择或读取固件失败: ' + e, " at pages/akbletest.uvue:308") + } + }, + + _readFileAsUint8Array(path : string) : Promise { + return new Promise((resolve, reject) => { + try { + console.log('should readfile', " at pages/akbletest.uvue:315") + const fsm = uni.getFileSystemManager() + console.log(fsm, " at pages/akbletest.uvue:317") + // Read file as ArrayBuffer directly to avoid base64 encoding issues + fsm.readFile({ + filePath: path, success: (res) => { + try { + const data = res.data as ArrayBuffer + const arr = new Uint8Array(data) + resolve(arr) + } catch (e) { reject(e) } + }, fail: (err) => { reject(err) } + }) + } catch (e) { reject(e) } + }) + }, + + log(msg : string) { + const ts = new Date().toISOString(); + this.logs.unshift(`[${ts}] ${msg}`) + if (this.logs.length > 100) this.logs.length = 100 + }, + _fmt(obj : any) : string { + try { + if (obj == null) return 'null' + if (typeof obj == 'string') return obj + return JSON.stringify(obj) + } catch (e) { + return '' + obj + } + }, + onPresetChange(e : any) { + try { + // Some platforms emit { detail: { value: 'x' } }, others emit { value: 'x' } or just 'x'. + // Serialize and regex-extract to avoid direct property access that the UTS->Kotlin generator may emit incorrectly. + const s = (() => { try { return JSON.stringify(e); } catch (err) { return ''; } })() + let val : string = this.presetSelected + // try detail.value first + const m = s.match(/"detail"\s*:\s*\{[^}]*"value"\s*:\s*"([^\"]+)"/i) + if (m != null && m.length >= 2 && m[1] != null) { + val = '' + m[1] + } else { + const m2 = s.match(/"value"\s*:\s*"([^\"]+)"/i) + if (m2 != null && m2.length >= 2 && m2[1] != null) { + val = '' + m2[1] + } + } + this.presetSelected = val + if (val == 'custom' || val == '') { + this.log('已选择预设: ' + (val == 'custom' ? '自定义' : '无')) + return; + } + this.optionalServicesInput = val; + this.log('已选择预设服务 UUID: ' + val) + } catch (err) { + this.log('[error] onPresetChange: ' + getErrorMessage(err)) + } + }, + scanDevices() { + try { + this.scanning = true + this.devices = [] + // prepare optional services: prefer free-form input, otherwise use selected preset (unless preset is 'custom' or empty) + let raw = (this.optionalServicesInput != null ? this.optionalServicesInput : '').trim(); + if (raw.length == 0 && this.presetSelected != null && this.presetSelected !== '' && this.presetSelected !== 'custom') { + raw = this.presetSelected; + } + // normalize helper: expand 16-bit UUIDs like '180F' to full 128-bit UUIDs + const normalize = (s : string) => { + if (s == null || s.length == 0) return ''; + const u = s.toLowerCase().replace(/^0x/, '').trim(); + const hex = u.replace(/[^0-9a-f]/g, ''); + if (/^[0-9a-f]{4}$/.test(hex)) return `0000${hex}-0000-1000-8000-00805f9b34fb`; + return s; + }; + const optionalServices = raw.length > 0 ? raw.split(',').map(s => normalize(s.trim())).filter(s => s.length > 0) : [] + this.log('开始扫描... optionalServices=' + JSON.stringify(optionalServices)) + bluetoothService.scanDevices({ "protocols": ['BLE'], "optionalServices": optionalServices }) + .then(() => { + this.log('scanDevices resolved') + }) + .catch((e) => { + this.log('[error] scanDevices failed: ' + getErrorMessage(e)) + this.scanning = false + }) + } catch (err) { + this.log('[error] scanDevices thrown: ' + getErrorMessage(err)) + this.scanning = false + } + }, + connect(deviceId : string) { + this.connecting = true + this.log(`connect start -> ${deviceId}`) + try { + bluetoothService.connectDevice(deviceId, 'BLE', { timeout: 10000 }).then(() => { + if (!this.connectedIds.includes(deviceId)) this.connectedIds.push(deviceId) + this.log('连接成功: ' + deviceId) + }).catch((e) => { + this.log('连接失败: ' + getErrorMessage(e!)); + }).finally(() => { + this.connecting = false + this.log(`connect finished -> ${deviceId}`) + }) + } catch (err) { + this.log('[error] connect thrown: ' + getErrorMessage(err)) + this.connecting = false + } + }, + disconnect(deviceId : string) { + if (!this.connectedIds.includes(deviceId)) return + this.disconnecting = true + this.log(`disconnect start -> ${deviceId}`) + bluetoothService.disconnectDevice(deviceId, 'BLE').then(() => { + this.log('已断开: ' + deviceId) + this.connectedIds = this.connectedIds.filter(id => id !== deviceId) + // 清理协议处理器缓存 + this.protocolHandlerMap.delete(deviceId) + }).catch((e) => { + this.log('断开失败: ' + getErrorMessage(e!)); + }).finally(() => { + this.disconnecting = false + this.log(`disconnect finished -> ${deviceId}`) + }) + }, + showServices(deviceId : string) { + this.showingServicesFor = deviceId + this.services = [] + this.log(`showServices start -> ${deviceId}`) + bluetoothService.getServices(deviceId).then((list) => { + this.log('showServices result -> ' + this._fmt(list)) + this.services = list as BleService[] + this.log('服务数: ' + (list != null ? list.length : 0) + ' [' + deviceId + ']'); + }).catch((e) => { + this.log('获取服务失败: ' + getErrorMessage(e!)); + }).finally(() => { + this.log(`showServices finished -> ${deviceId}`) + }); + }, + closeServices() { + this.showingServicesFor = '' + this.services = [] + }, + showCharacteristics(deviceId : string, serviceId : string) { + this.showingCharacteristicsFor = { deviceId, serviceId } + this.characteristics = [] + bluetoothService.getCharacteristics(deviceId, serviceId).then((list) => { + this.characteristics = list as BleCharacteristic[] + console.log('特征数: ' + (list != null ? list.length : 0) + ' [' + deviceId + ']', " at pages/akbletest.uvue:462"); + // 自动查找可用的写入和通知特征 + const writeChar = this.characteristics.find(c => c.properties.write) + const notifyChar = this.characteristics.find(c => c.properties.notify) + if (writeChar != null && notifyChar != null) { + this.protocolDeviceId = deviceId + this.protocolServiceId = serviceId + this.protocolWriteCharId = writeChar.uuid + this.protocolNotifyCharId = notifyChar.uuid + let abs = bluetoothService as BluetoothService + this.protocolHandler = new ProtocolHandler(abs) + let handler = this.protocolHandler + handler?.setConnectionParameters(deviceId, serviceId, writeChar.uuid, notifyChar.uuid) + handler?.initialize()?.then(() => { + console.log("协议处理器已初始化,可进行协议测试", " at pages/akbletest.uvue:476") + })?.catch(e => { + console.log("协议处理器初始化失败: " + getErrorMessage(e!), " at pages/akbletest.uvue:478") + }) + } + }).catch((e) => { + console.log('获取特征失败: ' + getErrorMessage(e!), " at pages/akbletest.uvue:482"); + }); + // tracking notifying state + // this.$set(this, 'notifyingMap', this.notifyingMap || {}); + }, + closeCharacteristics() { + this.showingCharacteristicsFor = { deviceId: '', serviceId: '' } + this.characteristics = [] + }, + charProps(char : BleCharacteristic) : string { + const p = char.properties + const parts = [] as string[] + if (p.read) parts.push('R') + if (p.write) parts.push('W') + if (p.notify) parts.push('N') + if (p.indicate) parts.push('I') + return parts.join('/') + // return [p.read ? 'R' : '', p.write ? 'W' : '', p.notify ? 'N' : '', p.indicate ? 'I' : ''].filter(Boolean).join('/') + }, + isNotifying(uuid : string) { + return this.notifyingMap.has(uuid) && this.notifyingMap.get(uuid) == true + }, + async readCharacteristic(deviceId : string, serviceId : string, charId : string) { + try { + this.log(`readCharacteristic ${charId} ...`) + const buf = await bluetoothService.readCharacteristic(deviceId, serviceId, charId) + let text = '' + try { text = new TextDecoder().decode(new Uint8Array(buf)) } catch (e) { text = '' } + const hex = Array.from(new Uint8Array(buf)).map(b => b.toString(16).padStart(2, '0')).join(' ') + console.log(`读取 ${charId}: text='${text}' hex='${hex}'`, " at pages/akbletest.uvue:511") + this.log(`读取 ${charId}: text='${text}' hex='${hex}'`) + + } catch (e) { + this.log('读取特征失败: ' + getErrorMessage(e)) + } + }, + async writeCharacteristic(deviceId : string, serviceId : string, charId : string) { + try { + const payload = new Uint8Array([0x01]) + const ok = await bluetoothService.writeCharacteristic(deviceId, serviceId, charId, payload, null) + if (ok) this.log(`写入 ${charId} 成功`); + else this.log(`写入 ${charId} 失败`); + } catch (e) { + this.log('写入特征失败: ' + getErrorMessage(e)) + } + }, + async toggleNotify(deviceId : string, serviceId : string, charId : string) { + try { + const map = this.notifyingMap + const cur = map.get(charId) == true + if (cur) { + // unsubscribe + await bluetoothService.unsubscribeCharacteristic(deviceId, serviceId, charId) + map.set(charId, false) + this.log(`取消订阅 ${charId}`) + } else { + // subscribe with callback + await bluetoothService.subscribeCharacteristic(deviceId, serviceId, charId, (payload : any) => { + let data : ArrayBuffer | null = null + try { + if (payload instanceof ArrayBuffer) { + data = payload + } else if (payload != null && typeof payload == 'string') { + // some runtimes deliver base64 strings + try { + const s = atob(payload) + const tmp = new Uint8Array(s.length) + for (let i = 0; i < s.length; i++) { + const ch = s.charCodeAt(i) + tmp[i] = (ch == null) ? 0 : (ch & 0xff) + } + data = tmp.buffer + } catch (e) { data = null } + } else if (payload != null && (payload as UTSJSONObject).get('data') instanceof ArrayBuffer) { + data = (payload as UTSJSONObject).get('data') as ArrayBuffer + } + const arr = data != null ? new Uint8Array(data) : new Uint8Array([]) + const hex = Array.from(arr).map(b => b.toString(16).padStart(2, '0')).join(' ') + this.log(`notify ${charId}: ${hex}`) + } catch (e) { this.log('notify callback error: ' + getErrorMessage(e)) } + }) + map.set(charId, true) + this.log(`订阅 ${charId}`) + } + } catch (e) { + this.log('订阅/取消订阅失败: ' + getErrorMessage(e)) + } + }, + autoConnect() { + if (this.connecting) return; + this.connecting = true; + const toConnect = this.devices.filter(d => !this.connectedIds.includes(d.deviceId)); + if (toConnect.length == 0) { + this.log('没有可自动连接的设备'); + this.connecting = false; + return; + } + let successCount = 0; + let failCount = 0; + let finished = 0; + toConnect.forEach(device => { + bluetoothService.connectDevice(device.deviceId, 'BLE', { timeout: 10000 }).then(() => { + if (!this.connectedIds.includes(device.deviceId)) this.connectedIds.push(device.deviceId); + this.log('自动连接成功: ' + device.deviceId); + successCount++; + // this.getOrInitProtocolHandler(device.deviceId); + }).catch((e) => { + this.log('自动连接失败: ' + device.deviceId + ' ' + getErrorMessage(e!)); + failCount++; + }).finally(() => { + finished++; + if (finished == toConnect.length) { + this.connecting = false; + this.log(`自动连接完成,成功${successCount},失败${failCount}`); + } + }); + }); + }, + autoDiscoverInterfaces(deviceId : string) { + this.log('自动发现接口中...') + bluetoothService.getAutoBleInterfaces(deviceId) + .then((res) => { + console.log(res, " at pages/akbletest.uvue:604") + this.log('自动发现接口成功: ' + JSON.stringify(res)) + }) + .catch((e) => { + console.log(e, " at pages/akbletest.uvue:608") + this.log('自动发现接口失败: ' + getErrorMessage(e!)) + }) + }, + // 新增:测试电量功能 + async getOrInitProtocolHandler(deviceId : string) : Promise { + let handler = this.protocolHandlerMap.get(deviceId); + if (handler == null) { + // 自动发现接口 + const res = await bluetoothService.getAutoBleInterfaces(deviceId); + handler = new ProtocolHandler(bluetoothService as BluetoothService); + handler.setConnectionParameters(deviceId, res.serviceId, res.writeCharId, res.notifyCharId); + await handler.initialize(); + this.protocolHandlerMap.set(deviceId, handler); + this.log(`协议处理器已初始化: ${deviceId}`); + } + return handler!; + }, + + async getDeviceInfo(deviceId : string) { + this.log('获取设备信息中...'); + try { + // First try protocol handler (if device exposes custom protocol) + try { + const handler = await this.getOrInitProtocolHandler(deviceId); + // 获取电量 + const battery = await handler.testBatteryLevel(); + this.log('协议: 电量: ' + battery); + // 获取软件/硬件版本 + const swVersion = await handler.testVersionInfo(false); + this.log('协议: 软件版本: ' + swVersion); + const hwVersion = await handler.testVersionInfo(true); + this.log('协议: 硬件版本: ' + hwVersion); + } catch (protoErr) { + this.log('协议处理器不可用或初始化失败,继续使用通用 GATT 查询: ' + ((protoErr != null && protoErr instanceof Error) ? protoErr.message : this._fmt(protoErr))); + } + + // Additionally, attempt to read standard services: Generic Access (0x1800), Generic Attribute (0x1801), Battery (0x180F) + const stdServices = ['1800', '1801', '180f'].map(s => { + const hex = s.toLowerCase().replace(/^0x/, ''); + return /^[0-9a-f]{4}$/.test(hex) ? `0000${hex}-0000-1000-8000-00805f9b34fb` : s; + }); + // fetch services once to avoid repeated GATT server queries + const services = await bluetoothService.getServices(deviceId); + for (const svc of stdServices) { + try { + this.log('读取服务: ' + svc); + // find matching service + const found = services.find((x : any) => { + const uuid = (x as UTSJSONObject).get('uuid') + return uuid != null && uuid.toString().toLowerCase() == svc.toLowerCase() + }); + if (found == null) { + this.log('未发现服务 ' + svc + '(需重新扫描并包含 optionalServices)'); + continue; + } + const chars = await bluetoothService.getCharacteristics(deviceId, found?.uuid as string); + console.log(`服务 ${svc} 包含 ${chars.length} 个特征`, chars, " at pages/akbletest.uvue:665"); + for (const c of chars) { + try { + if (c.properties?.read == true) { + const buf = await bluetoothService.readCharacteristic(deviceId, found?.uuid as string, c.uuid); + // try to decode as utf8 then hex + let text = ''; + try { text = new TextDecoder().decode(new Uint8Array(buf)); } catch (e) { text = ''; } + const hex = Array.from(new Uint8Array(buf)).map(b => b.toString(16).padStart(2, '0')).join(' '); + console.log(`特征 ${c.uuid} 读取: text='${text}' hex='${hex}'`, " at pages/akbletest.uvue:674"); + } else { + console.log(`特征 ${c.uuid} 不可读`, " at pages/akbletest.uvue:676"); + } + } catch (e) { + console.log(`读取特征 ${c.uuid} 失败: ${getErrorMessage(e)}`, " at pages/akbletest.uvue:679"); + } + } + } catch (e) { + console.log('查询服务 ' + svc + ' 失败: ' + getErrorMessage(e), " at pages/akbletest.uvue:683"); + } + } + + } catch (e) { + console.log('获取设备信息失败: ' + getErrorMessage(e), " at pages/akbletest.uvue:688"); + } + } + } + }) + function getErrorMessage(e : Error | string | null) : string { + if (e == null) return ''; + if (typeof e == 'string') return e; + try { + return JSON.stringify(e); + } catch (err) { + return '' + e; + } + } + +export default __sfc__ +function GenPagesAkbletestRender(this: InstanceType): any | null { +const _ctx = this +const _cache = this.$.renderCache + return _cE("scroll-view", _uM({ + direction: "vertical", + class: "container" + }), [ + _cE("view", _uM({ class: "section" }), [ + _cE("button", _uM({ + onClick: _ctx.scanDevices, + disabled: _ctx.scanning + }), _tD(_ctx.scanning ? '正在扫描...' : '扫描设备'), 9 /* TEXT, PROPS */, ["onClick", "disabled"]), + _cE("input", _uM({ + modelValue: _ctx.optionalServicesInput, + onInput: ($event: UniInputEvent) => {(_ctx.optionalServicesInput) = $event.detail.value}, + placeholder: "可选服务 UUID, 逗号分隔", + style: _nS(_uM({"margin-left":"12px","width":"40%"})) + }), null, 44 /* STYLE, PROPS, NEED_HYDRATION */, ["modelValue", "onInput"]), + _cE("button", _uM({ + onClick: _ctx.autoConnect, + disabled: _ctx.connecting || _ctx.devices.length == 0, + style: _nS(_uM({"margin-left":"12px"})) + }), _tD(_ctx.connecting ? '正在自动连接...' : '自动连接'), 13 /* TEXT, STYLE, PROPS */, ["onClick", "disabled"]), + _cE("view", null, [ + _cE("text", null, "设备计数: " + _tD(_ctx.devices.length), 1 /* TEXT */), + _cE("text", _uM({ + style: _nS(_uM({"font-size":"12px","color":"gray"})) + }), _tD(_ctx._fmt(_ctx.devices)), 5 /* TEXT, STYLE */) + ]), + isTrue(_ctx.devices.length) + ? _cE("view", _uM({ key: 0 }), [ + _cE("text", null, "已发现设备:"), + _cE(Fragment, null, RenderHelpers.renderList(_ctx.devices, (item, __key, __index, _cached): any => { + return _cE("view", _uM({ + key: item.deviceId, + class: "device-item" + }), [ + _cE("text", null, _tD(item.name!='' ? item.name : '未知设备') + " (" + _tD(item.deviceId) + ")", 1 /* TEXT */), + _cE("button", _uM({ + onClick: () => {_ctx.connect(item.deviceId)} + }), "连接", 8 /* PROPS */, ["onClick"]), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 0, + onClick: () => {_ctx.disconnect(item.deviceId)}, + disabled: _ctx.disconnecting + }), "断开", 8 /* PROPS */, ["onClick", "disabled"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 1, + onClick: () => {_ctx.showServices(item.deviceId)} + }), "查看服务", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 2, + onClick: () => {_ctx.autoDiscoverInterfaces(item.deviceId)} + }), "自动发现接口", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 3, + onClick: () => {_ctx.getDeviceInfo(item.deviceId)} + }), "设备信息", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 4, + onClick: () => {_ctx.startDfuFlow(item.deviceId)} + }), "DFU 升级", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 5, + onClick: () => {_ctx.startDfuFlow(item.deviceId, '/static/OmFw2509140009.zip')} + }), "使用内置固件 DFU", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true) + ]) + }), 128 /* KEYED_FRAGMENT */) + ]) + : _cC("v-if", true) + ]), + _cE("view", _uM({ class: "section" }), [ + _cE("text", null, "日志:"), + _cE("scroll-view", _uM({ + direction: "vertical", + style: _nS(_uM({"height":"240px"})) + }), [ + _cE(Fragment, null, RenderHelpers.renderList(_ctx.logs, (log, idx, __index, _cached): any => { + return _cE("text", _uM({ + key: idx, + style: _nS(_uM({"font-size":"12px"})) + }), _tD(log), 5 /* TEXT, STYLE */) + }), 128 /* KEYED_FRAGMENT */) + ], 4 /* STYLE */) + ]), + isTrue(_ctx.showingServicesFor) + ? _cE("view", _uM({ key: 0 }), [ + _cE("view", _uM({ class: "section" }), [ + _cE("text", null, "设备 " + _tD(_ctx.showingServicesFor) + " 的服务:", 1 /* TEXT */), + isTrue(_ctx.services.length) + ? _cE("view", _uM({ key: 0 }), [ + _cE(Fragment, null, RenderHelpers.renderList(_ctx.services, (srv, __key, __index, _cached): any => { + return _cE("view", _uM({ + key: srv.uuid, + class: "service-item" + }), [ + _cE("text", null, _tD(srv.uuid), 1 /* TEXT */), + _cE("button", _uM({ + onClick: () => {_ctx.showCharacteristics(_ctx.showingServicesFor, srv.uuid)} + }), "查看特征", 8 /* PROPS */, ["onClick"]) + ]) + }), 128 /* KEYED_FRAGMENT */) + ]) + : _cE("view", _uM({ key: 1 }), [ + _cE("text", null, "无服务") + ]), + _cE("button", _uM({ onClick: _ctx.closeServices }), "关闭", 8 /* PROPS */, ["onClick"]) + ]) + ]) + : _cC("v-if", true), + isTrue(_ctx.showingCharacteristicsFor) + ? _cE("view", _uM({ key: 1 }), [ + _cE("view", _uM({ class: "section" }), [ + _cE("text", null, "服务 的特征:"), + isTrue(_ctx.characteristics.length) + ? _cE("view", _uM({ key: 0 }), [ + _cE(Fragment, null, RenderHelpers.renderList(_ctx.characteristics, (char, __key, __index, _cached): any => { + return _cE("view", _uM({ + key: char.uuid, + class: "char-item" + }), [ + _cE("text", null, _tD(char.uuid) + " [" + _tD(_ctx.charProps(char)) + "]", 1 /* TEXT */), + _cE("view", _uM({ + style: _nS(_uM({"display":"flex","flex-direction":"row","margin-top":"6px"})) + }), [ + isTrue(char.properties?.read) + ? _cE("button", _uM({ + key: 0, + onClick: () => {_ctx.readCharacteristic(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid)} + }), "读取", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(char.properties?.write) + ? _cE("button", _uM({ + key: 1, + onClick: () => {_ctx.writeCharacteristic(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid)} + }), "写入(测试)", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(char.properties?.notify) + ? _cE("button", _uM({ + key: 2, + onClick: () => {_ctx.toggleNotify(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid)} + }), _tD(_ctx.isNotifying(char.uuid) ? '取消订阅' : '订阅'), 9 /* TEXT, PROPS */, ["onClick"]) + : _cC("v-if", true) + ], 4 /* STYLE */) + ]) + }), 128 /* KEYED_FRAGMENT */) + ]) + : _cE("view", _uM({ key: 1 }), [ + _cE("text", null, "无特征") + ]), + _cE("button", _uM({ onClick: _ctx.closeCharacteristics }), "关闭", 8 /* PROPS */, ["onClick"]) + ]) + ]) + : _cC("v-if", true) + ]) +} +const GenPagesAkbletestStyles = [_uM([["container", _pS(_uM([["paddingTop", 16], ["paddingRight", 16], ["paddingBottom", 16], ["paddingLeft", 16], ["flex", 1]]))], ["section", _pS(_uM([["marginBottom", 18]]))], ["device-item", _pS(_uM([["display", "flex"], ["flexDirection", "row"], ["flexWrap", "wrap"]]))], ["service-item", _pS(_uM([["marginTop", 6], ["marginRight", 0], ["marginBottom", 6], ["marginLeft", 0]]))], ["char-item", _pS(_uM([["marginTop", 6], ["marginRight", 0], ["marginBottom", 6], ["marginLeft", 0]]))]])] diff --git a/unpackage/dist/dev/.tsc/app-android/pages/akbletest.uvue.ts.map b/unpackage/dist/dev/.tsc/app-android/pages/akbletest.uvue.ts.map new file mode 100644 index 0000000..7383954 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/pages/akbletest.uvue.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"pages/akbletest.uvue","names":[],"sources":["pages/akbletest.uvue"],"sourcesContent":["\r\n\r\n\r\n\r\n"],"mappings":";CA2FC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;CAC7E,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;;CAErI,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;;;;;CAKrF,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;CAC1G,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;;;CAGnF,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;;CAErF,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;CAC7D,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE;EAChC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;EACjB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;CAClB;;CAEA,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;EACd,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;GACN,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACN,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IACf,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IACjB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IACpB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC5B,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACpB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACtB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC5B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACvF,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1C,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACV,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACpB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACrB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACvB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACxB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAClC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACtD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;IAC/C,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IACjD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACzB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IACnF,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;KACd,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC;KACzB,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;KAClF,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;KACrF,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;KACpF,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;KACtE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;KAC7E,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACjC,CAAC;IACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IAClB,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC9D,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;GACzC;EACD,CAAC;EACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;GACT,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;IACpE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;KACb,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACrD;;;GAGD,CAAC,CAAC;GACF,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;GACvC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;GACxE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;IAC/C,CAAC,CAAC,EAAE;KACH,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC1D,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC7D,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC/D,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC/B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;MACtB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAClE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACP;;KAEA,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;KACd,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;;KAEzC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;MACjB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;MACvE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACP;;KAEA,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACxB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;MACjD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC;MACjD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACP;;KAEA,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC;;KAE/D,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;MACZ,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;MAC9C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACzC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;MAC1E,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;KAClD,EAAE,CAAC,CAAC,CAAC,EAAE;MACN,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;MAC1E,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;KACnD;IACD,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;KACb,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE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AAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC1B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAClD,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACvB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE;OACf,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;QAC9F,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACtC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACxC;MACD,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE;OACtB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;QAC9C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACzE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACxC;MACD;KACD;IACD,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;KACb,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACjF;GACD,CAAC;EACF,CAAC;EACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;GACR,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE;IACnE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;KACpD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC9C,EAAE,CAAC,CAAC,CAAC,EAAE;KACN,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC3B;IACA,CAAC,CAAC,EAAE;KACH,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;KACpC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;KAClC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;MACpD,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;MACxC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;MAC9C,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACjD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACzE,EAAE,CAAC,CAAC,CAAC,EAAE;MACN,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;OACvD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;MAChF,CAAC;MACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACf,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACnE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC5E,CAAC,CAAC,EAAE;OACH,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;OACnF,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACjG,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE;QAC/B,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;QACrE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;QAC3E,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;SACpB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;SACpB,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;SAC/B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;UACjE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;UAC7F,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;WAClD,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;WAC/D,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;UACpD;SACD;QACD;OACD;OACA,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACnD,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;QACvE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;QAClE,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;OAC5B;MACD,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KAC9B;KACA,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE;MAC3C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAChB,CAAC,CAAC,CAAC,CAAC,CAAC;KACN;KACA,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;KACzC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;KAC1C,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACzC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;KAC3H,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;KACjD,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACpD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACtC,CAAC,CAAC,EAAE;MACH,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;OAC1C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;OAChB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;OAC1D,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC;OAC5C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;MACrB,CAAC;MACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;KAClB,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;MACX,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACzC;IACD,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;KACX,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC;IAC9B;GACD,CAAC;;GAED,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IAC1D,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KACvC,CAAC,CAAC,EAAE;MACH,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC7B,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACrC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACf,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;MACnE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACZ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;QACjC,CAAC,CAAC,EAAE;SACH,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;SACnC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;SAC/B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACZ,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;OACzB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;MACjC,CAAC;KACF,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACzB,CAAC;GACF,CAAC;;GAED,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACjB,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACnC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAClC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;GAClD,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACxB,CAAC,CAAC,EAAE;KACH,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;KAC7B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;KACrC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1B,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;KACX,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC;IACf;GACD,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE;IACvB,CAAC,CAAC,EAAE;KACH,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;KACzF,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAClH,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;KACnF,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACrC,CAAC,EAAE,CAAC,CAAC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AC,EAAE;IACb,CAAC,CAAC,EAAE;KACH,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;KACnB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;KAChB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;KACvH,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACvF,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;MACrH,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC1B;KACA,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;KACzE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;MACjC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;MACzC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACnD,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;MACvC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC9E,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;KACT,CAAC;KACD,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC;KACpH,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACvE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;MAC1F,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;OACX,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAChC,CAAC;MACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;OACb,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OAC5D,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;MACrB,CAAC;IACH,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;KACb,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC9D,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;IACrB;GACD,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IAC1B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;IACrB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACvC,CAAC,CAAC,EAAE;KACH,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;MAC9E,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC1E,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC7B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;MACf,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACzC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;MAChB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;MACtB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC3C,CAAC;IACF,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;KACb,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC1D,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;IACvB;GACD,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IAC7B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IAChD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;IACxB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KAC7D,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC3B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAClE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACX,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACxC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KACf,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACzC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KAChB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;KACzB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC9C,CAAC;GACF,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IAC/B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACjC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;IACjB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC5C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KACrD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACpD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACnC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;IAC7E,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KACf,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC3C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KAChB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAChD,CAAC,CAAC;GACH,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACf,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;IAC3B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;GAClB,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IAC1D,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACvD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;IACxB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KACvE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACjD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;KAC/E,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAChB,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACnE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACrE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;MAC5C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC/B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACjC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACxC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC1C,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC7C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC9C,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACjC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAA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C,EAAE;IAC5C,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACxB,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC3B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC3B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC5B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC9B,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACrB,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;GACvH,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IAC1B,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;GACzE,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IAChF,CAAC,CAAC,EAAE;KACH,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;KAC3C,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACjF,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;KACZ,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE;KACnF,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;KAC9F,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACvD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;;IAErD,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;KACX,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACzC;GACD,CAAC;GACD,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACjF,CAAC,CAAC,EAAE;KACH,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACrC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;KAChG,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;KACnC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;IACjC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;KACX,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC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,EAAE;QAC3B,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;SAC5F,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAC5D;QACA,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACnE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,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AAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;IAChB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;KAC3B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;MACrF,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACzF,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CA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AC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACjE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACnE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC3F,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC1B,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC9C,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACnC;IACA,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;GAChB,CAAC;;GAED,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;IACtC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACtB,CAAC,CAAC,EAAE;KACH,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAChE,CAAC,CAAC,EAAE;MACH,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC7D,CAAC,EAAE,CAAC,CAAC,CAAC;MACN,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAChD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAC9B,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACX,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACtD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MAClC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;MACrD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACnC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;MAClB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACzI;;KAEA,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KACxH,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;MACrD,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;MAC9C,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;KAChF,CAAC,CAAC;KACF,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC3D,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;KAC7D,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;MAC9B,CAAC,CAAC,EAAE;OACH,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;OACxB,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACvB,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE;QACxC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAC5C,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACzE,CAAC,CAAC;OACF,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;QAClB,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACxD,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACT;OACA,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACxF,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;OACtD,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;QACtB,CAAC,CAAC,EAAE;SACH,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE;UAC/B,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;UAC9F,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;UAChC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;UACb,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE;UACrF,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;UAC/F,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;SAC5D,EAAE,CAAC,CAAC,CAAC,EAAE;UACN,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;SAChC;QACD,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;SA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"} \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts.ts new file mode 100644 index 0000000..9e13060 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts.ts @@ -0,0 +1,279 @@ +import type { + BleDevice, + BleConnectionState, + BleEvent, + BleEventCallback, + BleEventPayload, + BleScanResult, + BleConnectOptionsExt, + AutoBleInterfaces, + BleDataPayload, + SendDataPayload, + BleOptions, + MultiProtocolDevice, + ScanHandler, + BleProtocolType, + ScanDevicesOptions +} from '../interface.uts'; +import { ProtocolHandler } from '../protocol_handler.uts'; +import { BluetoothService } from '../interface.uts'; +import { DeviceManager } from './device_manager.uts'; + +// Shape used when callers register plain objects as handlers. Using a named +// type keeps member access explicit so the code generator emits valid Kotlin +// member references instead of trying to access properties on Any. +type RawProtocolHandler = { + protocol?: BleProtocolType; + scanDevices?: (options?: ScanDevicesOptions) => Promise; + connect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; + disconnect?: (device: BleDevice) => Promise; + sendData?: (device: BleDevice, payload?: SendDataPayload, options?: BleOptions) => Promise; + autoConnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; +} + +// 设备上下文 +class DeviceContext { + device : BleDevice; + protocol : BleProtocolType; + state : BleConnectionState; + handler : ProtocolHandler; + constructor(device : BleDevice, protocol : BleProtocolType, handler : ProtocolHandler) { + this.device = device; + this.protocol = protocol; + this.state = 0; // DISCONNECTED + this.handler = handler; + } +} + +const deviceMap = new Map(); // key: deviceId|protocol +// Single active protocol handler (no multi-protocol registration) +let activeProtocol: BleProtocolType = 'standard'; +let activeHandler: ProtocolHandler | null = null; +// 事件监听注册表 +const eventListeners = new Map>(); + +function emit(event : BleEvent, payload : BleEventPayload) { + if (event === 'connectionStateChanged') { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:57','[AKBLE][LOG] bluetooth_manager.uts emit connectionStateChanged', payload) + } + const listeners = eventListeners.get(event); + if (listeners != null) { + listeners.forEach(cb => { + try { cb(payload); } catch (e) { } + }); + } +} +class ProtocolHandlerWrapper extends ProtocolHandler { + private _raw: RawProtocolHandler | null; + constructor(raw?: RawProtocolHandler) { + // pass a lightweight BluetoothService instance to satisfy generators + super(new BluetoothService()); + this._raw = (raw != null) ? raw : null; + } + override async scanDevices(options?: ScanDevicesOptions): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.scanDevices === 'function') { + await rawTyped.scanDevices(options); + } + return; + } + override async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.connect === 'function') { + await rawTyped.connect(device, options); + } + return; + } + override async disconnect(device: BleDevice): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.disconnect === 'function') { + await rawTyped.disconnect(device); + } + return; + } + override async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.sendData === 'function') { + await rawTyped.sendData(device, payload, options); + } + return; + } + override async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.autoConnect === 'function') { + return await rawTyped.autoConnect(device, options); + } + return { serviceId: '', writeCharId: '', notifyCharId: '' }; + } +} + +// Strong runtime detector for plain object handlers (no Type Predicate) +// Note: the UTS bundler doesn't support TypeScript type predicates (x is T), +// and it doesn't accept the 'unknown' type. This returns a boolean and +// callers must cast the value to RawProtocolHandler after the function +// returns true. +function isRawProtocolHandler(x: any): boolean { + if (x == null || typeof x !== 'object') return false; + const r = x as Record; + if (typeof r['scanDevices'] === 'function') return true; + if (typeof r['connect'] === 'function') return true; + if (typeof r['disconnect'] === 'function') return true; + if (typeof r['sendData'] === 'function') return true; + if (typeof r['autoConnect'] === 'function') return true; + if (typeof r['protocol'] === 'string') return true; + return false; +} + +export const registerProtocolHandler = (handler : any) => { + if (handler == null) return; + // Determine protocol value defensively. Default to 'standard' when unknown. + let proto: BleProtocolType = 'standard'; + if (handler instanceof ProtocolHandler) { + try { proto = (handler as ProtocolHandler).protocol as BleProtocolType; } catch (e) { } + activeHandler = handler as ProtocolHandler; + } else if (isRawProtocolHandler(handler)) { + try { proto = (handler as RawProtocolHandler).protocol as BleProtocolType; } catch (e) { } + activeHandler = new ProtocolHandlerWrapper(handler as RawProtocolHandler); + (activeHandler as ProtocolHandler).protocol = proto; + } else { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:139','[AKBLE] registerProtocolHandler: unsupported handler type, ignoring', handler); + return; + } + activeProtocol = proto; +} + + +export const scanDevices = async (options ?: ScanDevicesOptions) : Promise => { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:147','[AKBLE] start scan', options) + // Determine which protocols to run: either user-specified or all registered + // Single active handler flow + if (activeHandler == null) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:151','[AKBLE] no active scan handler registered') + return + } + const handler = activeHandler as ProtocolHandler; + const scanOptions : ScanDevicesOptions = { + onDeviceFound: (device : BleDevice) => emit('deviceFound', { event: 'deviceFound', device }), + onScanFinished: () => emit('scanFinished', { event: 'scanFinished' }) + } + try { + await handler.scanDevices(scanOptions) + } catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:162','[AKBLE] scanDevices handler error', e) + } +} + + +export const connectDevice = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => { + const handler = activeHandler; + if (handler == null) throw new Error('No protocol handler'); + const device : BleDevice = { deviceId, name: '', rssi: 0 }; // 可扩展 + await handler.connect(device, options); + const ctx = new DeviceContext(device, protocol, handler); + ctx.state = 2; // CONNECTED + deviceMap.set(getDeviceKey(deviceId, protocol), ctx); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:175',deviceMap) + emit('connectionStateChanged', { event: 'connectionStateChanged', device, protocol, state: 2 }); +} + +export const disconnectDevice = async (deviceId : string, protocol : BleProtocolType) : Promise => { + const ctx = deviceMap.get(getDeviceKey(deviceId, protocol)); + if (ctx == null || ctx.handler == null) return; + await ctx.handler.disconnect(ctx.device); + ctx.state = 0; + emit('connectionStateChanged', { event: 'connectionStateChanged', device: ctx.device, protocol, state: 0 }); + deviceMap.delete(getDeviceKey(deviceId, protocol)); +} +export const sendData = async (payload : SendDataPayload, options ?: BleOptions) : Promise => { + const ctx = deviceMap.get(getDeviceKey(payload.deviceId, payload.protocol)); + if (ctx == null) throw new Error('Device not connected'); + // copy to local non-null variable so generator can smart-cast across awaits + const deviceCtx = ctx as DeviceContext; + if (deviceCtx.handler == null) throw new Error('sendData not supported for this protocol'); + await deviceCtx.handler.sendData(deviceCtx.device, payload, options); + emit('dataSent', { event: 'dataSent', device: deviceCtx.device, protocol: payload.protocol, data: payload.data }); +} + +export const getConnectedDevices = () : MultiProtocolDevice[] => { + const result : MultiProtocolDevice[] = []; + deviceMap.forEach((ctx : DeviceContext) => { + const dev : MultiProtocolDevice = { + deviceId: ctx.device.deviceId, + name: ctx.device.name, + rssi: ctx.device.rssi, + protocol: ctx.protocol + }; + result.push(dev); + }); + return result; +} + +export const getConnectionState = (deviceId : string, protocol : BleProtocolType) : BleConnectionState => { + const ctx = deviceMap.get(getDeviceKey(deviceId, protocol)); + if (ctx == null) return 0; + return ctx.state; +} + +export const on = (event : BleEvent, callback : BleEventCallback) => { + if (!eventListeners.has(event)) eventListeners.set(event, new Set()); + eventListeners.get(event)!.add(callback); +} + +export const off = (event : BleEvent, callback ?: BleEventCallback) => { + if (callback == null) { + eventListeners.delete(event); + } else { + eventListeners.get(event)?.delete(callback as BleEventCallback); + } +} + +function getDeviceKey(deviceId : string, protocol : BleProtocolType) : string { + return `${deviceId}|${protocol}`; +} + +export const autoConnect = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => { + const handler = activeHandler; + if (handler == null) throw new Error('autoConnect not supported for this protocol'); + const device : BleDevice = { deviceId, name: '', rssi: 0 }; + // safe call - handler.autoConnect exists on ProtocolHandler + return await handler.autoConnect(device, options) as AutoBleInterfaces; +} + +// Ensure there is at least one handler registered so callers can scan/connect +// without needing to import a registry module. This creates a minimal default +// ProtocolHandler backed by a BluetoothService instance. +try { + if (activeHandler == null) { + // Create a DeviceManager-backed raw handler that delegates to native code + const _dm = DeviceManager.getInstance(); + const _raw: RawProtocolHandler = { + protocol: 'standard', + scanDevices: (options?: ScanDevicesOptions) => { + try { + const scanOptions = options != null ? options : {} as ScanDevicesOptions; + _dm.startScan(scanOptions); + } catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:256','[AKBLE] DeviceManager.startScan failed', e); + } + return Promise.resolve(); + }, + connect: (device, options?: BleConnectOptionsExt) => { + return _dm.connectDevice(device.deviceId, options); + }, + disconnect: (device) => { + return _dm.disconnectDevice(device.deviceId); + }, + autoConnect: (device, options?: any) => { + // DeviceManager does not provide an autoConnect helper; return default + const result: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' }; + return Promise.resolve(result); + } + }; + const _wrapper = new ProtocolHandlerWrapper(_raw); + activeHandler = _wrapper; + activeProtocol = _raw.protocol as BleProtocolType; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:275','[AKBLE] default protocol handler (BluetoothService-backed) registered', activeProtocol); + } +} catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:278','[AKBLE] failed to register default protocol handler', e); +} \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts.ts new file mode 100644 index 0000000..6b3ed54 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts.ts @@ -0,0 +1,311 @@ +import type { BleDevice, BleOptions, BleConnectionState, BleConnectionStateChangeCallback } from '../interface.uts' +import type { BleConnectOptionsExt } from '../interface.uts' +import type { ScanDevicesOptions } from '../interface.uts'; +import Context from "android.content.Context"; +import BluetoothAdapter from "android.bluetooth.BluetoothAdapter"; +import BluetoothManager from "android.bluetooth.BluetoothManager"; +import BluetoothDevice from "android.bluetooth.BluetoothDevice"; +import BluetoothGatt from "android.bluetooth.BluetoothGatt"; +import BluetoothGattCallback from "android.bluetooth.BluetoothGattCallback"; +import ScanCallback from "android.bluetooth.le.ScanCallback"; +import ScanResult from "android.bluetooth.le.ScanResult"; +import ScanSettings from "android.bluetooth.le.ScanSettings"; +import Handler from "android.os.Handler"; +import Looper from "android.os.Looper"; +import ContextCompat from "androidx.core.content.ContextCompat"; +import PackageManager from "android.content.pm.PackageManager"; +// 定义 PendingConnect 类型和实现类 +interface PendingConnect { + resolve: () => void; + reject: (err?: any) => void; // Changed to make err optional + timer?: number; +} + +class PendingConnectImpl implements PendingConnect { + resolve: () => void; + reject: (err?: any) => void; // Changed to make err optional + timer?: number; + + constructor(resolve: () => void, reject: (err?: any) => void, timer?: number) { + this.resolve = resolve; + this.reject = reject; + this.timer = timer; + } +} +// 引入全局回调管理 +import { gattCallback } from './service_manager.uts' +const pendingConnects = new Map(); + +const STATE_DISCONNECTED = 0; +const STATE_CONNECTING = 1; +const STATE_CONNECTED = 2; +const STATE_DISCONNECTING = 3; + +export class DeviceManager { + private static instance: DeviceManager | null = null; + private devices = new Map(); + private connectionStates = new Map(); + private connectionStateChangeListeners: BleConnectionStateChangeCallback[] = [] + private gattMap = new Map(); + private scanCallback: ScanCallback | null = null + private isScanning: boolean = false + private constructor() {} + static getInstance(): DeviceManager { + if (DeviceManager.instance == null) { + DeviceManager.instance = new DeviceManager(); + } + return DeviceManager.instance!; + } + startScan(options: ScanDevicesOptions): void { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:60','ak startscan now') + const adapter = this.getBluetoothAdapter(); + if (adapter == null) { + throw new Error('未找到蓝牙适配器'); + } + if (!adapter.isEnabled) { + // 尝试请求用户开启蓝牙 + try { + adapter.enable(); // 直接调用,无需可选链和括号 + } catch (e) { + // 某些设备可能不支持 enable + } + setTimeout(() => { + if (!adapter.isEnabled) { + throw new Error('蓝牙未开启'); + } + }, 1500); + throw new Error('正在开启蓝牙,请重试'); + } + const foundDevices = this.devices; // 直接用全局 devices + + class MyScanCallback extends ScanCallback { + private foundDevices: Map; + private onDeviceFound: (device: BleDevice) => void; + constructor(foundDevices: Map, onDeviceFound: (device: BleDevice) => void) { + super(); + this.foundDevices = foundDevices; + this.onDeviceFound = onDeviceFound; + } + override onScanResult(callbackType: Int, result: ScanResult): void { + const device = result.getDevice(); + if (device != null) { + const deviceId = device.getAddress(); + let bleDevice = foundDevices.get(deviceId); + if (bleDevice == null) { + bleDevice = { + deviceId, + name: device.getName() ?? 'Unknown', + rssi: result.getRssi(), + lastSeen: Date.now() + }; + foundDevices.set(deviceId, bleDevice); + this.onDeviceFound(bleDevice); + } else { + // 更新属性(已确保 bleDevice 非空) + bleDevice.rssi = result.getRssi(); + bleDevice.name = device.getName() ?? bleDevice.name; + bleDevice.lastSeen = Date.now(); + } + } + } + + + override onScanFailed(errorCode: Int): void { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:114','ak scan fail') + } + } + this.scanCallback = new MyScanCallback(foundDevices, options.onDeviceFound ?? (() => {})); + const scanner = adapter.getBluetoothLeScanner(); + if (scanner == null) { + throw new Error('无法获取扫描器'); + } + const scanSettings = new ScanSettings.Builder() + .setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY) + .build(); + scanner.startScan(null, scanSettings, this.scanCallback); + this.isScanning = true; + // 默认10秒后停止扫描 + new Handler(Looper.getMainLooper()).postDelayed(() => { + if (this.isScanning && this.scanCallback != null) { + scanner.stopScan(this.scanCallback); + this.isScanning = false; + // this.devices = foundDevices; + if (options.onScanFinished != null) options.onScanFinished?.invoke(); + } + }, 40000); + } + + async connectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:139','[AKBLE] connectDevice called, deviceId:', deviceId, 'options:', options, 'connectionStates:') + const adapter = this.getBluetoothAdapter(); + if (adapter == null) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:142','[AKBLE] connectDevice failed: 蓝牙适配器不可用') + throw new Error('蓝牙适配器不可用'); + } + const device = adapter.getRemoteDevice(deviceId); + if (device == null) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:147','[AKBLE] connectDevice failed: 未找到设备', deviceId) + throw new Error('未找到设备'); + } + this.connectionStates.set(deviceId, STATE_CONNECTING); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:151','[AKBLE] connectDevice set STATE_CONNECTING, deviceId:', deviceId, 'connectionStates:') + this.emitConnectionStateChange(deviceId, STATE_CONNECTING); + const activity = UTSAndroid.getUniActivity(); + const timeout = options?.timeout ?? 15000; + const key = `${deviceId}|connect`; + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:158','[AKBLE] connectDevice 超时:', deviceId) + pendingConnects.delete(key); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + this.gattMap.set(deviceId, null); + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + reject(new Error('连接超时')); + }, timeout); + + // 创建一个适配器函数来匹配类型签名 + const resolveAdapter = () => { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:168','[AKBLE] connectDevice resolveAdapter:', deviceId) + resolve(); + }; + const rejectAdapter = (err?: any) => { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:172','[AKBLE] connectDevice rejectAdapter:', deviceId, err) + reject(err); + }; + + pendingConnects.set(key, new PendingConnectImpl(resolveAdapter, rejectAdapter, timer)); + try { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:178','[AKBLE] connectGatt 调用前:', deviceId) + const gatt = device.connectGatt(activity, false, gattCallback); + this.gattMap.set(deviceId, gatt); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:181','[AKBLE] connectGatt 调用后:', deviceId, gatt) + } catch (e) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:183','[AKBLE] connectGatt 异常:', deviceId, e) + clearTimeout(timer); + pendingConnects.delete(key); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + this.gattMap.set(deviceId, null); + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + reject(e); + } + }); + } + + // 统一分发连接回调(应在 gattCallback.onConnectionStateChange 内调用) + static handleConnectionStateChange(deviceId: string, newState: number, error?: any) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:196','[AKBLE] handleConnectionStateChange:', deviceId, 'newState:', newState, 'error:', error, 'pendingConnects:') + const key = `${deviceId}|connect`; + const cb = pendingConnects.get(key); + if (cb != null) { + // 修复 timer 的空安全问题,使用临时变量 + const timerValue = cb.timer; + if (timerValue != null) { + clearTimeout(timerValue); + } + + // 修复 error 处理 + if (newState === STATE_CONNECTED) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:208','[AKBLE] handleConnectionStateChange: 连接成功', deviceId) + cb.resolve(); + } else { + // 正确处理可空值 + const errorToUse = error != null ? error : new Error('连接断开'); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:213','[AKBLE] handleConnectionStateChange: 连接失败', deviceId, errorToUse) + cb.reject(errorToUse); + } + pendingConnects.delete(key); + } else { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:218','[AKBLE] handleConnectionStateChange: 未找到 pendingConnects', deviceId, newState) + } + } + + async disconnectDevice(deviceId: string, isActive: boolean = true): Promise { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:223','[AKBLE] disconnectDevice called, deviceId:', deviceId, 'isActive:', isActive) + let gatt = this.gattMap.get(deviceId); + if (gatt != null) { + gatt.disconnect(); + gatt.close(); + // gatt=null; + this.gattMap.set(deviceId, null); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:231','[AKBLE] disconnectDevice set STATE_DISCONNECTED, deviceId:', deviceId, 'connectionStates:') + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + return; + } else { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:235','[AKBLE] disconnectDevice: gatt is null, deviceId:', deviceId) + return; + } + } + + async reconnectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise { + let attempts = 0; + const maxAttempts = options?.maxAttempts ?? 3; + const interval = options?.interval ?? 3000; + while (attempts < maxAttempts) { + try { + await this.disconnectDevice(deviceId, false); + await this.connectDevice(deviceId, options); + return; + } catch (e) { + attempts++; + if (attempts >= maxAttempts) throw new Error('重连失败'); + // 修复 setTimeout 问题,使用旧式 Promise + setTimeout 解决 + await new Promise((resolve) => { + setTimeout(() => { + resolve(); + }, interval); + }); + } + } + } + + getConnectedDevices(): BleDevice[] { + // 创建一个空数组来存储结果 + const result: BleDevice[] = []; + + // 遍历 devices Map 并检查连接状态 + this.devices.forEach((device, deviceId) => { + if (this.connectionStates.get(deviceId) === STATE_CONNECTED) { + result.push(device); + } + }); + + return result; + } + + onConnectionStateChange(listener: BleConnectionStateChangeCallback) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:277','[AKBLE][LOG] onConnectionStateChange 注册, 当前监听数:', this.connectionStateChangeListeners.length + 1, listener) + this.connectionStateChangeListeners.push(listener) + } + + protected emitConnectionStateChange(deviceId: string, state: BleConnectionState) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:282','[AKBLE][LOG] emitConnectionStateChange', deviceId, state, 'listeners:', this.connectionStateChangeListeners.length, 'connectionStates:', this.connectionStates) + for (const listener of this.connectionStateChangeListeners) { + try { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:285','[AKBLE][LOG] emitConnectionStateChange 调用 listener', listener) + listener(deviceId, state) + } catch (e) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:288','[AKBLE][LOG] emitConnectionStateChange listener error', e) + } + } + } + + getGattInstance(deviceId: string): BluetoothGatt | null { + return this.gattMap.get(deviceId) ?? null; + } + + private getBluetoothAdapter(): BluetoothAdapter | null { + const context = UTSAndroid.getAppContext(); + if (context == null) return null; + const manager = context?.getSystemService(Context.BLUETOOTH_SERVICE) as BluetoothManager; + return manager.getAdapter(); + } + + /** + * 获取指定ID的设备(如果存在) + */ + public getDevice(deviceId: string): BleDevice | null { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:308',deviceId,this.devices) + return this.devices.get(deviceId) ?? null; + } +} diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts.ts new file mode 100644 index 0000000..7fca0e4 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts.ts @@ -0,0 +1,734 @@ +import { BleService } from '../interface.uts' +import type { WriteCharacteristicOptions, DfuOptions, ControlParserResult } from '../interface.uts' +import { DeviceManager } from './device_manager.uts' +import { ServiceManager } from './service_manager.uts' +import BluetoothGatt from 'android.bluetooth.BluetoothGatt' +import BluetoothGattCharacteristic from 'android.bluetooth.BluetoothGattCharacteristic' +import BluetoothGattDescriptor from 'android.bluetooth.BluetoothGattDescriptor' +import UUID from 'java.util.UUID' + +// 通用 Nordic DFU UUIDs (常见设备可能使用这些;如厂商自定义请替换) +const DFU_SERVICE_UUID = '0000fe59-0000-1000-8000-00805f9b34fb' +const DFU_CONTROL_POINT_UUID = '8ec90001-f315-4f60-9fb8-838830daea50' +const DFU_PACKET_UUID = '8ec90002-f315-4f60-9fb8-838830daea50' + +type DfuSession = { + resolve : () => void; + reject : (err ?: any) => void; + onProgress ?: (p : number) => void; + onLog ?: (s : string) => void; + controlParser ?: (data : Uint8Array) => ControlParserResult | null; + // Nordic 专用字段 + bytesSent ?: number; + totalBytes ?: number; + useNordic ?: boolean; + // PRN (packet receipt notification) support + prn ?: number; + packetsSincePrn ?: number; + prnResolve ?: () => void; + prnReject ?: (err ?: any) => void; +} + + + +export class DfuManager { + // 会话表,用于把 control-point 通知路由到当前 DFU 流程 + private sessions : Map = new Map(); + + // 简化:只实现最基本的 GATT-based DFU 上传逻辑,需按设备协议调整 control point 的命令/解析 + + // Emit a DFU lifecycle event for a session. name should follow Nordic listener names + private _emitDfuEvent(deviceId : string, name : string, payload ?: any) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:42','[DFU][Event]', name, deviceId, payload ?? ''); + const s = this.sessions.get(deviceId); + if (s == null) return; + if (typeof s.onLog == 'function') { + try { + const logFn = s.onLog as (msg : string) => void; + logFn(`[${name}] ${payload != null ? JSON.stringify(payload) : ''}`); + } catch (e) { } + } + if (name == 'onProgress' && typeof s.onProgress == 'function' && typeof payload == 'number') { + try { s.onProgress(payload); } catch (e) { } + } + } + + async startDfu(deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) : Promise { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:57','startDfu 0') + const deviceManager = DeviceManager.getInstance(); + const serviceManager = ServiceManager.getInstance(); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:60','startDfu 1') + const gatt : BluetoothGatt | null = deviceManager.getGattInstance(deviceId); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:62','startDfu 2') + if (gatt == null) throw new Error('Device not connected'); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:64','[DFU] startDfu start deviceId=', deviceId, 'firmwareBytes=', firmwareBytes != null ? firmwareBytes.length : 0, 'options=', options); + try { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:66','[DFU] requesting high connection priority for', deviceId); + gatt.requestConnectionPriority(BluetoothGatt.CONNECTION_PRIORITY_HIGH); + } catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:69','[DFU] requestConnectionPriority failed', e); + } + + // 发现服务并特征 + // ensure services discovered before accessing GATT; serviceManager exposes Promise-based API + await serviceManager.getServices(deviceId, null); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:75','[DFU] services ensured for', deviceId); + const dfuService = gatt.getService(UUID.fromString(DFU_SERVICE_UUID)); + if (dfuService == null) throw new Error('DFU service not found'); + const controlChar = dfuService.getCharacteristic(UUID.fromString(DFU_CONTROL_POINT_UUID)); + const packetChar = dfuService.getCharacteristic(UUID.fromString(DFU_PACKET_UUID)); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:80','[DFU] dfuService=', dfuService != null ? dfuService.getUuid().toString() : null, 'controlChar=', controlChar != null ? controlChar.getUuid().toString() : null, 'packetChar=', packetChar != null ? packetChar.getUuid().toString() : null); + if (controlChar == null || packetChar == null) throw new Error('DFU characteristics missing'); + const packetProps = packetChar.getProperties(); + const supportsWriteWithResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE) != 0; + const supportsWriteNoResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) != 0; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:85','[DFU] packet characteristic props mask=', packetProps, 'supportsWithResponse=', supportsWriteWithResponse, 'supportsNoResponse=', supportsWriteNoResponse); + + // Allow caller to request a desired MTU via options for higher throughput + const desiredMtu = (options != null && typeof options.mtu == 'number') ? options.mtu : 247; + try { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:90','[DFU] requesting MTU=', desiredMtu, 'for', deviceId); + await this._requestMtu(gatt, desiredMtu, 8000); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:92','[DFU] requestMtu completed for', deviceId); + } catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:94','[DFU] requestMtu failed or timed out, continue with default.', e); + } + const mtu = desiredMtu; // 假定成功或使用期望值 + const chunkSize = Math.max(20, mtu - 3); + + // small helper to convert a byte (possibly signed) to a two-digit hex string + const byteToHex = (b : number) => { + const v = (b < 0) ? (b + 256) : b; + let s = v.toString(16); + if (s.length < 2) s = '0' + s; + return s; + }; + + // Parameterize PRN window and timeout via options early so they are available + // for session logging. Defaults: prn = 12 packets, prnTimeoutMs = 10000 ms + let prnWindow = 0; + if (options != null && typeof options.prn == 'number') { + prnWindow = Math.max(0, Math.floor(options.prn)); + } + const prnTimeoutMs = (options != null && typeof options.prnTimeoutMs == 'number') ? Math.max(1000, Math.floor(options.prnTimeoutMs)) : 8000; + const disablePrnOnTimeout = !(options != null && options.disablePrnOnTimeout == false); + + // 订阅 control point 通知并将通知路由到会话处理器 + const controlHandler = (data : Uint8Array) => { + // 交给会话处理器解析并触发事件 + try { + const hexParts: string[] = []; + for (let i = 0; i < data.length; i++) { + const v = data[i] as number; + hexParts.push(byteToHex(v)); + } + const hex = hexParts.join(' '); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:126','[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data), 'hex=', hex); + } catch (e) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:128','[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data)); + } + this._handleControlNotification(deviceId, data); + }; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:132','[DFU] subscribing control point for', deviceId); + await serviceManager.subscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, controlHandler); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:134','[DFU] subscribeCharacteristic returned for', deviceId); + + // 保存会话回调(用于 waitForControlEvent); 支持 Nordic 模式追踪已发送字节 + this.sessions.set(deviceId, { + resolve: () => { }, + reject: (err ?: any) => {__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:139',err) }, + onProgress: null, + onLog: null, + controlParser: (data : Uint8Array) => this._defaultControlParser(data), + bytesSent: 0, + totalBytes: firmwareBytes.length, + useNordic: options != null && options.useNordic == true, + prn: null, + packetsSincePrn: 0, + prnResolve: null, + prnReject: null + }); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:151','[DFU] session created for', deviceId, 'totalBytes=', firmwareBytes.length); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:152','[DFU] DFU session details:', { deviceId: deviceId, totalBytes: firmwareBytes.length, chunkSize: chunkSize, prnWindow: prnWindow, prnTimeoutMs: prnTimeoutMs }); + + // wire options callbacks into the session (if provided) + const sessRef = this.sessions.get(deviceId); + if (sessRef != null) { + sessRef.onProgress = (options != null && typeof options.onProgress == 'function') ? options.onProgress : null; + sessRef.onLog = (options != null && typeof options.onLog == 'function') ? options.onLog : null; + } + + // emit initial lifecycle events (Nordic-like) + this._emitDfuEvent(deviceId, 'onDeviceConnecting', null); + + // 写入固件数据(非常保守的实现:逐包写入并等待短延迟) + // --- PRN setup (optional, Nordic-style flow) --- + // Parameterize PRN window and timeout via options: options.prn, options.prnTimeoutMs + // Defaults were set earlier; build PRN payload using arithmetic to avoid + // bitwise operators which don't map cleanly to generated Kotlin. + if (prnWindow > 0) { + try { + // send Set PRN to device (format: [OP_CODE_SET_PRN, prn LSB, prn MSB]) + // WARNING: Ensure your device uses the same opcode/format; change if needed. + const prnLsb = prnWindow % 256; + const prnMsb = Math.floor(prnWindow / 256) % 256; + const prnPayload = new Uint8Array([0x02, prnLsb, prnMsb]); + await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, prnPayload, null); + const sess0 = this.sessions.get(deviceId); + if (sess0 != null) { + sess0.useNordic = true; + sess0.prn = prnWindow; + sess0.packetsSincePrn = 0; + sess0.controlParser = (data : Uint8Array) => this._nordicControlParser(data); + } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:184','[DFU] Set PRN sent (prn=', prnWindow, ') for', deviceId); + } catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:186','[DFU] Set PRN failed (continuing without PRN):', e); + const sessFallback = this.sessions.get(deviceId); + if (sessFallback != null) sessFallback.prn = 0; + } + } else { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:191','[DFU] PRN disabled (prnWindow=', prnWindow, ') for', deviceId); + } + + // 写入固件数据(逐包写入并根据 options.waitForResponse 选择是否等待响应) + let offset = 0; + const total = firmwareBytes.length; + this._emitDfuEvent(deviceId, 'onDfuProcessStarted', null); + this._emitDfuEvent(deviceId, 'onUploadingStarted', null); + // Track outstanding write operations when using fire-and-forget mode so we can + // log and throttle if the Android stack becomes overwhelmed. + let outstandingWrites = 0; + // read tuning parameters from options in a safe, generator-friendly way + let configuredMaxOutstanding = 2; + let writeSleepMs = 0; + let writeRetryDelay = 100; + let writeMaxAttempts = 12; + let writeGiveupTimeout = 60000; + let drainOutstandingTimeout = 3000; + let failureBackoffMs = 0; + + // throughput measurement + let throughputWindowBytes = 0; + let lastThroughputTime = Date.now(); + function _logThroughputIfNeeded(force ?: boolean) { + try { + const now = Date.now(); + const elapsed = now - lastThroughputTime; + if (force == true || elapsed >= 1000) { + const bytes = throughputWindowBytes; + const bps = Math.floor((bytes * 1000) / Math.max(1, elapsed)); + // reset window + throughputWindowBytes = 0; + lastThroughputTime = now; + const human = `${bps} B/s`; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:225','[DFU] throughput:', human, 'elapsedMs=', elapsed); + const s = this.sessions.get(deviceId); + if (s != null && typeof s.onLog == 'function') { + try { s.onLog?.invoke('[DFU] throughput: ' + human); } catch (e) { } + } + } + } catch (e) { } + } + + function _safeErr(e ?: any) { + try { + if (e == null) return ''; + if (typeof e == 'string') return e; + try { return JSON.stringify(e); } catch (e2) { } + try { return (e as any).toString(); } catch (e3) { } + return ''; + } catch (e4) { return ''; } + } + try { + if (options != null) { + try { + if (options.maxOutstanding != null) { + const parsed = Math.floor(options.maxOutstanding as number); + if (!isNaN(parsed) && parsed > 0) configuredMaxOutstanding = parsed; + } + } catch (e) { } + try { + if (options.writeSleepMs != null) { + const parsedWs = Math.floor(options.writeSleepMs as number); + if (!isNaN(parsedWs) && parsedWs >= 0) writeSleepMs = parsedWs; + } + } catch (e) { } + try { + if (options.writeRetryDelayMs != null) { + const parsedRetry = Math.floor(options.writeRetryDelayMs as number); + if (!isNaN(parsedRetry) && parsedRetry >= 0) writeRetryDelay = parsedRetry; + } + } catch (e) { } + try { + if (options.writeMaxAttempts != null) { + const parsedAttempts = Math.floor(options.writeMaxAttempts as number); + if (!isNaN(parsedAttempts) && parsedAttempts > 0) writeMaxAttempts = parsedAttempts; + } + } catch (e) { } + try { + if (options.writeGiveupTimeoutMs != null) { + const parsedGiveupTimeout = Math.floor(options.writeGiveupTimeoutMs as number); + if (!isNaN(parsedGiveupTimeout) && parsedGiveupTimeout > 0) writeGiveupTimeout = parsedGiveupTimeout; + } + } catch (e) { } + try { + if (options.drainOutstandingTimeoutMs != null) { + const parsedDrain = Math.floor(options.drainOutstandingTimeoutMs as number); + if (!isNaN(parsedDrain) && parsedDrain >= 0) drainOutstandingTimeout = parsedDrain; + } + } catch (e) { } + } + if (configuredMaxOutstanding < 1) configuredMaxOutstanding = 1; + if (writeSleepMs < 0) writeSleepMs = 0; + } catch (e) { } + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + if (configuredMaxOutstanding > 1) configuredMaxOutstanding = 1; + if (writeSleepMs < 15) writeSleepMs = 15; + if (writeRetryDelay < 150) writeRetryDelay = 150; + if (writeMaxAttempts < 40) writeMaxAttempts = 40; + if (writeGiveupTimeout < 120000) writeGiveupTimeout = 120000; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:291','[DFU] packet char only supports WRITE_NO_RESPONSE; serializing writes with conservative pacing'); + } + const maxOutstandingCeiling = configuredMaxOutstanding; + let adaptiveMaxOutstanding = configuredMaxOutstanding; + const minOutstandingWindow = 1; + + while (offset < total) { + const end = Math.min(offset + chunkSize, total); + const slice = firmwareBytes.subarray(offset, end); + // Decide whether to wait for response per-chunk. Honor characteristic support. + // Generator-friendly: avoid 'undefined' and use explicit boolean check. + let finalWaitForResponse = true; + if (options != null) { + try { + const maybe = options.waitForResponse; + if (maybe == true && supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + // caller requested response but characteristic cannot provide it; keep true to ensure we await the write promise. + finalWaitForResponse = true; + } else if (maybe == false) { + finalWaitForResponse = false; + } else if (maybe == true) { + finalWaitForResponse = true; + } + } catch (e) { finalWaitForResponse = true; } + } + + const writeOpts: WriteCharacteristicOptions = { + waitForResponse: finalWaitForResponse, + retryDelayMs: writeRetryDelay, + maxAttempts: writeMaxAttempts, + giveupTimeoutMs: writeGiveupTimeout, + forceWriteTypeNoResponse: finalWaitForResponse == false + }; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:324','[DFU] writing packet chunk offset=', offset, 'len=', slice.length, 'waitForResponse=', finalWaitForResponse, 'outstanding=', outstandingWrites); + + // Fire-and-forget path: do not await the write if waitForResponse == false. + if (finalWaitForResponse == false) { + if (failureBackoffMs > 0) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:329','[DFU] applying failure backoff', failureBackoffMs, 'ms before next write for', deviceId); + await this._sleep(failureBackoffMs); + failureBackoffMs = Math.floor(failureBackoffMs / 2); + } + while (outstandingWrites >= adaptiveMaxOutstanding) { + await this._sleep(Math.max(1, writeSleepMs)); + } + // increment outstanding counter and kick the write without awaiting. + outstandingWrites = outstandingWrites + 1; + // fire-and-forget: start the write but don't await its Promise + const writeOffset = offset; + serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts).then((res) => { + outstandingWrites = Math.max(0, outstandingWrites - 1); + if (res == true) { + if (adaptiveMaxOutstanding < maxOutstandingCeiling) { + adaptiveMaxOutstanding = Math.min(maxOutstandingCeiling, adaptiveMaxOutstanding + 1); + } + if (failureBackoffMs > 0) failureBackoffMs = Math.floor(failureBackoffMs / 2); + } + // log occasional completions + if ((outstandingWrites & 0x1f) == 0) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:350','[DFU] write completion callback, outstandingWrites=', outstandingWrites, 'adaptiveWindow=', adaptiveMaxOutstanding, 'device=', deviceId); + } + // detect write failure signaled by service manager + if (res !== true) { + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)); + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:356','[DFU] writeCharacteristic returned false for device=', deviceId, 'offset=', writeOffset, 'adaptiveWindow now=', adaptiveMaxOutstanding); + try { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: 'write returned false' }); } catch (e) { } + } + }).catch((e) => { + outstandingWrites = Math.max(0, outstandingWrites - 1); + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)); + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))); + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:363','[DFU] fire-and-forget write failed for device=', deviceId, e, 'adaptiveWindow now=', adaptiveMaxOutstanding); + try { + const errMsg ='[DFU] fire-and-forget write failed for device='; + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: errMsg }); + } catch (e2) { } + }); + // account bytes for throughput + throughputWindowBytes += slice.length; + _logThroughputIfNeeded(false); + } else { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:373','[DFU] awaiting write for chunk offset=', offset); + try { + const writeResult = await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts); + if (writeResult !== true) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:377','[DFU] writeCharacteristic(await) returned false at offset=', offset, 'device=', deviceId); + try { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: 'write returned false' }); } catch (e) { } + // abort DFU by throwing + throw new Error('write failed'); + } + } catch (e) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:383','[DFU] awaiting write failed at offset=', offset, 'device=', deviceId, e); + try { + const errMsg = '[DFU] awaiting write failed '; + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: errMsg }); + } catch (e2) { } + throw e; + } + // account bytes for throughput + throughputWindowBytes += slice.length; + _logThroughputIfNeeded(false); + } + // update PRN counters and wait when window reached + const sessAfter = this.sessions.get(deviceId); + if (sessAfter != null && sessAfter.useNordic == true && typeof sessAfter.prn == 'number' && (sessAfter.prn ?? 0) > 0) { + sessAfter.packetsSincePrn = (sessAfter.packetsSincePrn ?? 0) + 1; + if ((sessAfter.packetsSincePrn ?? 0) >= (sessAfter.prn ?? 0) && (sessAfter.prn ?? 0) > 0) { + // wait for PRN (device notification) before continuing + try { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:401','[DFU] reached PRN window, waiting for PRN for', deviceId, 'packetsSincePrn=', sessAfter.packetsSincePrn, 'prn=', sessAfter.prn); + await this._waitForPrn(deviceId, prnTimeoutMs); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:403','[DFU] PRN received, resuming transfer for', deviceId); + } catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:405','[DFU] PRN wait failed/timed out, continuing anyway for', deviceId, e); + if (disablePrnOnTimeout) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:407','[DFU] disabling PRN waits after timeout for', deviceId); + sessAfter.prn = 0; + } + } + // reset counter + sessAfter.packetsSincePrn = 0; + } + } + offset = end; + // 如果启用 nordic 模式,统计已发送字节 + const sess = this.sessions.get(deviceId); + if (sess != null && typeof sess.bytesSent == 'number') { + sess.bytesSent = (sess.bytesSent ?? 0) + slice.length; + } + // 简单节流与日志,避免过快。默认睡眠非常短以提高吞吐量; 可在设备上调节 + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:422','[DFU] wrote chunk for', deviceId, 'offset=', offset, '/', total, 'chunkSize=', slice.length, 'bytesSent=', sess != null ? sess.bytesSent : null, 'outstanding=', outstandingWrites); + // emit upload progress event (percent) if available + if (sess != null && typeof sess.bytesSent == 'number' && typeof sess.totalBytes == 'number') { + const p = Math.floor((sess.bytesSent / sess.totalBytes) * 100); + this._emitDfuEvent(deviceId, 'onProgress', p); + } + // yield to event loop and avoid starving the Android BLE stack + await this._sleep(Math.max(0, writeSleepMs)); + } + // wait for outstanding writes to drain before continuing with control commands + if (outstandingWrites > 0) { + const drainStart = Date.now(); + while (outstandingWrites > 0 && (Date.now() - drainStart) < drainOutstandingTimeout) { + await this._sleep(Math.max(0, writeSleepMs)); + } + if (outstandingWrites > 0) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:438','[DFU] outstandingWrites remain after drain timeout, continuing with', outstandingWrites); + } else { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:440','[DFU] outstandingWrites drained before control phase'); + } + } + this._emitDfuEvent(deviceId, 'onUploadingCompleted', null); + + // force final throughput log before activate/validate + _logThroughputIfNeeded(true); + + // 发送 activate/validate 命令到 control point(需根据设备协议实现) + // 下面为占位:请替换为实际的 opcode + // 在写入前先启动控制结果等待,防止设备快速响应导致丢失通知 + const controlTimeout = 20000; + const controlResultPromise = this._waitForControlResult(deviceId, controlTimeout); + try { + // control writes: pass undefined options explicitly to satisfy the generator/typechecker + const activatePayload = new Uint8Array([0x04]); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:456','[DFU] sending activate/validate payload=', Array.from(activatePayload)); + await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, activatePayload, null); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:458','[DFU] activate/validate write returned for', deviceId); + } catch (e) { + // 写入失败时取消控制等待,避免悬挂定时器 + try { + const sessOnWriteFail = this.sessions.get(deviceId); + if (sessOnWriteFail != null && typeof sessOnWriteFail.reject == 'function') { + sessOnWriteFail.reject(e); + } + } catch (rejectErr) { } + await controlResultPromise.catch(() => { }); + try { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e2) { } + this.sessions.delete(deviceId); + throw e; + } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:472','[DFU] sent control activate/validate command to control point for', deviceId); + this._emitDfuEvent(deviceId, 'onValidating', null); + + // 等待 control-point 返回最终结果(成功或失败),超时可配置 + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:476','[DFU] waiting for control result (timeout=', controlTimeout, ') for', deviceId); + try { + await controlResultPromise; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:479','[DFU] control result resolved for', deviceId); + } catch (err) { + // 清理订阅后抛出 + try { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e) { } + this.sessions.delete(deviceId); + throw err; + } + + // 取消订阅 + try { + await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); + } catch (e) { } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:491','[DFU] unsubscribed control point for', deviceId); + + // 清理会话 + this.sessions.delete(deviceId); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:495','[DFU] session cleared for', deviceId); + + return; + } + + async _requestMtu(gatt : BluetoothGatt, mtu : number, timeoutMs : number) : Promise { + return new Promise((resolve, reject) => { + // 在当前项目,BluetoothGattCallback.onMtuChanged 未被封装;简单发起请求并等待短超时 + try { + const ok = gatt.requestMtu(Math.floor(mtu) as Int); + if (!ok) { + return reject(new Error('requestMtu failed')); + } + } catch (e) { + return reject(e); + } + // 无 callback 监听时退回,等待一小段时间以便成功 + setTimeout(() => resolve(), Math.min(2000, timeoutMs)); + }); + } + + _sleep(ms : number) { + return new Promise((r) => { setTimeout(() => { r() }, ms); }); + } + + _waitForPrn(deviceId : string, timeoutMs : number) : Promise { + const session = this.sessions.get(deviceId); + if (session == null) return Promise.reject(new Error('no dfu session')); + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + // timeout waiting for PRN + // clear pending handlers + session.prnResolve = null; + session.prnReject = null; + reject(new Error('PRN timeout')); + }, timeoutMs); + const prnResolve = () => { + clearTimeout(timer); + resolve(); + }; + const prnReject = (err ?: any) => { + clearTimeout(timer); + reject(err); + }; + session.prnResolve = prnResolve; + session.prnReject = prnReject; + }); + } + + // 默认 control point 解析器(非常通用的尝试解析:如果设备发送 progress byte 或成功码) + _defaultControlParser(data : Uint8Array) : ControlParserResult | null { + // 假设协议:第一个字节为 opcode, 第二字节可为状态或进度 + if (data == null || data.length === 0) return null; + const op = data[0]; + // Nordic-style response: [0x10, requestOp, resultCode] + if (op === 0x10 && data.length >= 3) { + const requestOp = data[1]; + const resultCode = data[2]; + if (resultCode === 0x01) { + return { type: 'success' }; + } + return { type: 'error', error: { requestOp: requestOp, resultCode: resultCode, raw: Array.from(data) } }; + } + // Nordic PRN notification: [0x11, LSB, MSB] -> return as progress (bytes received) + if (op === 0x11 && data.length >= 3) { + const lsb = data[1]; + const msb = data[2]; + const received = (msb << 8) | lsb; + return { type: 'progress', progress: received }; + } + // vendor-specific opcode example: 0x60 may mean 'response/progress' for some firmwares + if (op === 0x60) { + if (data.length >= 3) { + const requestOp = data[1]; + const status = data[2]; + // Known success/status codes observed in field devices + if (status === 0x00 || status === 0x01 || status === 0x0A) { + return { type: 'success' }; + } + return { type: 'error', error: { requestOp: requestOp, resultCode: status, raw: Array.from(data) } }; + } + if (data.length >= 2) { + return { type: 'progress', progress: data[1] }; + } + } + // 通用进度回退:若第二字节位于 0-100 之间,当作百分比 + if (data.length >= 2) { + const maybeProgress = data[1]; + if (maybeProgress >= 0 && maybeProgress <= 100) { + return { type: 'progress', progress: maybeProgress }; + } + } + // 若找到明显的 success opcode (示例 0x01) 或 error 0xFF + if (op === 0x01) return { type: 'success' }; + if (op === 0xFF) return { type: 'error', error: data }; + return { type: 'info' }; + } + + // Nordic DFU control-parser(支持 Response and Packet Receipt Notification) + _nordicControlParser(data : Uint8Array) : ControlParserResult | null { + // Nordic opcodes (简化): + // - 0x10 : Response (opcode, requestOp, resultCode) + // - 0x11 : Packet Receipt Notification (opcode, value LSB, value MSB) + if (data == null || data.length == 0) return null; + const op = data[0]; + if (op == 0x11 && data.length >= 3) { + // packet receipt notif: bytes received (little endian) + const lsb = data[1]; + const msb = data[2]; + const received = (msb << 8) | lsb; + // Return received bytes as progress value; parser does not resolve device-specific session here. + return { type: 'progress', progress: received }; + } + // Nordic vendor-specific progress/response opcode (example 0x60) + if (op == 0x60) { + if (data.length >= 3) { + const requestOp = data[1]; + const status = data[2]; + if (status == 0x00 || status == 0x01 || status == 0x0A) { + return { type: 'success' }; + } + return { type: 'error', error: { requestOp, resultCode: status, raw: Array.from(data) } }; + } + if (data.length >= 2) { + return { type: 'progress', progress: data[1] }; + } + } + // Response: check result code for success (0x01 may indicate success in some stacks) + if (op == 0x10 && data.length >= 3) { + const requestOp = data[1]; + const resultCode = data[2]; + // Nordic resultCode 0x01 = SUCCESS typically + if (resultCode == 0x01) return { type: 'success' }; + else return { type: 'error', error: { requestOp, resultCode } }; + } + return null; + } + + _handleControlNotification(deviceId : string, data : Uint8Array) { + const session = this.sessions.get(deviceId); + if (session == null) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:636','[DFU] control notification received but no session for', deviceId, 'data=', Array.from(data)); + return; + } + try { + // human readable opcode mapping + let opcodeName = 'unknown'; + switch (data[0]) { + case 0x10: opcodeName = 'Response'; break; + case 0x11: opcodeName = 'PRN'; break; + case 0x60: opcodeName = 'VendorProgress'; break; + case 0x01: opcodeName = 'SuccessOpcode'; break; + case 0xFF: opcodeName = 'ErrorOpcode'; break; + } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:649','[DFU] _handleControlNotification deviceId=', deviceId, 'opcode=0x' + data[0].toString(16), 'name=', opcodeName, 'raw=', Array.from(data)); + const parsed = session.controlParser != null ? session.controlParser(data) : null; + if (session.onLog != null) session.onLog('DFU control notify: ' + Array.from(data).join(',')); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:652','[DFU] parsed control result=', parsed); + if (parsed == null) return; + if (parsed.type == 'progress' && parsed.progress != null) { + // 如果在 nordic 模式 parsed.progress 可能是已接收字节数,则转换为百分比 + if (session.useNordic == true && session.totalBytes != null && session.totalBytes > 0) { + const percent = Math.floor((parsed.progress / session.totalBytes) * 100); + session.onProgress?.(percent); + // If we have written all bytes locally, log that event + if (session.bytesSent != null && session.totalBytes != null && session.bytesSent >= session.totalBytes) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:661','[DFU] all bytes written locally for', deviceId, 'bytesSent=', session.bytesSent, 'total=', session.totalBytes); + // emit uploading completed once + this._emitDfuEvent(deviceId, 'onUploadingCompleted', null); + } + // If a PRN wait is pending, resolve it (PRN indicates device received packets) + if (typeof session.prnResolve == 'function') { + try { session.prnResolve(); } catch (e) { } + session.prnResolve = null; + session.prnReject = null; + session.packetsSincePrn = 0; + } + } else { + const progress = parsed.progress + if (progress != null) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:675','[DFU] progress for', deviceId, 'progress=', progress); + session.onProgress?.(progress); + // also resolve PRN if was waiting (in case device reports numeric progress) + if (typeof session.prnResolve == 'function') { + try { session.prnResolve(); } catch (e) { } + session.prnResolve = null; + session.prnReject = null; + session.packetsSincePrn = 0; + } + } + } + } else if (parsed.type == 'success') { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:687','[DFU] parsed success for', deviceId, 'resolving session'); + session.resolve(); + // Log final device-acknowledged success + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:690','[DFU] device reported DFU success for', deviceId); + this._emitDfuEvent(deviceId, 'onDfuCompleted', null); + } else if (parsed.type == 'error') { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:693','[DFU] parsed error for', deviceId, parsed.error); + session.reject(parsed.error ?? new Error('DFU device error')); + this._emitDfuEvent(deviceId, 'onError', parsed.error ?? {}); + } else { + // info - just log + } + } catch (e) { + session.onLog?.('control parse error: ' + e); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:701','[DFU] control parse exception for', deviceId, e); + } + } + + _waitForControlResult(deviceId : string, timeoutMs : number) : Promise { + const session = this.sessions.get(deviceId); + if (session == null) return Promise.reject(new Error('no dfu session')); + return new Promise((resolve, reject) => { + // wrap resolve/reject to clear timer + const timer = setTimeout(() => { + // 超时 + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:712','[DFU] _waitForControlResult timeout for', deviceId); + reject(new Error('DFU control timeout')); + }, timeoutMs); + const origResolve = () => { + clearTimeout(timer); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:717','[DFU] _waitForControlResult resolved for', deviceId); + resolve(); + }; + const origReject = (err ?: any) => { + clearTimeout(timer); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:722','[DFU] _waitForControlResult rejected for', deviceId, 'err=', err); + reject(err); + }; + // replace session handlers temporarily (guard nullable) + if (session != null) { + session.resolve = origResolve; + session.reject = origReject; + } + }); + } +} + +export const dfuManager = new DfuManager(); \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts.ts new file mode 100644 index 0000000..b280d09 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts.ts @@ -0,0 +1,110 @@ +import * as BluetoothManager from './bluetooth_manager.uts'; +import { ServiceManager } from './service_manager.uts'; +import type { ScanDevicesOptions, BleConnectOptionsExt, MultiProtocolDevice, BleEvent, BleEventCallback, BleService, BleCharacteristic, WriteCharacteristicOptions, AutoBleInterfaces, BleDataReceivedCallback } from '../interface.uts'; +import { DeviceManager } from './device_manager.uts'; + +const serviceManager = ServiceManager.getInstance(); + +export class BluetoothService { + scanDevices(options?: ScanDevicesOptions) { return BluetoothManager.scanDevices(options); } + connectDevice(deviceId: string, protocol: string, options?: BleConnectOptionsExt) { return BluetoothManager.connectDevice(deviceId, protocol, options); } + disconnectDevice(deviceId: string, protocol: string) { return BluetoothManager.disconnectDevice(deviceId, protocol); } + getConnectedDevices(): MultiProtocolDevice[] { return BluetoothManager.getConnectedDevices(); } + on(event: BleEvent, callback: BleEventCallback) { return BluetoothManager.on(event, callback); } + off(event: BleEvent, callback?: BleEventCallback) { return BluetoothManager.off(event, callback); } + getServices(deviceId: string): Promise { + return new Promise((resolve, reject) => { + serviceManager.getServices(deviceId, (list, err) => { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:18','getServices:', list, err); // 新增日志 + if (err != null) reject(err); + else resolve((list as BleService[]) ?? []); + }); + }); + } + getCharacteristics(deviceId: string, serviceId: string): Promise { + return new Promise((resolve, reject) => { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:26',deviceId,serviceId) + serviceManager.getCharacteristics(deviceId, serviceId, (list, err) => { + if (err != null) reject(err); + else resolve((list as BleCharacteristic[]) ?? []); + }); + }); + } + /** + * 自动发现服务和特征,返回可用的写入和通知特征ID + * @param deviceId 设备ID + * @returns {Promise} + */ + async getAutoBleInterfaces(deviceId: string): Promise { + // 1. 获取服务列表 + const services = await this.getServices(deviceId); + if (services == null || services.length == 0) throw new Error('未发现服务'); + + // 2. 选择目标服务(优先bae前缀,可根据需要调整) + let serviceId = ''; + for (let i = 0; i < services.length; i++) { + const s = services[i]; + const uuidCandidate: string | null = (s.uuid != null ? s.uuid : null) + const uuid: string = uuidCandidate != null ? uuidCandidate : '' + // prefer regex test to avoid nullable receiver calls in generated Kotlin + if (/^bae/i.test(uuid)) { + serviceId = uuid + break; + } + } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:55',serviceId) + if (serviceId == null || serviceId == '') serviceId = services[0].uuid; + + // 3. 获取特征列表 + const characteristics = await this.getCharacteristics(deviceId, serviceId); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:60',characteristics) + if (characteristics == null || characteristics.length == 0) throw new Error('未发现特征值'); + + // 4. 筛选write和notify特征 + let writeCharId = ''; + let notifyCharId = ''; + for (let i = 0; i < characteristics.length; i++) { + + const c = characteristics[i]; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:69',c) + if ((writeCharId == null || writeCharId == '') && c.properties != null && (c.properties.write || c.properties.writeWithoutResponse==true)) writeCharId = c.uuid; + if ((notifyCharId == null || notifyCharId == '') && c.properties != null && (c.properties.notify || c.properties.indicate)) notifyCharId = c.uuid; + } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:73',serviceId, writeCharId, notifyCharId); + if ((writeCharId == null || writeCharId == '') || (notifyCharId == null || notifyCharId == '')) throw new Error('未找到合适的写入或通知特征'); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:75',serviceId, writeCharId, notifyCharId); + // // 发现服务和特征后 + const deviceManager = DeviceManager.getInstance(); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:78',deviceManager); + const device = deviceManager.getDevice(deviceId); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:80',deviceId,device) + device!.serviceId = serviceId; + device!.writeCharId = writeCharId; + device!.notifyCharId = notifyCharId; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:84',device); + return { serviceId, writeCharId, notifyCharId }; + } + async subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, onData: BleDataReceivedCallback): Promise { + return serviceManager.subscribeCharacteristic(deviceId, serviceId, characteristicId, onData); + } + async readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + return serviceManager.readCharacteristic(deviceId, serviceId, characteristicId); + } + async writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, data: Uint8Array, options?: WriteCharacteristicOptions): Promise { + return serviceManager.writeCharacteristic(deviceId, serviceId, characteristicId, data, options); + } + async unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + return serviceManager.unsubscribeCharacteristic(deviceId, serviceId, characteristicId); + } + async autoDiscoverAll(deviceId: string): Promise { + return serviceManager.autoDiscoverAll(deviceId); + } + async subscribeAllNotifications(deviceId: string, onData: BleDataReceivedCallback): Promise { + return serviceManager.subscribeAllNotifications(deviceId, onData); + } +} + +export const bluetoothService = new BluetoothService(); + +// Ensure protocol handlers are registered when this module is imported. + // import './protocol_registry.uts'; diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts.ts new file mode 100644 index 0000000..2166ef7 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts.ts @@ -0,0 +1,663 @@ +import type { BleService, BleCharacteristic, BleDataReceivedCallback, BleCharacteristicProperties, WriteCharacteristicOptions, ByteArray } from '../interface.uts' +import BluetoothGatt from "android.bluetooth.BluetoothGatt"; +import BluetoothGattService from "android.bluetooth.BluetoothGattService"; +import BluetoothGattCharacteristic from "android.bluetooth.BluetoothGattCharacteristic"; +import BluetoothGattDescriptor from "android.bluetooth.BluetoothGattDescriptor"; +import BluetoothGattCallback from "android.bluetooth.BluetoothGattCallback"; + +import UUID from "java.util.UUID"; +import { DeviceManager } from './device_manager.uts' +import { AkBleErrorImpl, AkBluetoothErrorCode } from '../unierror.uts' +import { AutoDiscoverAllResult } from '../interface.uts' + + + + +// 补全UUID格式,将短格式转换为标准格式 +function getFullUuid(shortUuid : string) : string { + return `0000${shortUuid}-0000-1000-8000-00805f9b34fb` +} + + +const deviceWriteQueues = new Map>(); + +function enqueueDeviceWrite(deviceId : string, work : () => Promise) : Promise { + const previous = deviceWriteQueues.get(deviceId) ?? Promise.resolve(); + const next = (async () : Promise => { + try { + await previous; + } catch (e) { /* ignore previous rejection to keep queue alive */ } + return await work(); + })(); + const queued = next.then(() => { }, () => { }); + deviceWriteQueues.set(deviceId, queued); + return next.finally(() => { + if (deviceWriteQueues.get(deviceId) == queued) { + deviceWriteQueues.delete(deviceId); + } + }); +} + + + +function createCharProperties(props : number) : BleCharacteristicProperties { + const result : BleCharacteristicProperties = { + read: false, + write: false, + notify: false, + indicate: false, + canRead: false, + canWrite: false, + canNotify: false, + writeWithoutResponse: false + }; + result.read = (props & BluetoothGattCharacteristic.PROPERTY_READ) !== 0; + result.write = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0; + result.notify = (props & BluetoothGattCharacteristic.PROPERTY_NOTIFY) !== 0; + result.indicate = (props & BluetoothGattCharacteristic.PROPERTY_INDICATE) !== 0; + result.writeWithoutResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0; + + result.canRead = result.read; + const writeWithoutResponse = result.writeWithoutResponse; + result.canWrite = (result.write != null && result.write) || (writeWithoutResponse != null && writeWithoutResponse); + result.canNotify = result.notify; + return result; +} + +// 定义 PendingCallback 类型和实现类 +interface PendingCallback { + resolve : (data : any) => void; + reject : (err ?: any) => void; + timer ?: number; // Changed from any to number +} + +class PendingCallbackImpl implements PendingCallback { + resolve : (data : any) => void; + reject : (err ?: any) => void; + timer ?: number; // Changed from any to number + + constructor(resolve : (data : any) => void, reject : (err ?: any) => void, timer ?: number) { + this.resolve = resolve; + this.reject = reject; + this.timer = timer; + } +} + +// 全局回调管理(必须在类外部声明) +let pendingCallbacks : Map; +let notifyCallbacks : Map; + +// 在全局范围内初始化 +pendingCallbacks = new Map(); +notifyCallbacks = new Map(); + +// 服务发现等待队列:deviceId -> 回调数组 +const serviceDiscoveryWaiters = new Map void)[]>(); +// 服务发现状态:deviceId -> 是否已发现 +const serviceDiscovered = new Map(); + +// 特征发现等待队列:deviceId|serviceId -> 回调数组 +const characteristicDiscoveryWaiters = new Map void)[]>(); + +class GattCallback extends BluetoothGattCallback { + constructor() { + super(); + } + + override onServicesDiscovered(gatt : BluetoothGatt, status : Int) : void { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:108','ak onServicesDiscovered') + const deviceId = gatt.getDevice().getAddress(); + if (status == BluetoothGatt.GATT_SUCCESS) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:111',`服务发现成功: ${deviceId}`); + serviceDiscovered.set(deviceId, true); + // 统一回调所有等待 getServices 的调用 + const waiters = serviceDiscoveryWaiters.get(deviceId); + if (waiters != null && waiters.length > 0) { + const services = gatt.getServices(); + const result : BleService[] = []; + if (services != null) { + const servicesList = services; + const size = servicesList.size; + for (let i = 0; i < size; i++) { + const service = servicesList.get(i as Int); + if (service != null) { + const bleService : BleService = { + uuid: service.getUuid().toString(), + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + result.push(bleService); + } + } + } + for (let i = 0; i < waiters.length; i++) { + const cb = waiters[i]; + if (cb != null) { cb(result, null); } + } + serviceDiscoveryWaiters.delete(deviceId); + } + } else { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:139',`服务发现失败: ${deviceId}, status: ${status}`); + // 失败时也要通知等待队列 + const waiters = serviceDiscoveryWaiters.get(deviceId); + if (waiters != null && waiters.length > 0) { + for (let i = 0; i < waiters.length; i++) { + const cb = waiters[i]; + if (cb != null) { cb(null, new Error('服务发现失败')); } + } + serviceDiscoveryWaiters.delete(deviceId); + } + } + } + override onConnectionStateChange(gatt : BluetoothGatt, status : Int, newState : Int) : void { + const deviceId = gatt.getDevice().getAddress(); + if (newState == BluetoothGatt.STATE_CONNECTED) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:154',`设备已连接: ${deviceId}`); + DeviceManager.handleConnectionStateChange(deviceId, 2, null); // 2 = STATE_CONNECTED + } else if (newState == BluetoothGatt.STATE_DISCONNECTED) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:157',`设备已断开: ${deviceId}`); + serviceDiscovered.delete(deviceId); + DeviceManager.handleConnectionStateChange(deviceId, 0, null); // 0 = STATE_DISCONNECTED + } + } + override onCharacteristicChanged(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic) : void { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:163','ak onCharacteristicChanged') + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|notify`; + const callback = notifyCallbacks.get(key); + const value = characteristic.getValue(); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:170','[onCharacteristicChanged]', key, value); + if (callback != null && value != null) { + const valueLength = value.size; + const arr = new Uint8Array(valueLength); + for (let i = 0 as Int; i < valueLength; i++) { + const v = value[i as Int]; + arr[i] = v != null ? v : 0; + } + // 保存接收日志 + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:179',` + INSERT INTO ble_data_log (device_id, service_id, char_id, direction, data, timestamp) + VALUES ('${deviceId}', '${serviceId}', '${charId}', 'recv', '${Array.from(arr).join(',')}', ${Date.now()}) + `) + + callback(arr); + } + } + override onCharacteristicRead(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:188','ak onCharacteristicRead', status) + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|read`; + const pending = pendingCallbacks.get(key); + const value = characteristic.getValue(); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:195','[onCharacteristicRead]', key, 'status=', status, 'value=', value); + if (pending != null) { + try { + const timer = pending.timer; + if (timer != null) { + clearTimeout(timer); + pending.timer = null; + } + pendingCallbacks.delete(key); + if (status == BluetoothGatt.GATT_SUCCESS && value != null) { + const valueLength = value.size + const arr = new Uint8Array(valueLength); + for (let i = 0 as Int; i < valueLength; i++) { + const v = value[i as Int]; + arr[i] = v != null ? v : 0; + } + + // resolve with ArrayBuffer + pending.resolve(arr.buffer as ArrayBuffer); + } else { + pending.reject(new Error('Characteristic read failed')); + } + } catch (e) { + try { pending.reject(e); } catch (e2) { __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:218',e2); } + } + } + } + + override onCharacteristicWrite(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:224','ak onCharacteristicWrite', status) + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|write`; + const pending = pendingCallbacks.get(key); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:230','[onCharacteristicWrite]', key, 'status=', status); + if (pending != null) { + try { + const timer = pending.timer; + if (timer != null) { + clearTimeout(timer); + } + pendingCallbacks.delete(key); + if (status == BluetoothGatt.GATT_SUCCESS) { + pending.resolve('ok'); + } else { + pending.reject(new Error('Characteristic write failed')); + } + } catch (e) { + try { pending.reject(e); } catch (e2) { __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:244',e2); } + } + } + } +} + +// 导出单例实例供外部使用 +export const gattCallback = new GattCallback(); + +export class ServiceManager { + private static instance : ServiceManager | null = null; + private services = new Map(); + private characteristics = new Map>(); + private deviceManager = DeviceManager.getInstance(); + private constructor() { } + static getInstance() : ServiceManager { + if (ServiceManager.instance == null) { + ServiceManager.instance = new ServiceManager(); + } + return ServiceManager.instance!; + } + + getServices(deviceId : string, callback ?: (services : BleService[] | null, error ?: Error) => void) : any | Promise { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:267','ak start getservice', deviceId); + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) { + if (callback != null) { callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); } + return Promise.reject(new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); + } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:273','ak serviceDiscovered', gatt) + // 如果服务已发现,直接返回 + if (serviceDiscovered.get(deviceId) == true) { + const services = gatt.getServices(); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:277',services) + const result : BleService[] = []; + if (services != null) { + const servicesList = services; + const size = servicesList.size; + if (size > 0) { + for (let i = 0 as Int; i < size; i++) { + const service = servicesList != null ? servicesList.get(i) : servicesList[i]; + if (service != null) { + const bleService : BleService = { + uuid: service.getUuid().toString(), + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + result.push(bleService); + + if (bleService.uuid == getFullUuid('0001')) { + const device = this.deviceManager.getDevice(deviceId); + if (device != null) { + device.serviceId = bleService.uuid; + this.getCharacteristics(deviceId, device.serviceId, (chars, err) => { + if (err == null && chars != null) { + const writeChar = chars.find(c => c.uuid == getFullUuid('0010')); + const notifyChar = chars.find(c => c.uuid == getFullUuid('0011')); + if (writeChar != null) device.writeCharId = writeChar.uuid; + if (notifyChar != null) device.notifyCharId = notifyChar.uuid; + } + }); + } + } + } + } + } + } + if (callback != null) { callback(result, null); } + return Promise.resolve(result); + } + // 未发现则发起服务发现并加入等待队列 + if (!serviceDiscoveryWaiters.has(deviceId)) { + serviceDiscoveryWaiters.set(deviceId, []); + gatt.discoverServices(); + } + return new Promise((resolve, reject) => { + const cb = (services : BleService[] | null, error ?: Error) => { + if (error != null) reject(error); + else resolve(services ?? []); + if (callback != null) callback(services, error); + }; + const arr = serviceDiscoveryWaiters.get(deviceId); + if (arr != null) arr.push(cb); + }); + } + getCharacteristics(deviceId : string, serviceId : string, callback : (characteristics : BleCharacteristic[] | null, error ?: Error) => void) : void { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); + // 如果服务还没发现,等待服务发现后再查特征 + if (serviceDiscovered.get(deviceId) !== true) { + // 先注册到服务发现等待队列 + this.getServices(deviceId, (services, err) => { + if (err != null) { + callback(null, err); + } else { + this.getCharacteristics(deviceId, serviceId, callback); + } + }); + return; + } + // 服务已发现,正常获取特征 + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "")); + const chars = service.getCharacteristics(); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:347',chars) + const result : BleCharacteristic[] = []; + if (chars != null) { + const characteristicsList = chars; + const size = characteristicsList.size; + const bleService : BleService = { + uuid: serviceId, + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + for (let i = 0 as Int; i < size; i++) { + const char = characteristicsList != null ? characteristicsList.get(i as Int) : characteristicsList[i]; + if (char != null) { + const props = char.getProperties(); + try { + const charUuid = char.getUuid() != null ? char.getUuid().toString() : ''; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:362','[ServiceManager] characteristic uuid=', charUuid); + } catch (e) { __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:363','[ServiceManager] failed to read char uuid', e); } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:364',props); + const bleCharacteristic : BleCharacteristic = { + uuid: char.getUuid().toString(), + service: bleService, + properties: createCharProperties(props) + }; + result.push(bleCharacteristic); + } + } + } + callback(result, null); + } + + public async readCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|read`; + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:385',key) + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + pendingCallbacks.delete(key); + reject(new AkBleErrorImpl(AkBluetoothErrorCode.ConnectionTimeout, "Connection timeout", "")); + }, 5000); + const resolveAdapter = (data : any) => { __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:391','read resolve:', data); resolve(data as ArrayBuffer); }; + const rejectAdapter = (err ?: any) => { reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")); }; + pendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)); + if (gatt.readCharacteristic(char) == false) { + clearTimeout(timer); + pendingCallbacks.delete(key); + reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")); + } + else { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:400','read should be succeed', key) + } + }); + } + + public async writeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, data : Uint8Array, options ?: WriteCharacteristicOptions) : Promise { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:406','[writeCharacteristic] deviceId:', deviceId, 'serviceId:', serviceId, 'characteristicId:', characteristicId, 'data:', data); + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:409','[writeCharacteristic] gatt is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + } + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:414','[writeCharacteristic] service is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + } + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:419','[writeCharacteristic] characteristic is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + } + const key = `${deviceId}|${serviceId}|${characteristicId}|write`; + const wantsNoResponse = options != null && options.waitForResponse == false; + let retryMaxAttempts = 20; + let retryDelay = 100; + let giveupTimeout = 20000; + if (options != null) { + try { + if (options.maxAttempts != null) { + const parsedAttempts = Math.floor(options.maxAttempts as number); + if (!isNaN(parsedAttempts) && parsedAttempts > 0) retryMaxAttempts = parsedAttempts; + } + } catch (e) { } + try { + if (options.retryDelayMs != null) { + const parsedDelay = Math.floor(options.retryDelayMs as number); + if (!isNaN(parsedDelay) && parsedDelay >= 0) retryDelay = parsedDelay; + } + } catch (e) { } + try { + if (options.giveupTimeoutMs != null) { + const parsedGiveup = Math.floor(options.giveupTimeoutMs as number); + if (!isNaN(parsedGiveup) && parsedGiveup > 0) giveupTimeout = parsedGiveup; + } + } catch (e) { } + } + const gattInstance = gatt; + const executeWrite = () : Promise => { + + return new Promise((resolve) => { + const initialTimeout = Math.max(giveupTimeout + 5000, 10000); + let timer = setTimeout(() => { + pendingCallbacks.delete(key); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:454','[writeCharacteristic] timeout'); + resolve(false); + }, initialTimeout); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:457','[writeCharacteristic] initial timeout set to', initialTimeout, 'ms for', key); + const resolveAdapter = (data : any) => { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:459','[writeCharacteristic] resolveAdapter called'); + resolve(true); + }; + const rejectAdapter = (err ?: any) => { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:463','[writeCharacteristic] rejectAdapter called', err); + resolve(false); + }; + pendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)); + const byteArray = new ByteArray(data.length as Int); + for (let i = 0 as Int; i < data.length; i++) { + byteArray[i] = data[i].toByte(); + } + const forceWriteTypeNoResponse = options != null && options.forceWriteTypeNoResponse == true; + let usesNoResponse = forceWriteTypeNoResponse || wantsNoResponse; + try { + const props = char.getProperties(); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:475','[writeCharacteristic] characteristic properties mask=', props); + if (usesNoResponse == false) { + const supportsWriteWithResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0; + const supportsWriteNoResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0; + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + usesNoResponse = true; + } + } + if (usesNoResponse) { + try { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_NO_RESPONSE); } catch (e) { } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:485','[writeCharacteristic] using WRITE_TYPE_NO_RESPONSE'); + } else { + try { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT); } catch (e) { } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:488','[writeCharacteristic] using WRITE_TYPE_DEFAULT'); + } + } catch (e) { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:491','[writeCharacteristic] failed to inspect/set write type', e); + } + const maxAttempts = retryMaxAttempts; + function attemptWrite(att : Int) : void { + try { + let setOk = true; + try { + const setRes = char.setValue(byteArray); + if (typeof setRes == 'boolean' && setRes == false) { + setOk = false; + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:501','[writeCharacteristic] setValue returned false for', key, 'attempt', att); + } + } catch (e) { + setOk = false; + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:505','[writeCharacteristic] setValue threw for', key, 'attempt', att, e); + } + if (setOk == false) { + if (att >= maxAttempts) { + try { clearTimeout(timer); } catch (e) { } + pendingCallbacks.delete(key); + resolve(false); + return; + } + setTimeout(() => { attemptWrite((att + 1) as Int); }, retryDelay); + return; + } + try { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:518','[writeCharacteristic] attempt', att, 'calling gatt.writeCharacteristic'); + const r = gattInstance.writeCharacteristic(char); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:520','[writeCharacteristic] attempt', att, 'result=', r); + if (r == true) { + if (usesNoResponse) { + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:523','[writeCharacteristic] WRITE_TYPE_NO_RESPONSE success for', key); + try { clearTimeout(timer); } catch (e) { } + pendingCallbacks.delete(key); + resolve(true); + return; + } + try { clearTimeout(timer); } catch (e) { } + const extra = 20000; + timer = setTimeout(() => { + pendingCallbacks.delete(key); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:533','[writeCharacteristic] timeout after write initiated'); + resolve(false); + }, extra); + const pendingEntry = pendingCallbacks.get(key); + if (pendingEntry != null) pendingEntry.timer = timer; + return; + } + } catch (e) { + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:541','[writeCharacteristic] attempt', att, 'exception when calling writeCharacteristic', e); + } + if (att < maxAttempts) { + const nextAtt = (att + 1) as Int; + setTimeout(() => { attemptWrite(nextAtt); }, retryDelay); + return; + } + if (usesNoResponse) { + try { clearTimeout(timer); } catch (e) { } + pendingCallbacks.delete(key); + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:551','[writeCharacteristic] all attempts failed with WRITE_NO_RESPONSE for', key); + resolve(false); + return; + } + try { clearTimeout(timer); } catch (e) { } + const giveupTimeoutLocal = giveupTimeout; + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:557','[writeCharacteristic] all attempts failed; waiting for late callback up to', giveupTimeoutLocal, 'ms for', key); + const giveupTimer = setTimeout(() => { + pendingCallbacks.delete(key); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:560','[writeCharacteristic] giveup timeout expired for', key); + resolve(false); + }, giveupTimeoutLocal); + const pendingEntryAfter = pendingCallbacks.get(key); + if (pendingEntryAfter != null) pendingEntryAfter.timer = giveupTimer; + } catch (e) { + clearTimeout(timer); + pendingCallbacks.delete(key); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:568','[writeCharacteristic] Exception in attemptWrite', e); + resolve(false); + } + } + + try { + attemptWrite(1 as Int); + } catch (e) { + clearTimeout(timer); + pendingCallbacks.delete(key); + __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:578','[writeCharacteristic] Exception before attempting write', e); + resolve(false); + } + }); + }; + return enqueueDeviceWrite(deviceId, executeWrite); + } + + public async subscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, onData : BleDataReceivedCallback) : Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|notify`; + notifyCallbacks.set(key, onData); + if (gatt.setCharacteristicNotification(char, true) == false) { + notifyCallbacks.delete(key); + throw new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", ""); + } else { + // 写入 CCCD 描述符,启用 notify + const descriptor = char.getDescriptor(UUID.fromString("00002902-0000-1000-8000-00805f9b34fb")); + if (descriptor != null) { + // 设置描述符值 + const value = + BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE; + + descriptor.setValue(value); + const writedescript = gatt.writeDescriptor(descriptor); + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:608','subscribeCharacteristic: CCCD written for notify', writedescript); + } else { + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:610','subscribeCharacteristic: CCCD descriptor not found!'); + } + __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:612','subscribeCharacteristic ok!!'); + } + } + + public async unsubscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|notify`; + notifyCallbacks.delete(key); + if (gatt.setCharacteristicNotification(char, false) == false) { + throw new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", ""); + } + } + + + // 自动发现所有服务和特征 + public async autoDiscoverAll(deviceId : string) : Promise { + const services = await this.getServices(deviceId, null) as BleService[]; + const allCharacteristics : BleCharacteristic[] = []; + for (const service of services) { + await new Promise((resolve, reject) => { + this.getCharacteristics(deviceId, service.uuid, (chars, err) => { + if (err != null) reject(err); + else { + if (chars != null) allCharacteristics.push(...chars); + resolve(); + } + }); + }); + } + return { services, characteristics: allCharacteristics }; + } + + // 自动订阅所有支持 notify/indicate 的特征 + public async subscribeAllNotifications(deviceId : string, onData : BleDataReceivedCallback) : Promise { + const { services, characteristics } = await this.autoDiscoverAll(deviceId); + for (const char of characteristics) { + if (char.properties.notify || char.properties.indicate) { + try { + await this.subscribeCharacteristic(deviceId, char.service.uuid, char.uuid, onData); + } catch (e) { + // 可以选择忽略单个特征订阅失败 + __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:658',`订阅特征 ${char.uuid} 失败:`, e); + } + } + } + } +} \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts.ts new file mode 100644 index 0000000..c02b46d --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts.ts @@ -0,0 +1,481 @@ +// 蓝牙相关接口和类型定义 + +// 基础设备信息类型 +export type BleDeviceInfo = { + deviceId : string; + name : string; + RSSI ?: number; + connected ?: boolean; + // 新增 + serviceId ?: string; + writeCharId ?: string; + notifyCharId ?: string; +} +export type AutoDiscoverAllResult = { + services : BleService[]; + characteristics : BleCharacteristic[]; +} + +// 服务信息类型 +export type BleServiceInfo = { + uuid : string; + isPrimary : boolean; +} + +// 特征值属性类型 +export type BleCharacteristicProperties = { + read : boolean; + write : boolean; + notify : boolean; + indicate : boolean; + writeWithoutResponse ?: boolean; + canRead ?: boolean; + canWrite ?: boolean; + canNotify ?: boolean; +} + +// 特征值信息类型 +export type BleCharacteristicInfo = { + uuid : string; + serviceId : string; + properties : BleCharacteristicProperties; +} + +// 错误状态码 +export enum BleErrorCode { + UNKNOWN_ERROR = 0, + BLUETOOTH_UNAVAILABLE = 1, + PERMISSION_DENIED = 2, + DEVICE_NOT_CONNECTED = 3, + SERVICE_NOT_FOUND = 4, + CHARACTERISTIC_NOT_FOUND = 5, + OPERATION_TIMEOUT = 6 +} + +// 命令类型 +export enum CommandType { + BATTERY = 1, + DEVICE_INFO = 2, + CUSTOM = 99, + TestBatteryLevel = 0x01 +} + +// 错误接口 +export type BleError { + errCode : number; + errMsg : string; + errSubject ?: string; +} + + +// 连接选项 +export type BleConnectOptions = { + deviceId : string; + timeout ?: number; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 断开连接选项 +export type BleDisconnectOptions = { + deviceId : string; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 获取特征值选项 +export type BleCharacteristicOptions = { + deviceId : string; + serviceId : string; + characteristicId : string; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 写入特征值选项 +export type BleWriteOptions = { + deviceId : string; + serviceId : string; + characteristicId : string; + value : Uint8Array; + writeType ?: number; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// Options for writeCharacteristic helper +export type WriteCharacteristicOptions = { + waitForResponse ?: boolean; + maxAttempts ?: number; + retryDelayMs ?: number; + giveupTimeoutMs ?: number; + forceWriteTypeNoResponse ?: boolean; +} + +// 通知特征值回调函数 +export type BleNotifyCallback = (data : Uint8Array) => void; + +// 通知特征值选项 +export type BleNotifyOptions = { + deviceId : string; + serviceId : string; + characteristicId : string; + state ?: boolean; // true: 启用通知,false: 禁用通知 + onCharacteristicValueChange : BleNotifyCallback; + success ?: (result : any) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 获取服务选项 +export type BleDeviceServicesOptions = { + deviceId : string; + success ?: (result : BleServicesResult) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 获取特征值选项 +export type BleDeviceCharacteristicsOptions = { + deviceId : string; + serviceId : string; + success ?: (result : BleCharacteristicsResult) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 蓝牙扫描选项 +export type BluetoothScanOptions = { + services ?: string[]; + timeout ?: number; + onDeviceFound ?: (device : BleDeviceInfo) => void; + success ?: (result : BleScanResult) => void; + fail ?: (error : BleError) => void; + complete ?: (result : any) => void; +} + +// 扫描结果 + +// 服务结果 +export type BleServicesResult = { + services : BleServiceInfo[]; + errMsg ?: string; +} + +// 特征值结果 +export type BleCharacteristicsResult = { + characteristics : BleCharacteristicInfo[]; + errMsg ?: string; +} + +// 定义连接状态枚举 +export enum BLE_CONNECTION_STATE { + DISCONNECTED = 0, + CONNECTING = 1, + CONNECTED = 2, + DISCONNECTING = 3 +} + +// 电池状态类型定义 +export type BatteryStatus = { + batteryLevel : number; // 电量百分比 + isCharging : boolean; // 充电状态 +} + +// 蓝牙服务接口类型定义 - 转换为type类型 +export type BleService = { + uuid : string; + isPrimary : boolean; +} + +// 蓝牙特征值接口定义 - 转换为type类型 +export type BleCharacteristic = { + uuid : string; + service : BleService; + properties : BleCharacteristicProperties; +} + +// PendingPromise接口定义 +export interface PendingCallback { + resolve : (data : any) => void; + reject : (err ?: any) => void; + timer ?: number; +} + +// 蓝牙相关接口和类型定义 +export type BleDevice = { + deviceId : string; + name : string; + rssi ?: number; + lastSeen ?: number; // 新增 + // 新增 + serviceId ?: string; + writeCharId ?: string; + notifyCharId ?: string; +} + +// BLE常规选项 +export type BleOptions = { + timeout ?: number; + success ?: (result : any) => void; + fail ?: (error : any) => void; + complete ?: () => void; +} + +export type BleConnectionState = number; // 0: DISCONNECTED, 1: CONNECTING, 2: CONNECTED, 3: DISCONNECTING + +export type BleConnectOptionsExt = { + timeout ?: number; + services ?: string[]; + requireResponse ?: boolean; + autoReconnect ?: boolean; + maxAttempts ?: number; + interval ?: number; +}; + +// 回调函数类型 +export type BleDeviceFoundCallback = (device : BleDevice) => void; +export type BleConnectionStateChangeCallback = (deviceId : string, state : BleConnectionState) => void; + +export type BleDataPayload = { + deviceId : string; + serviceId ?: string; + characteristicId ?: string; + data : string | ArrayBuffer; + format ?: number; // 0: JSON, 1: XML, 2: RAW +} + +export type BleDataSentCallback = (payload : BleDataPayload, success : boolean, error ?: BleError) => void; +export type BleErrorCallback = (error : BleError) => void; + +// 健康数据类型定义 +export enum HealthDataType { + HEART_RATE = 1, + BLOOD_OXYGEN = 2, + TEMPERATURE = 3, + STEP_COUNT = 4, + SLEEP_DATA = 5, + HEALTH_DATA = 6 +} + +// Platform-specific services should be imported from per-platform entrypoints +// (e.g. './app-android/index.uts' or './web/index.uts'). +// Avoid re-exporting platform modules at the SDK root to prevent bundlers +// Platform-specific services should be imported from per-platform entrypoints +// (e.g. './app-android/index.uts' or './web/index.uts'). +// Avoid re-exporting platform modules at the SDK root to prevent bundlers +// from pulling android.* symbols into web bundles. +// If a typed ambient reference is required, declare the shape here instead of importing implementation. +// Example lightweight typed placeholder (do not import platform code here): +// export type BluetoothService = any; // platform-specific implementation exported from platform index files + + + +// ====== 新增多协议、统一事件、协议适配、状态管理支持 ====== +export type BleProtocolType = + | 'standard' + | 'custom' + | 'health' + | 'ibeacon' + | 'mesh'; + +export type BleEvent = + | 'deviceFound' + | 'scanFinished' + | 'connectionStateChanged' + | 'dataReceived' + | 'dataSent' + | 'error' + | 'servicesDiscovered' + | 'connected' // 新增 + | 'disconnected'; // 新增 + +// 事件回调参数 +export type BleEventPayload = { + event : BleEvent; + device ?: BleDevice; + protocol ?: BleProtocolType; + state ?: BleConnectionState; + data ?: ArrayBuffer | string | object; + format ?: string; + error ?: BleError; + extra ?: any; +} + +// 事件回调函数 +export type BleEventCallback = (payload : BleEventPayload) => void; + +// 多协议设备信息(去除交叉类型,直接展开字段) +export type MultiProtocolDevice = { + deviceId : string; + name : string; + rssi ?: number; + protocol : BleProtocolType; +}; + +export type ScanDevicesOptions = { + protocols ?: BleProtocolType[]; + optionalServices ?: string[]; + timeout ?: number; + onDeviceFound ?: (device : BleDevice) => void; + onScanFinished ?: () => void; +}; +// Named payload type used by sendData +export type SendDataPayload = { + deviceId : string; + serviceId ?: string; + characteristicId ?: string; + data : string | ArrayBuffer; + format ?: number; + protocol : BleProtocolType; +} +// 协议处理器接口(为 protocol-handler 适配器预留) +export type ScanHandler = { + protocol : BleProtocolType; + scanDevices ?: (options : ScanDevicesOptions) => Promise; + connect : (device : BleDevice, options ?: BleConnectOptionsExt) => Promise; + disconnect : (device : BleDevice) => Promise; + // Optional: send arbitrary data via the protocol's write characteristic + sendData ?: (device : BleDevice, payload : SendDataPayload, options ?: BleOptions) => Promise; + // Optional: try to connect and discover service/characteristic ids for this device + autoConnect ?: (device : BleDevice, options ?: BleConnectOptionsExt) => Promise; + +} + + +// 自动发现服务和特征返回类型 +export type AutoBleInterfaces = { + serviceId : string; + writeCharId : string; + notifyCharId : string; +} +export type ResponseCallbackEntry = { + cb : (data : Uint8Array) => boolean | void; + multi : boolean; +}; + +// Result returned by a DFU control parser. Use a plain string `type` to keep +// the generated Kotlin simple and avoid inline union types which the generator +// does not handle well. +export type ControlParserResult = { + type : string; // e.g. 'progress', 'success', 'error', 'info' + progress ?: number; + error ?: any; +} + +// DFU types +export type DfuOptions = { + mtu ?: number; + useNordic ?: boolean; + // If true, the DFU upload will await a write response per-packet. Set false to use + // WRITE_NO_RESPONSE (fire-and-forget) for higher throughput. Default: false. + waitForResponse ?: boolean; + // Maximum number of outstanding NO_RESPONSE writes to allow before throttling. + // This implements a simple sliding window. Default: 32. + maxOutstanding ?: number; + // Per-chunk sleep (ms) to yield to event loop / Android BLE stack. Default: 2. + writeSleepMs ?: number; + // Retry delay (ms) used by the Android write helper when gatt.writeCharacteristic + // returns false. Smaller values can improve throughput on congested stacks. + writeRetryDelayMs ?: number; + // Maximum number of immediate write attempts before falling back to the give-up timeout. + writeMaxAttempts ?: number; + // Timeout (ms) to wait for a late onCharacteristicWrite callback after all retries fail. + writeGiveupTimeoutMs ?: number; + // Packet Receipt Notification (PRN) window size in packets. If set, DFU + // manager will send a Set PRN command to the device and wait for PRN + // notifications after this many packets. Default: 12. + prn ?: number; + // Timeout (ms) to wait for a PRN notification once the window is reached. + // Default: 10000 (10s). + prnTimeoutMs ?: number; + // When true, disable PRN waits automatically after the first timeout to prevent + // repeated long stalls on devices that do not send PRNs. Default: true. + disablePrnOnTimeout ?: boolean; + // Time (ms) to wait for outstanding fire-and-forget writes to drain before issuing + // the activate/validate control command. Default: 3000. + drainOutstandingTimeoutMs ?: number; + controlTimeout ?: number; + onProgress ?: (percent : number) => void; + onLog ?: (message : string) => void; + controlParser ?: (data : Uint8Array) => ControlParserResult | null; +} + +export type DfuManagerType = { + startDfu : (deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) => Promise; +} + +// Lightweight runtime / UTS shims and missing types +// These are conservative placeholders to satisfy typings used across platform files. +// UTSJSONObject: bundler environments used by the build may not support +// TypeScript-style index signatures in this .uts context. Use a conservative +// 'any' alias so generated code doesn't rely on unsupported syntax while +// preserving a usable type at the source level. +export type UTSJSONObject = any; + +// ByteArray / Int are used in the Android platform code to interop with Java APIs. +// Define minimal aliases so source can compile. Runtime uses Uint8Array and number. +export type ByteArray = any; // runtime will use Java byte[] via UTS bridge; keep as any here + +// Callback types used by service_manager and index wrappers +export type BleDataReceivedCallback = (data: Uint8Array) => void; +export type BleScanResult = { + deviceId: string; + name?: string; + rssi?: number; + advertising?: any; +}; + +// Minimal UI / framework placeholders (some files reference these in types only) +export type ComponentPublicInstance = any; +export type UniElement = any; +export type UniPage = any; + +// Platform service placeholder (actual implementation exported from platform index files) +// Provide a lightweight, strongly-shaped class skeleton so source-level code +// (and the code generator) can rely on concrete method names and signatures. +// Implementations are platform-specific and exported from per-platform index +// files (e.g. './app-android/index.uts' or './web/index.uts'). This class is +// intentionally thin — it declares method signatures used across pages and +// platform shims so the generator emits resolvable Kotlin symbols. +export class BluetoothService { + // Event emitter style + on(event: BleEvent | string, callback: BleEventCallback): void {} + off(event: BleEvent | string, callback?: BleEventCallback): void {} + + // Scanning / discovery + scanDevices(options?: ScanDevicesOptions): Promise { return Promise.resolve(); } + + // Connection management + connectDevice(deviceId: string, protocol?: string, options?: BleConnectOptionsExt): Promise { return Promise.resolve(); } + disconnectDevice(deviceId: string, protocol?: string): Promise { return Promise.resolve(); } + getConnectedDevices(): MultiProtocolDevice[] { return []; } + + // Services / characteristics + getServices(deviceId: string): Promise { return Promise.resolve([]); } + getCharacteristics(deviceId: string, serviceId: string): Promise { return Promise.resolve([]); } + + // Read / write / notify + readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(new ArrayBuffer(0)); } + writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, value: Uint8Array | ArrayBuffer, options?: WriteCharacteristicOptions): Promise { return Promise.resolve(true); } + subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, callback: BleNotifyCallback): Promise { return Promise.resolve(); } + unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(); } + + // Convenience helpers + getAutoBleInterfaces(deviceId: string): Promise { + const res: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' }; + return Promise.resolve(res); + } +} + +// Runtime protocol handler base class. Exporting a concrete class ensures the +// generator emits a resolvable runtime type that platform handlers can extend. +// Source-level code can still use the ScanHandler type for typing. +// Runtime ProtocolHandler is implemented in `protocol_handler.uts`. +// Keep the public typing in this file minimal to avoid duplicate runtime +// declarations. Consumers that need the runtime class should import it from +// './protocol_handler.uts'. \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts.ts new file mode 100644 index 0000000..d762fd6 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts.ts @@ -0,0 +1,115 @@ +// Minimal ProtocolHandler runtime class used by pages and components. +// This class adapts the platform `BluetoothService` to a small protocol API +// expected by pages: setConnectionParameters, initialize, testBatteryLevel, +// testVersionInfo. Implemented conservatively to avoid heavy dependencies. + +import type { BluetoothService, AutoBleInterfaces, AutoDiscoverAllResult, BleService, BleCharacteristic, BleProtocolType, BleDevice, ScanDevicesOptions, BleConnectOptionsExt, SendDataPayload, BleOptions } from './interface.uts' + +export class ProtocolHandler { + // bluetoothService may be omitted for lightweight wrappers; allow null + bluetoothService: BluetoothService | null = null + protocol: BleProtocolType = 'standard' + deviceId: string | null = null + serviceId: string | null = null + writeCharId: string | null = null + notifyCharId: string | null = null + initialized: boolean = false + + // Accept an optional BluetoothService so wrapper subclasses can call + // `super()` without forcing a runtime instance. + constructor(bluetoothService?: BluetoothService) { + if (bluetoothService != null) this.bluetoothService = bluetoothService + } + + setConnectionParameters(deviceId: string, serviceId: string, writeCharId: string, notifyCharId: string) { + this.deviceId = deviceId + this.serviceId = serviceId + this.writeCharId = writeCharId + this.notifyCharId = notifyCharId + } + + // initialize: optional setup, returns a Promise that resolves when ready + async initialize(): Promise { + // Simple async initializer — keep implementation minimal and generator-friendly. + try { + // If bluetoothService exposes any protocol-specific setup, call it here. + this.initialized = true + return + } catch (e) { + throw e + } + } + + // Protocol lifecycle / operations — default no-ops so generated code has + // concrete member references and platform-specific handlers can override. + async scanDevices(options?: ScanDevicesOptions): Promise { return; } + async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return; } + async disconnect(device: BleDevice): Promise { return; } + async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { return; } + async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return { serviceId: '', writeCharId: '', notifyCharId: '' }; } + + // Example: testBatteryLevel will attempt to read the battery characteristic + // if write/notify-based protocol is not available. Returns number percentage. + async testBatteryLevel(): Promise { + if (this.deviceId == null) throw new Error('deviceId not set') + // copy to local so Kotlin generator can smart-cast the value across awaits + const deviceId = this.deviceId + // try reading standard Battery characteristic (180F -> 2A19) + if (this.bluetoothService == null) throw new Error('bluetoothService not set') + const services = await this.bluetoothService.getServices(deviceId) + + + let found: BleService | null = null + for (let i = 0; i < services.length; i++) { + const s = services[i] + const uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null) + const uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : '' + if (uuid.indexOf('180f') !== -1) { found = s; break } + } + if (found == null) { + // fallback: if writeCharId exists and notify available use protocol (not implemented) + return 0 + } + const foundUuid = found!.uuid + const charsRaw = await this.bluetoothService.getCharacteristics(deviceId, foundUuid) + const chars: BleCharacteristic[] = charsRaw + const batChar = chars.find((c: BleCharacteristic) => ((c.properties != null && c.properties.read) || (c.uuid != null && ('' + c.uuid).toLowerCase().includes('2a19')))) + if (batChar == null) return 0 + const buf = await this.bluetoothService.readCharacteristic(deviceId, foundUuid, batChar.uuid) + const arr = new Uint8Array(buf) + if (arr.length > 0) { + return arr[0] + } + return 0 + } + + // testVersionInfo: try to read Device Information characteristics or return empty + async testVersionInfo(hw: boolean): Promise { + // copy to local so Kotlin generator can smart-cast the value across awaits + const deviceId = this.deviceId + if (deviceId == null) return '' + // Device Information service 180A, characteristics: 2A26 (SW), 2A27 (HW) sometimes + if (this.bluetoothService == null) return '' + const _services = await this.bluetoothService.getServices(deviceId) + const services2: BleService[] = _services + let found2: BleService | null = null + for (let i = 0; i < services2.length; i++) { + const s = services2[i] + const uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null) + const uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : '' + if (uuid.indexOf('180a') !== -1) { found2 = s; break } + } + if (found2 == null) return '' + const _found2 = found2 + const found2Uuid = _found2!.uuid + const chars = await this.bluetoothService.getCharacteristics(deviceId, found2Uuid) + const target = chars.find((c) => { + const id = ('' + c.uuid).toLowerCase() + if (hw) return id.includes('2a27') || id.includes('hardware') + return id.includes('2a26') || id.includes('software') + }) + if (target == null) return '' + const buf = await this.bluetoothService.readCharacteristic(deviceId, found2Uuid, target.uuid) + try { return new TextDecoder().decode(new Uint8Array(buf)) } catch (e) { return '' } + } +} diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts.ts new file mode 100644 index 0000000..09c394a --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts.ts @@ -0,0 +1,34 @@ +// Minimal error definitions used across the BLE module. +// Keep this file small and avoid runtime dependencies; it's mainly for typing and +// simple runtime error construction used by native platform code. + +export enum AkBluetoothErrorCode { + UnknownError = 0, + DeviceNotFound = 1, + ServiceNotFound = 2, + CharacteristicNotFound = 3, + ConnectionTimeout = 4, + Unspecified = 99 +} + +export class AkBleErrorImpl extends Error { + public code: AkBluetoothErrorCode; + public detail: any|null; + constructor(code: AkBluetoothErrorCode, message?: string, detail: any|null = null) { + super(message ?? AkBleErrorImpl.defaultMessage(code)); + this.name = 'AkBleError'; + this.code = code; + this.detail = detail; + } + static defaultMessage(code: AkBluetoothErrorCode) { + switch (code) { + case AkBluetoothErrorCode.DeviceNotFound: return 'Device not found'; + case AkBluetoothErrorCode.ServiceNotFound: return 'Service not found'; + case AkBluetoothErrorCode.CharacteristicNotFound: return 'Characteristic not found'; + case AkBluetoothErrorCode.ConnectionTimeout: return 'Connection timed out'; + case AkBluetoothErrorCode.UnknownError: default: return 'Unknown Bluetooth error'; + } + } +} + +export default AkBleErrorImpl; diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts.ts new file mode 100644 index 0000000..8343697 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts.ts @@ -0,0 +1,76 @@ +import Context from "android.content.Context"; +import BatteryManager from "android.os.BatteryManager"; + +import { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts' +import IntentFilter from 'android.content.IntentFilter'; +import Intent from 'android.content.Intent'; + +import { GetBatteryInfoFailImpl } from '../unierror'; + +/** + * 异步获取电量 + */ +export const getBatteryInfo : GetBatteryInfo = function (options : GetBatteryInfoOptions) { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const manager = context.getSystemService( + Context.BATTERY_SERVICE + ) as BatteryManager; + const level = manager.getIntProperty( + BatteryManager.BATTERY_PROPERTY_CAPACITY + ); + + let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED); + let batteryStatus = context.registerReceiver(null, ifilter); + let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1); + let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL; + + const res : GetBatteryInfoSuccess = { + errMsg: 'getBatteryInfo:ok', + level, + isCharging: isCharging + } + options.success?.(res) + options.complete?.(res) + } else { + let res = new GetBatteryInfoFailImpl(1001); + options.fail?.(res) + options.complete?.(res) + } +} + +/** + * 同步获取电量 + */ +export const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const manager = context.getSystemService( + Context.BATTERY_SERVICE + ) as BatteryManager; + const level = manager.getIntProperty( + BatteryManager.BATTERY_PROPERTY_CAPACITY + ); + + let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED); + let batteryStatus = context.registerReceiver(null, ifilter); + let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1); + let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL; + + const res : GetBatteryInfoResult = { + level: level, + isCharging: isCharging + }; + return res; + } + else { + /** + * 无有效上下文 + */ + const res : GetBatteryInfoResult = { + level: -1, + isCharging: false + }; + return res; + } +} diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-ios/index.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-ios/index.uts.ts new file mode 100644 index 0000000..5578c9f --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-ios/index.uts.ts @@ -0,0 +1,36 @@ +// 引用 iOS 原生平台 api +import { UIDevice } from "UIKit"; + +import { GetBatteryInfo, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts'; + +/** + * 异步获取电量 + */ +export const getBatteryInfo : GetBatteryInfo = function (options) { + // 开启电量检测 + UIDevice.current.isBatteryMonitoringEnabled = true + + // 返回数据 + const res : GetBatteryInfoSuccess = { + errMsg: "getBatteryInfo:ok", + level: Math.abs(Number(UIDevice.current.batteryLevel * 100)), + isCharging: UIDevice.current.batteryState == UIDevice.BatteryState.charging, + }; + options.success?.(res); + options.complete?.(res); +} + +/** + * 同步获取电量 + */ +export const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult { + // 开启电量检测 + UIDevice.current.isBatteryMonitoringEnabled = true + + // 返回数据 + const res : GetBatteryInfoResult = { + level: Math.abs(Number(UIDevice.current.batteryLevel * 100)), + isCharging: UIDevice.current.batteryState == UIDevice.BatteryState.charging, + }; + return res; +} diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/index.d.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/index.d.ts new file mode 100644 index 0000000..367327b --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/index.d.ts @@ -0,0 +1,43 @@ +declare namespace UniNamespace { + interface GetBatteryInfoSuccessCallbackResult { + /** + * 是否正在充电中 + */ + isCharging: boolean; + /** + * 设备电量,范围 1 - 100 + */ + level: number; + errMsg: string; + } + + interface GetBatteryInfoOption { + /** + * 接口调用结束的回调函数(调用成功、失败都会执行) + */ + complete?: Function + /** + * 接口调用失败的回调函数 + */ + fail?: Function + /** + * 接口调用成功的回调函数 + */ + success?: (result: GetBatteryInfoSuccessCallbackResult) => void + } +} + +declare interface Uni { + /** + * 获取设备电量 + * + * @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html + */ + getBatteryInfo(option?: UniNamespace.GetBatteryInfoOption): void; + + /** + * 同步获取电池电量信息 + * @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html + */ + getBatteryInfoSync(): UniNamespace.GetBatteryInfoSuccessCallbackResult; +} diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts.ts new file mode 100644 index 0000000..21ee06a --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts.ts @@ -0,0 +1,138 @@ +export type GetBatteryInfoSuccess = { + errMsg : string, + /** + * 设备电量,范围1 - 100 + */ + level : number, + /** + * 是否正在充电中 + */ + isCharging : boolean +} + +export type GetBatteryInfoOptions = { + /** + * 接口调用结束的回调函数(调用成功、失败都会执行) + */ + success ?: (res : GetBatteryInfoSuccess) => void + /** + * 接口调用失败的回调函数 + */ + fail ?: (res : UniError) => void + /** + * 接口调用成功的回调 + */ + complete ?: (res : any) => void +} + +export type GetBatteryInfoResult = { + /** + * 设备电量,范围1 - 100 + */ + level : number, + /** + * 是否正在充电中 + */ + isCharging : boolean +} + +/** + * 错误码 + * - 1001 getAppContext is null + */ +export type GetBatteryInfoErrorCode = 1001 ; +/** + * GetBatteryInfo 的错误回调参数 + */ +export interface GetBatteryInfoFail extends IUniError { + errCode : GetBatteryInfoErrorCode +}; + +/** +* 获取电量信息 +* @param {GetBatteryInfoOptions} options +* +* +* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html +* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22 +* @since 3.6.11 +* +* @assert () => success({errCode: 0, errSubject: "uni-getBatteryInfo", errMsg: "getBatteryInfo:ok", level: 60, isCharging: false }) +* @assert () => fail({errCode: 1001, errSubject: "uni-getBatteryInfo", errMsg: "getBatteryInfo:fail getAppContext is null" }) +*/ +export type GetBatteryInfo = (options : GetBatteryInfoOptions) => void + + +export type GetBatteryInfoSync = () => GetBatteryInfoResult + +interface Uni { + + /** + * 获取电池电量信息 + * @description 获取电池电量信息 + * @param {GetBatteryInfoOptions} options + * @example + * ```typescript + * uni.getBatteryInfo({ + * success(res) { + * __f__('log','at uni_modules/uni-getbatteryinfo/utssdk/interface.uts:78',res); + * } + * }) + * ``` + * @remark + * - 该接口需要同步调用 + * @uniPlatform { + * "app": { + * "android": { + * "osVer": "4.4.4", + * "uniVer": "3.6.11", + * "unixVer": "3.9.0" + * }, + * "ios": { + * "osVer": "12.0", + * "uniVer": "3.6.11", + * "unixVer": "4.11" + * } + * }, + * "web": { + * "uniVer": "3.6.11", + * "unixVer": "4.0" + * } + * } + * @uniVueVersion 2,3 //支持的vue版本 + * + */ + getBatteryInfo (options : GetBatteryInfoOptions) : void, + /** + * 同步获取电池电量信息 + * @description 获取电池电量信息 + * @example + * ```typescript + * uni.getBatteryInfo() + * ``` + * @remark + * - 该接口需要同步调用 + * @uniPlatform { + * "app": { + * "android": { + * "osVer": "4.4.4", + * "uniVer": "3.6.11", + * "unixVer": "3.9.0" + * }, + * "ios": { + * "osVer": "12.0", + * "uniVer": "3.6.11", + * "unixVer": "4.11" + * } + * }, + * "web": { + * "uniVer": "3.6.11", + * "unixVer": "4.0" + * } + * } + * @uniVueVersion 2,3 //支持的vue版本 + * + */ + getBatteryInfoSync():GetBatteryInfoResult + +} diff --git a/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts.ts b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts.ts new file mode 100644 index 0000000..43d0be5 --- /dev/null +++ b/unpackage/dist/dev/.tsc/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts.ts @@ -0,0 +1,34 @@ +import { GetBatteryInfoErrorCode, GetBatteryInfoFail } from "./interface.uts" +/** + * 错误主题 + */ +export const UniErrorSubject = 'uni-getBatteryInfo'; + + +/** + * 错误信息 + * @UniError + */ +export const UniErrors : Map = new Map([ + /** + * 错误码及对应的错误信息 + */ + [1001, 'getBatteryInfo:fail getAppContext is null'], +]); + + +/** + * 错误对象实现 + */ +export class GetBatteryInfoFailImpl extends UniError implements GetBatteryInfoFail { + + /** + * 错误对象构造函数 + */ + constructor(errCode : GetBatteryInfoErrorCode) { + super(); + this.errSubject = UniErrorSubject; + this.errCode = errCode; + this.errMsg = UniErrors[errCode] ?? ""; + } +} \ No newline at end of file diff --git a/unpackage/dist/dev/.tsc/uni-ext-api.d.ts b/unpackage/dist/dev/.tsc/uni-ext-api.d.ts new file mode 100644 index 0000000..786202a --- /dev/null +++ b/unpackage/dist/dev/.tsc/uni-ext-api.d.ts @@ -0,0 +1,5 @@ + +interface Uni { + getBatteryInfo: typeof import("@/uni_modules/uni-getbatteryinfo")["getBatteryInfo"] + getBatteryInfoSync: typeof import("@/uni_modules/uni-getbatteryinfo")["getBatteryInfoSync"] +} diff --git a/unpackage/dist/dev/.uvue/app-android/App.uvue b/unpackage/dist/dev/.uvue/app-android/App.uvue new file mode 100644 index 0000000..b8387af --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/App.uvue @@ -0,0 +1,37 @@ +// import { initTables } from './ak/sqlite.uts' +let firstBackTime = 0; +const __sfc__ = defineApp({ + onLaunch: function () { + console.log('App Launch', " at App.uvue:10"); + // initTables(); + }, + onShow: function () { + console.log('App Show', " at App.uvue:15"); + }, + onHide: function () { + console.log('App Hide', " at App.uvue:18"); + }, + onLastPageBackPress: function () { + console.log('App LastPageBackPress', " at App.uvue:22"); + if (firstBackTime == 0) { + uni.showToast({ + title: '再按一次退出应用', + position: 'bottom', + }); + firstBackTime = Date.now(); + setTimeout(() => { + firstBackTime = 0; + }, 2000); + } + else if (Date.now() - firstBackTime < 2000) { + firstBackTime = Date.now(); + uni.exit(); + } + }, + onExit: function () { + console.log('App Exit', " at App.uvue:39"); + }, +}); +export default __sfc__; +const GenAppStyles = [_uM([["uni-row", _pS(_uM([["flexDirection", "row"]]))], ["uni-column", _pS(_uM([["flexDirection", "column"]]))]])]; +//# sourceMappingURL=App.uvue.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/App.uvue.map b/unpackage/dist/dev/.uvue/app-android/App.uvue.map new file mode 100644 index 0000000..bb10a33 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/App.uvue.map @@ -0,0 +1 @@ +{"version":3,"sources":["App.uvue"],"names":[],"mappings":"AAEC,+CAA8C;AAI/C,IAAI,aAAY,GAAI,CAAA,CAAA;AACpB,MAAK,OAAQ,GAAE,SAAA,CAAA;IACb,QAAQ,EAAE;QACT,OAAO,CAAC,GAAG,CAAC,YAAY,EAAA,iBAAA,CAAA,CAAA;QACxB,gBAAe;IAEhB,CAAC;IACD,MAAM,EAAE;QACP,OAAO,CAAC,GAAG,CAAC,UAAU,EAAA,iBAAA,CAAA,CAAA;IACvB,CAAC;IACD,MAAM,EAAE;QACP,OAAO,CAAC,GAAG,CAAC,UAAU,EAAA,iBAAA,CAAA,CAAA;IACvB,CAAC;IAED,mBAAmB,EAAE;QACpB,OAAO,CAAC,GAAG,CAAC,uBAAuB,EAAA,iBAAA,CAAA,CAAA;QACnC,IAAI,aAAY,IAAK,CAAC,EAAE;YACvB,GAAG,CAAC,SAAS,CAAC;gBACb,KAAK,EAAE,UAAU;gBACjB,QAAQ,EAAE,QAAQ;aAClB,CAAA,CAAA;YACD,aAAY,GAAI,IAAI,CAAC,GAAG,EAAC,CAAA;YACzB,UAAU,CAAC,GAAG,EAAC;gBACd,aAAY,GAAI,CAAA,CAAA;YACjB,CAAC,EAAE,IAAI,CAAA,CAAA;SACR;aAAO,IAAI,IAAI,CAAC,GAAG,EAAC,GAAI,aAAY,GAAI,IAAI,EAAE;YAC7C,aAAY,GAAI,IAAI,CAAC,GAAG,EAAC,CAAA;YACzB,GAAG,CAAC,IAAI,EAAC,CAAA;SACV;IACD,CAAC;IAED,MAAM,EAAE;QACP,OAAO,CAAC,GAAG,CAAC,UAAU,EAAA,iBAAA,CAAA,CAAA;IACvB,CAAC;CACF,CAAA,CAAA","file":"App.uvue","sourceRoot":"","sourcesContent":["\r\n\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/ak/PermissionManager.uts b/unpackage/dist/dev/.uvue/app-android/ak/PermissionManager.uts new file mode 100644 index 0000000..8476b11 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/ak/PermissionManager.uts @@ -0,0 +1,305 @@ +/** + * PermissionManager.uts + * + * Utility class for managing Android permissions throughout the app + * Handles requesting permissions, checking status, and directing users to settings + */ +/** + * Common permission types that can be requested + */ +export enum PermissionType { + BLUETOOTH = 'bluetooth', + LOCATION = 'location', + STORAGE = 'storage', + CAMERA = 'camera', + MICROPHONE = 'microphone', + NOTIFICATIONS = 'notifications', + CALENDAR = 'calendar', + CONTACTS = 'contacts', + SENSORS = 'sensors' +} +/** + * Result of a permission request + */ +type PermissionResult = { + granted: boolean; + grantedPermissions: string[]; + deniedPermissions: string[]; +}; +/** + * Manages permission requests and checks throughout the app + */ +export class PermissionManager { + /** + * Maps permission types to the actual Android permission strings + */ + private static getPermissionsForType(type: PermissionType): string[] { + switch (type) { + case PermissionType.BLUETOOTH: + return [ + 'android.permission.BLUETOOTH_SCAN', + 'android.permission.BLUETOOTH_CONNECT', + 'android.permission.BLUETOOTH_ADVERTISE' + ]; + case PermissionType.LOCATION: + return [ + 'android.permission.ACCESS_FINE_LOCATION', + 'android.permission.ACCESS_COARSE_LOCATION' + ]; + case PermissionType.STORAGE: + return [ + 'android.permission.READ_EXTERNAL_STORAGE', + 'android.permission.WRITE_EXTERNAL_STORAGE' + ]; + case PermissionType.CAMERA: + return ['android.permission.CAMERA']; + case PermissionType.MICROPHONE: + return ['android.permission.RECORD_AUDIO']; + case PermissionType.NOTIFICATIONS: + return ['android.permission.POST_NOTIFICATIONS']; + case PermissionType.CALENDAR: + return [ + 'android.permission.READ_CALENDAR', + 'android.permission.WRITE_CALENDAR' + ]; + case PermissionType.CONTACTS: + return [ + 'android.permission.READ_CONTACTS', + 'android.permission.WRITE_CONTACTS' + ]; + case PermissionType.SENSORS: + return ['android.permission.BODY_SENSORS']; + default: + return []; + } + } + /** + * Get appropriate display name for a permission type + */ + private static getPermissionDisplayName(type: PermissionType): string { + switch (type) { + case PermissionType.BLUETOOTH: + return '蓝牙'; + case PermissionType.LOCATION: + return '位置'; + case PermissionType.STORAGE: + return '存储'; + case PermissionType.CAMERA: + return '相机'; + case PermissionType.MICROPHONE: + return '麦克风'; + case PermissionType.NOTIFICATIONS: + return '通知'; + case PermissionType.CALENDAR: + return '日历'; + case PermissionType.CONTACTS: + return '联系人'; + case PermissionType.SENSORS: + return '身体传感器'; + default: + return '未知权限'; + } + } + /** + * Check if a permission is granted + * @param type The permission type to check + * @returns True if the permission is granted, false otherwise + */ + static isPermissionGranted(type: PermissionType): boolean { + try { + const permissions = this.getPermissionsForType(type); + const activity = UTSAndroid.getUniActivity(); + if (activity == null || permissions.length === 0) { + return false; + } + // Check each permission in the group + for (const permission of permissions) { + if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) { + return false; + } + } + return true; + } + catch (e: any) { + __f__('error', 'at ak/PermissionManager.uts:132', `Error checking ${type} permission:`, e); + return false; + } + } + /** + * Request a permission from the user + * @param type The permission type to request + * @param callback Function to call with the result of the permission request + * @param showRationale Whether to show a rationale dialog if permission was previously denied + */ + static requestPermission(type: PermissionType, callback: (result: PermissionResult) => void, showRationale: boolean = true): void { + try { + const permissions = this.getPermissionsForType(type); + const activity = UTSAndroid.getUniActivity(); + if (activity == null || permissions.length === 0) { + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: permissions + } as PermissionResult); + return; + } + // Check if already granted + let allGranted = true; + for (const permission of permissions) { + if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) { + allGranted = false; + break; + } + } + if (allGranted) { + callback({ + granted: true, + grantedPermissions: permissions, + deniedPermissions: [] + } as PermissionResult); + return; + } + // Request the permissions + UTSAndroid.requestSystemPermission(activity, permissions, (granted: boolean, grantedPermissions: string[]) => { + if (granted) { + callback({ + granted: true, + grantedPermissions: grantedPermissions, + deniedPermissions: [] + } as PermissionResult); + } + else if (showRationale) { + // Show rationale dialog + this.showPermissionRationale(type, callback); + } + else { + // Just report the denial + callback({ + granted: false, + grantedPermissions: grantedPermissions, + deniedPermissions: this.getDeniedPermissions(permissions, grantedPermissions) + } as PermissionResult); + } + }, (denied: boolean, deniedPermissions: string[]) => { + callback({ + granted: false, + grantedPermissions: this.getGrantedPermissions(permissions, deniedPermissions), + deniedPermissions: deniedPermissions + } as PermissionResult); + }); + } + catch (e: any) { + __f__('error', 'at ak/PermissionManager.uts:217', `Error requesting ${type} permission:`, e); + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + } as PermissionResult); + } + } + /** + * Show a rationale dialog explaining why the permission is needed + */ + private static showPermissionRationale(type: PermissionType, callback: (result: PermissionResult) => void): void { + const permissionName = this.getPermissionDisplayName(type); + uni.showModal({ + title: '权限申请', + content: `需要${permissionName}权限才能使用相关功能`, + confirmText: '去设置', + cancelText: '取消', + success: (result) => { + if (result.confirm) { + this.openAppSettings(); + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + } as PermissionResult); + } + else { + callback({ + granted: false, + grantedPermissions: [], + deniedPermissions: this.getPermissionsForType(type) + } as PermissionResult); + } + } + }); + } + /** + * Open the app settings page + */ + static openAppSettings(): void { + try { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const intent = new android.content.Intent(); + intent.setAction("android.settings.APPLICATION_DETAILS_SETTINGS"); + const uri = android.net.Uri.fromParts("package", context.getPackageName(), null); + intent.setData(uri); + intent.addFlags(android.content.Intent.FLAG_ACTIVITY_NEW_TASK); + context.startActivity(intent); + } + } + catch (e: any) { + __f__('error', 'at ak/PermissionManager.uts:285', 'Failed to open app settings', e); + uni.showToast({ + title: '请手动前往系统设置修改应用权限', + icon: 'none', + duration: 3000 + }); + } + } + /** + * Helper to get the list of granted permissions + */ + private static getGrantedPermissions(allPermissions: string[], deniedPermissions: string[]): string[] { + return allPermissions.filter((p): boolean => !deniedPermissions.includes(p)); + } + /** + * Helper to get the list of denied permissions + */ + private static getDeniedPermissions(allPermissions: string[], grantedPermissions: string[]): string[] { + return allPermissions.filter((p): boolean => !grantedPermissions.includes(p)); + } + /** + * Request multiple permission types at once + * @param types Array of permission types to request + * @param callback Function to call when all permissions have been processed + */ + static requestMultiplePermissions(types: PermissionType[], callback: (results: Map) => void): void { + if (types.length === 0) { + callback(new Map()); + return; + } + const results = new Map(); + let remaining = types.length; + for (const type of types) { + this.requestPermission(type, (result) => { + results.set(type, result); + remaining--; + if (remaining === 0) { + callback(results); + } + }, true); + } + } + /** + * Convenience method to request Bluetooth permissions + * @param callback Function to call after the permission request + */ + static requestBluetoothPermissions(callback: (granted: boolean) => void): void { + this.requestPermission(PermissionType.BLUETOOTH, (result) => { + // For Bluetooth, we also need location permissions on Android + if (result.granted) { + this.requestPermission(PermissionType.LOCATION, (locationResult) => { + callback(locationResult.granted); + }); + } + else { + callback(false); + } + }); + } +} +//# sourceMappingURL=PermissionManager.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/ak/PermissionManager.uts.map b/unpackage/dist/dev/.uvue/app-android/ak/PermissionManager.uts.map new file mode 100644 index 0000000..bf490c2 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/ak/PermissionManager.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"PermissionManager.uts","sourceRoot":"","sources":["ak/PermissionManager.uts"],"names":[],"mappings":"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","sourcesContent":["/**\r\n * PermissionManager.uts\r\n * \r\n * Utility class for managing Android permissions throughout the app\r\n * Handles requesting permissions, checking status, and directing users to settings\r\n */\r\n\r\n/**\r\n * Common permission types that can be requested\r\n */\r\nexport enum PermissionType {\r\n BLUETOOTH = 'bluetooth',\r\n LOCATION = 'location',\r\n STORAGE = 'storage',\r\n CAMERA = 'camera',\r\n MICROPHONE = 'microphone',\r\n NOTIFICATIONS = 'notifications',\r\n CALENDAR = 'calendar',\r\n CONTACTS = 'contacts',\r\n SENSORS = 'sensors'\r\n}\r\n\r\n/**\r\n * Result of a permission request\r\n */\r\ntype PermissionResult = {\r\n granted: boolean;\r\n grantedPermissions: string[];\r\n deniedPermissions: string[];\r\n}\r\n\r\n/**\r\n * Manages permission requests and checks throughout the app\r\n */\r\nexport class PermissionManager {\r\n /**\r\n * Maps permission types to the actual Android permission strings\r\n */\r\n private static getPermissionsForType(type: PermissionType): string[] {\r\n switch (type) {\r\n case PermissionType.BLUETOOTH:\r\n return [\r\n 'android.permission.BLUETOOTH_SCAN',\r\n 'android.permission.BLUETOOTH_CONNECT',\r\n 'android.permission.BLUETOOTH_ADVERTISE'\r\n ];\r\n case PermissionType.LOCATION:\r\n return [\r\n 'android.permission.ACCESS_FINE_LOCATION',\r\n 'android.permission.ACCESS_COARSE_LOCATION'\r\n ];\r\n case PermissionType.STORAGE:\r\n return [\r\n 'android.permission.READ_EXTERNAL_STORAGE',\r\n 'android.permission.WRITE_EXTERNAL_STORAGE'\r\n ];\r\n case PermissionType.CAMERA:\r\n return ['android.permission.CAMERA'];\r\n case PermissionType.MICROPHONE:\r\n return ['android.permission.RECORD_AUDIO'];\r\n case PermissionType.NOTIFICATIONS:\r\n return ['android.permission.POST_NOTIFICATIONS'];\r\n case PermissionType.CALENDAR:\r\n return [\r\n 'android.permission.READ_CALENDAR',\r\n 'android.permission.WRITE_CALENDAR'\r\n ];\r\n case PermissionType.CONTACTS:\r\n return [\r\n 'android.permission.READ_CONTACTS',\r\n 'android.permission.WRITE_CONTACTS'\r\n ];\r\n case PermissionType.SENSORS:\r\n return ['android.permission.BODY_SENSORS'];\r\n default:\r\n return [];\r\n }\r\n }\r\n \r\n /**\r\n * Get appropriate display name for a permission type\r\n */\r\n private static getPermissionDisplayName(type: PermissionType): string {\r\n switch (type) {\r\n case PermissionType.BLUETOOTH:\r\n return '蓝牙';\r\n case PermissionType.LOCATION:\r\n return '位置';\r\n case PermissionType.STORAGE:\r\n return '存储';\r\n case PermissionType.CAMERA:\r\n return '相机';\r\n case PermissionType.MICROPHONE:\r\n return '麦克风';\r\n case PermissionType.NOTIFICATIONS:\r\n return '通知';\r\n case PermissionType.CALENDAR:\r\n return '日历';\r\n case PermissionType.CONTACTS:\r\n return '联系人';\r\n case PermissionType.SENSORS:\r\n return '身体传感器';\r\n default:\r\n return '未知权限';\r\n }\r\n }\r\n \r\n /**\r\n * Check if a permission is granted\r\n * @param type The permission type to check\r\n * @returns True if the permission is granted, false otherwise\r\n */\r\n static isPermissionGranted(type: PermissionType): boolean {\r\n\r\n try {\r\n const permissions = this.getPermissionsForType(type);\r\n const activity = UTSAndroid.getUniActivity();\r\n \r\n if (activity == null || permissions.length === 0) {\r\n return false;\r\n }\r\n \r\n // Check each permission in the group\r\n for (const permission of permissions) {\r\n if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) {\r\n return false;\r\n }\r\n }\r\n \r\n return true;\r\n } catch (e) {\r\n __f__('error','at ak/PermissionManager.uts:132',`Error checking ${type} permission:`, e);\r\n return false;\r\n }\r\n\r\n \r\n\r\n\r\n\r\n }\r\n \r\n /**\r\n * Request a permission from the user\r\n * @param type The permission type to request\r\n * @param callback Function to call with the result of the permission request\r\n * @param showRationale Whether to show a rationale dialog if permission was previously denied\r\n */\r\n static requestPermission(\r\n type: PermissionType,\r\n callback: (result: PermissionResult) => void,\r\n showRationale: boolean = true\r\n ): void {\r\n\r\n try {\r\n const permissions = this.getPermissionsForType(type);\r\n const activity = UTSAndroid.getUniActivity();\r\n \r\n if (activity == null || permissions.length === 0) {\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: permissions\r\n });\r\n return;\r\n }\r\n \r\n // Check if already granted\r\n let allGranted = true;\r\n for (const permission of permissions) {\r\n if (!UTSAndroid.checkSystemPermissionGranted(activity, [permission])) {\r\n allGranted = false;\r\n break;\r\n }\r\n }\r\n \r\n if (allGranted) {\r\n callback({\r\n granted: true,\r\n grantedPermissions: permissions,\r\n deniedPermissions: []\r\n });\r\n return;\r\n }\r\n \r\n // Request the permissions\r\n UTSAndroid.requestSystemPermission(\r\n activity,\r\n permissions,\r\n (granted: boolean, grantedPermissions: string[]) => {\r\n if (granted) {\r\n callback({\r\n granted: true,\r\n grantedPermissions: grantedPermissions,\r\n deniedPermissions: []\r\n });\r\n } else if (showRationale) {\r\n // Show rationale dialog\r\n this.showPermissionRationale(type, callback);\r\n } else {\r\n // Just report the denial\r\n callback({\r\n granted: false,\r\n grantedPermissions: grantedPermissions,\r\n deniedPermissions: this.getDeniedPermissions(permissions, grantedPermissions)\r\n });\r\n }\r\n },\r\n (denied: boolean, deniedPermissions: string[]) => {\r\n callback({\r\n granted: false,\r\n grantedPermissions: this.getGrantedPermissions(permissions, deniedPermissions),\r\n deniedPermissions: deniedPermissions\r\n });\r\n }\r\n );\r\n } catch (e) {\r\n __f__('error','at ak/PermissionManager.uts:217',`Error requesting ${type} permission:`, e);\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: this.getPermissionsForType(type)\r\n });\r\n }\r\n\r\n \r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n }\r\n \r\n /**\r\n * Show a rationale dialog explaining why the permission is needed\r\n */\r\n private static showPermissionRationale(\r\n type: PermissionType,\r\n callback: (result: PermissionResult) => void\r\n ): void {\r\n const permissionName = this.getPermissionDisplayName(type);\r\n \r\n uni.showModal({\r\n title: '权限申请',\r\n content: `需要${permissionName}权限才能使用相关功能`,\r\n confirmText: '去设置',\r\n cancelText: '取消',\r\n success: (result) => {\r\n if (result.confirm) {\r\n this.openAppSettings();\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: this.getPermissionsForType(type)\r\n });\r\n } else {\r\n callback({\r\n granted: false,\r\n grantedPermissions: [],\r\n deniedPermissions: this.getPermissionsForType(type)\r\n });\r\n }\r\n }\r\n });\r\n }\r\n \r\n /**\r\n * Open the app settings page\r\n */\r\n static openAppSettings(): void {\r\n\r\n try {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const intent = new android.content.Intent();\r\n intent.setAction(\"android.settings.APPLICATION_DETAILS_SETTINGS\");\r\n const uri = android.net.Uri.fromParts(\"package\", context.getPackageName(), null);\r\n intent.setData(uri);\r\n intent.addFlags(android.content.Intent.FLAG_ACTIVITY_NEW_TASK);\r\n context.startActivity(intent);\r\n }\r\n } catch (e) {\r\n __f__('error','at ak/PermissionManager.uts:285','Failed to open app settings', e);\r\n uni.showToast({\r\n title: '请手动前往系统设置修改应用权限',\r\n icon: 'none',\r\n duration: 3000\r\n });\r\n }\r\n\r\n \r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n }\r\n \r\n /**\r\n * Helper to get the list of granted permissions\r\n */\r\n private static getGrantedPermissions(allPermissions: string[], deniedPermissions: string[]): string[] {\r\n return allPermissions.filter(p => !deniedPermissions.includes(p));\r\n }\r\n \r\n /**\r\n * Helper to get the list of denied permissions\r\n */\r\n private static getDeniedPermissions(allPermissions: string[], grantedPermissions: string[]): string[] {\r\n return allPermissions.filter(p => !grantedPermissions.includes(p));\r\n }\r\n \r\n /**\r\n * Request multiple permission types at once\r\n * @param types Array of permission types to request\r\n * @param callback Function to call when all permissions have been processed\r\n */\r\n static requestMultiplePermissions(\r\n types: PermissionType[],\r\n callback: (results: Map) => void\r\n ): void {\r\n if (types.length === 0) {\r\n callback(new Map());\r\n return;\r\n }\r\n \r\n const results = new Map();\r\n let remaining = types.length;\r\n \r\n for (const type of types) {\r\n this.requestPermission(\r\n type,\r\n (result) => {\r\n results.set(type, result);\r\n remaining--;\r\n \r\n if (remaining === 0) {\r\n callback(results);\r\n }\r\n },\r\n true\r\n );\r\n }\r\n }\r\n \r\n /**\r\n * Convenience method to request Bluetooth permissions\r\n * @param callback Function to call after the permission request\r\n */\r\n static requestBluetoothPermissions(callback: (granted: boolean) => void): void {\r\n this.requestPermission(PermissionType.BLUETOOTH, (result) => {\r\n // For Bluetooth, we also need location permissions on Android\r\n if (result.granted) {\r\n this.requestPermission(PermissionType.LOCATION, (locationResult) => {\r\n callback(locationResult.granted);\r\n });\r\n } else {\r\n callback(false);\r\n }\r\n });\r\n }\r\n}"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/main.uts b/unpackage/dist/dev/.uvue/app-android/main.uts new file mode 100644 index 0000000..b1f621b --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/main.uts @@ -0,0 +1,38 @@ +import 'F:/HBuilderX/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/index.ts'; +import App from './App.uvue'; +import { createSSRApp } from 'vue'; +export function createApp(): UTSJSONObject { + const app = createSSRApp(App); + return { + app + }; +} +export function main(app: IApp) { + definePageRoutes(); + defineAppConfig(); + (createApp()['app'] as VueApp).mount(app, GenUniApp()); +} +export class UniAppConfig extends io.dcloud.uniapp.appframe.AppConfig { + override name: string = "akbleserver"; + override appid: string = "__UNI__95B2570"; + override versionName: string = "1.0.1"; + override versionCode: string = "101"; + override uniCompilerVersion: string = "4.76"; + constructor() { super(); } +} +import GenPagesAkbletestClass from './pages/akbletest.uvue'; +function definePageRoutes() { + __uniRoutes.push({ path: "pages/akbletest", component: GenPagesAkbletestClass, meta: { isQuit: true } as UniPageMeta, style: _uM([["navigationBarTitleText", "akble"]]) } as UniPageRoute); +} +const __uniTabBar: Map | null = null; +const __uniLaunchPage: Map = _uM([["url", "pages/akbletest"], ["style", _uM([["navigationBarTitleText", "akble"]])]]); +function defineAppConfig() { + __uniConfig.entryPagePath = '/pages/akbletest'; + __uniConfig.globalStyle = _uM([["navigationBarTextStyle", "black"], ["navigationBarTitleText", "体测训练"], ["navigationBarBackgroundColor", "#F8F8F8"], ["backgroundColor", "#F8F8F8"]]); + __uniConfig.getTabBarConfig = (): Map | null => null; + __uniConfig.tabBar = __uniConfig.getTabBarConfig(); + __uniConfig.conditionUrl = ''; + __uniConfig.uniIdRouter = _uM(); + __uniConfig.ready = true; +} +//# sourceMappingURL=main.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/main.uts.map b/unpackage/dist/dev/.uvue/app-android/main.uts.map new file mode 100644 index 0000000..67d2b9c --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/main.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"main.uts","sourceRoot":"","sources":["main.uts"],"names":[],"mappings":"AAAA,OAAO,kGAAkG,CAAC;AAAA,OAAO,GAAG,MAAM,YAAY,CAAA;AAEtI,OAAO,EAAE,YAAY,EAAE,MAAM,KAAK,CAAA;AAClC,MAAM,UAAU,SAAS;IACxB,MAAM,GAAG,GAAG,YAAY,CAAC,GAAG,CAAC,CAAA;IAC7B,OAAO;QACN,GAAG;KACH,CAAA;AACF,CAAC;AACD,MAAM,UAAU,IAAI,CAAC,GAAG,EAAE,IAAI;IAC1B,gBAAgB,EAAE,CAAC;IACnB,eAAe,EAAE,CAAC;IAClB,CAAC,SAAS,EAAE,CAAC,KAAK,CAAC,IAAI,MAAM,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,SAAS,EAAE,CAAC,CAAC;AAC3D,CAAC;AAED,MAAM,OAAO,YAAa,SAAQ,EAAE,CAAC,MAAM,CAAC,MAAM,CAAC,QAAQ,CAAC,SAAS;IACjE,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,aAAa,CAAA;IACrC,QAAQ,CAAC,KAAK,EAAE,MAAM,GAAG,gBAAgB,CAAA;IACzC,QAAQ,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAA;IACtC,QAAQ,CAAC,WAAW,EAAE,MAAM,GAAG,KAAK,CAAA;IACpC,QAAQ,CAAC,kBAAkB,EAAE,MAAM,GAAG,MAAM,CAAA;IAE5C,gBAAgB,KAAK,EAAE,CAAA,CAAC,CAAC;CAC5B;AAED,OAAO,sBAAsB,MAAM,wBAAwB,CAAA;AAC3D,SAAS,gBAAgB;IACzB,WAAW,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,iBAAiB,EAAE,SAAS,EAAE,sBAAsB,EAAE,IAAI,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,WAAW,EAAE,KAAK,EAAE,GAAG,CAAC,CAAC,CAAC,wBAAwB,EAAC,OAAO,CAAC,CAAC,CAAC,EAAE,IAAI,YAAY,CAAC,CAAA;AACzL,CAAC;AACD,MAAM,WAAW,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,GAAG,IAAI,CAAC,GAAG,IAAI,GAAG,IAAI,CAAA;AACxD,MAAM,eAAe,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,GAAG,IAAI,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,KAAK,EAAC,iBAAiB,CAAC,EAAC,CAAC,OAAO,EAAC,GAAG,CAAC,CAAC,CAAC,wBAAwB,EAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAA;AACrI,SAAS,eAAe;IACtB,WAAW,CAAC,aAAa,GAAG,kBAAkB,CAAA;IAC9C,WAAW,CAAC,WAAW,GAAG,GAAG,CAAC,CAAC,CAAC,wBAAwB,EAAC,OAAO,CAAC,EAAC,CAAC,wBAAwB,EAAC,MAAM,CAAC,EAAC,CAAC,8BAA8B,EAAC,SAAS,CAAC,EAAC,CAAC,iBAAiB,EAAC,SAAS,CAAC,CAAC,CAAC,CAAA;IAC9K,WAAW,CAAC,eAAe,GAAG,IAAG,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,CAAC,EAAE,CAAE,IAAI,CAAA;IACjE,WAAW,CAAC,MAAM,GAAG,WAAW,CAAC,eAAe,EAAE,CAAA;IAClD,WAAW,CAAC,YAAY,GAAG,EAAE,CAAA;IAC7B,WAAW,CAAC,WAAW,GAAG,GAAG,EAAE,CAAA;IAE/B,WAAW,CAAC,KAAK,GAAG,IAAI,CAAA;AAC1B,CAAC","sourcesContent":["import 'F:/HBuilderX/plugins/uniapp-cli-vite/node_modules/@dcloudio/uni-console/src/runtime/app/index.ts';import App from './App.uvue'\r\n\r\nimport { createSSRApp } from 'vue'\r\nexport function createApp() {\r\n\tconst app = createSSRApp(App)\r\n\treturn {\r\n\t\tapp\r\n\t}\r\n}\nexport function main(app: IApp) {\n definePageRoutes();\n defineAppConfig();\n (createApp()['app'] as VueApp).mount(app, GenUniApp());\n}\n\nexport class UniAppConfig extends io.dcloud.uniapp.appframe.AppConfig {\n override name: string = \"akbleserver\"\n override appid: string = \"__UNI__95B2570\"\n override versionName: string = \"1.0.1\"\n override versionCode: string = \"101\"\n override uniCompilerVersion: string = \"4.76\"\n \n constructor() { super() }\n}\n\nimport GenPagesAkbletestClass from './pages/akbletest.uvue'\nfunction definePageRoutes() {\n__uniRoutes.push({ path: \"pages/akbletest\", component: GenPagesAkbletestClass, meta: { isQuit: true } as UniPageMeta, style: _uM([[\"navigationBarTitleText\",\"akble\"]]) } as UniPageRoute)\n}\nconst __uniTabBar: Map | null = null\nconst __uniLaunchPage: Map = _uM([[\"url\",\"pages/akbletest\"],[\"style\",_uM([[\"navigationBarTitleText\",\"akble\"]])]])\nfunction defineAppConfig(){\n __uniConfig.entryPagePath = '/pages/akbletest'\n __uniConfig.globalStyle = _uM([[\"navigationBarTextStyle\",\"black\"],[\"navigationBarTitleText\",\"体测训练\"],[\"navigationBarBackgroundColor\",\"#F8F8F8\"],[\"backgroundColor\",\"#F8F8F8\"]])\n __uniConfig.getTabBarConfig = ():Map | null => null\n __uniConfig.tabBar = __uniConfig.getTabBarConfig()\n __uniConfig.conditionUrl = ''\n __uniConfig.uniIdRouter = _uM()\n \n __uniConfig.ready = true\n}\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/pages/akbletest.uvue b/unpackage/dist/dev/.uvue/app-android/pages/akbletest.uvue new file mode 100644 index 0000000..98ed0c6 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/pages/akbletest.uvue @@ -0,0 +1,839 @@ +import { DfuOptions } from "../uni_modules/ak-sbsrv/utssdk/interface"; +import { ScanDevicesOptions } from "../uni_modules/ak-sbsrv/utssdk/interface"; +import { BleConnectOptionsExt } from "../uni_modules/ak-sbsrv/utssdk/interface"; +import { BluetoothService } from '@/uni_modules/ak-sbsrv/utssdk/interface.uts'; +// Platform-specific entrypoint: import the platform index per build target to avoid bundler including Android-only code in web builds +import { bluetoothService } from '@/uni_modules/ak-sbsrv/utssdk/app-android/index.uts'; +import type { BleDevice, BleService, BleCharacteristic } from '@/uni_modules/ak-sbsrv/utssdk/interface.uts'; +import { ProtocolHandler } from '@/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts'; +import { dfuManager } from '@/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts'; +import { PermissionManager } from '@/ak/PermissionManager.uts'; +type ShowingCharacteristicsFor = { + __$originalPosition?: UTSSourceMapPosition<"ShowingCharacteristicsFor", "pages/akbletest.uvue", 107, 7>; + deviceId: string; + serviceId: string; +}; +const __sfc__ = defineComponent({ + data() { + return { + scanning: false, + connecting: false, + disconnecting: false, + devices: [] as BleDevice[], + connectedIds: [] as string[], + logs: [] as string[], + showingServicesFor: '', + services: [] as BleService[], + showingCharacteristicsFor: { deviceId: '', serviceId: '' } as ShowingCharacteristicsFor, + characteristics: [] as BleCharacteristic[], + // 新增协议相关参数 + protocolDeviceId: '', + protocolServiceId: '', + protocolWriteCharId: '', + protocolNotifyCharId: '', + // protocol handler instances/cache + protocolHandlerMap: new Map(), + protocolHandler: null as ProtocolHandler | null, + // optional services input (comma-separated UUIDs) + optionalServicesInput: '', + // presets for common BLE services (label -> UUID). 'custom' allows free-form input. + presetOptions: [ + { label: '无', value: '' }, + { label: 'Battery Service (180F)', value: '0000180f-0000-1000-8000-00805f9b34fb' }, + { label: 'Device Information (180A)', value: '0000180a-0000-1000-8000-00805f9b34fb' }, + { label: 'Generic Attribute (1801)', value: '00001801-0000-1000-8000-00805f9b34fb' }, + { label: 'Nordic DFU', value: '00001530-1212-efde-1523-785feabcd123' }, + { label: 'Nordic UART (NUS)', value: '6e400001-b5a3-f393-e0a9-e50e24dcca9e' }, + { label: '自定义', value: 'custom' } + ], + presetSelected: '', + // map of characteristicId -> boolean (is currently subscribed) + notifyingMap: new Map(), + }; + }, + mounted() { + PermissionManager.requestBluetoothPermissions((granted: boolean) => { + if (!granted) { + uni.showToast({ title: '请授权蓝牙和定位权限', icon: 'none' }); + } + }); + this.log('页面 mounted: 初始化事件监听和蓝牙权限请求完成'); + // deviceFound - only accept devices whose name starts with 'CF' or 'BCL' + bluetoothService.on('deviceFound', (payload) => { + try { + // this.log('[event] deviceFound -> ' + this._fmt(payload)) + // console.log('[event] deviceFound -> ' + this._fmt(payload)) + // payload can be UTSJSONObject-like or plain object. Normalize. + let rawDevice = payload?.device; + if (rawDevice == null) { + this.log('[event] deviceFound - payload.device is null, ignoring'); + return; + } + // extract name + let name: string | null = rawDevice.name; + if (name == null) { + this.log('[event] deviceFound - 无名称,忽略: ' + this._fmt(rawDevice as any)); + return; + } + const n = name as string; + if (!(n.startsWith('CF') || n.startsWith('BCL'))) { + this.log('[event] deviceFound - 名称不匹配前缀,忽略: ' + n); + return; + } + const exists = this.devices.some((d): boolean => d != null && d.name == n); + if (!exists) { + // rawDevice is non-null here per earlier guard + this.devices.push(rawDevice as BleDevice); + const deviceIdStr = (rawDevice.deviceId != null) ? rawDevice.deviceId : ''; + this.log('发现设备: ' + n + ' (' + deviceIdStr + ')'); + } + else { + const deviceIdStr = (rawDevice.deviceId != null) ? rawDevice.deviceId : ''; + this.log('发现重复设备: ' + n + ' (' + deviceIdStr + ')'); + } + } + catch (err: any) { + this.log('[error] deviceFound handler error: ' + getErrorMessage(err)); + console.log(err, " at pages/akbletest.uvue:198"); + } + }); + // scanFinished + bluetoothService.on('scanFinished', (payload) => { + try { + this.scanning = false; + this.log('[event] scanFinished -> ' + this._fmt(payload)); + } + catch (err: any) { + this.log('[error] scanFinished handler error: ' + getErrorMessage(err)); + } + }); + // connectionStateChanged + bluetoothService.on('connectionStateChanged', (payload) => { + try { + this.log('[event] connectionStateChanged -> ' + this._fmt(payload)); + if (payload != null) { + const device = payload.device; + const state = payload.state; + this.log(`设备 ${device?.deviceId} 连接状态变为: ${state}`); + // maintain connectedIds + if (state == 2) { + if (device != null && device.deviceId != null && !this.connectedIds.includes(device.deviceId)) { + this.connectedIds.push(device.deviceId); + this.log(`已记录已连接设备: ${device.deviceId}`); + } + } + else if (state == 0) { + if (device != null && device.deviceId != null) { + this.connectedIds = this.connectedIds.filter((id): boolean => id !== device.deviceId); + this.log(`已移除已断开设备: ${device.deviceId}`); + } + } + } + } + catch (err: any) { + this.log('[error] connectionStateChanged handler error: ' + getErrorMessage(err)); + } + }); + }, + methods: { + async startDfuFlow(deviceId: string, staticFilePath: string = ''): Promise { + if (staticFilePath != null && staticFilePath !== '') { + this.log('DFU 开始: 使用内置固件文件 ' + staticFilePath); + } + else { + this.log('DFU 开始: 请选择固件文件'); + } + try { + let chosenPath: string | null = null; + let fileName: string | null = null; + if (staticFilePath != null && staticFilePath !== '') { + // Use the app's bundled static file path + chosenPath = staticFilePath.replace(/^\/+/, ''); + const tmpName = staticFilePath.split(/[\/]/).pop(); + fileName = (tmpName != null && tmpName !== '') ? tmpName : staticFilePath; + } + else { + const res = await new Promise((resolve, reject) => { + uni.chooseFile({ count: 1, success: (r) => resolve(r), fail: (e) => reject(e) }); + }); + console.log(res, " at pages/akbletest.uvue:257"); + // Generator-friendly: avoid property iteration or bracket indexing. + // Serialize and regex-match common file fields (path/uri/tempFilePath/name). + try { + const s = ((): string => { try { + return JSON.stringify(res); + } + catch (e: any) { + return ''; + } })(); + const m = s.match(/"(?:path|uri|tempFilePath|temp_file_path|tempFilePath|name)"\s*:\s*"([^"]+)"/i); + if (m != null && m.length >= 2) { + const capturedCandidate: string | null = (m[1] != null ? m[1] : null); + const captured: string = capturedCandidate != null ? capturedCandidate : ''; + if (captured !== '') { + chosenPath = captured; + const toTest: string = captured; + if (!(/^[a-zA-Z]:\\|^\\\//.test(toTest) || /:\/\//.test(toTest))) { + const m2 = s.match(/"(?:path|uri|tempFilePath|temp_file_path|tempFilePath)"\s*:\s*"([^"]+)"/i); + if (m2 != null && m2.length >= 2 && m2[1] != null) { + const pathCandidate: string = m2[1] != null ? ('' + m2[1]) : ''; + if (pathCandidate !== '') + chosenPath = pathCandidate; + } + } + } + } + const nameMatch = s.match(/"name"\s*:\s*"([^"]+)"/i); + if (nameMatch != null && nameMatch.length >= 2 && nameMatch[1] != null) { + const nm: string = nameMatch[1] != null ? ('' + nameMatch[1]) : ''; + if (nm !== '') + fileName = nm; + } + } + catch (err: any) { /* ignore */ } + } + if (chosenPath == null || chosenPath == '') { + this.log('未选择文件'); + return; + } + // filePath is non-null and non-empty here + const fpStr: string = chosenPath as string; + const lastSeg = fpStr.split(/[\/]/).pop(); + const displayName = (fileName != null && fileName !== '') ? fileName : (lastSeg != null && lastSeg !== '' ? lastSeg : fpStr); + this.log('已选文件: ' + displayName + ' 路径: ' + fpStr); + const bytes = await this._readFileAsUint8Array(fpStr); + this.log('固件读取完成, 大小: ' + bytes.length); + try { + await dfuManager.startDfu(deviceId, bytes, { + useNordic: false, + onProgress: (p: number) => this.log('DFU 进度: ' + p + '%'), + onLog: (s: string) => this.log('DFU: ' + s), + controlTimeout: 30000 + } as DfuOptions); + this.log('DFU 完成'); + } + catch (e: any) { + this.log('DFU 失败: ' + getErrorMessage(e)); + } + } + catch (e: any) { + console.log('选择或读取固件失败: ' + e, " at pages/akbletest.uvue:308"); + } + }, + _readFileAsUint8Array(path: string): Promise { + return new Promise((resolve, reject) => { + try { + console.log('should readfile', " at pages/akbletest.uvue:315"); + const fsm = uni.getFileSystemManager(); + console.log(fsm, " at pages/akbletest.uvue:317"); + // Read file as ArrayBuffer directly to avoid base64 encoding issues + fsm.readFile({ + filePath: path, success: (res) => { + try { + const data = res.data as ArrayBuffer; + const arr = new Uint8Array(data); + resolve(arr); + } + catch (e: any) { + reject(e); + } + }, fail: (err) => { reject(err); } + } as ReadFileOptions); + } + catch (e: any) { + reject(e); + } + }); + }, + log(msg: string) { + const ts = new Date().toISOString(); + this.logs.unshift(`[${ts}] ${msg}`); + if (this.logs.length > 100) + this.logs.length = 100; + }, + _fmt(obj: any): string { + try { + if (obj == null) + return 'null'; + if (typeof obj == 'string') + return obj as string; + return JSON.stringify(obj); + } + catch (e: any) { + return '' + obj; + } + }, + onPresetChange(e: any) { + try { + // Some platforms emit { detail: { value: 'x' } }, others emit { value: 'x' } or just 'x'. + // Serialize and regex-extract to avoid direct property access that the UTS->Kotlin generator may emit incorrectly. + const s = ((): string => { try { + return JSON.stringify(e); + } + catch (err: any) { + return ''; + } })(); + let val: string = this.presetSelected; + // try detail.value first + const m = s.match(/"detail"\s*:\s*\{[^}]*"value"\s*:\s*"([^\"]+)"/i); + if (m != null && m.length >= 2 && m[1] != null) { + val = '' + m[1]; + } + else { + const m2 = s.match(/"value"\s*:\s*"([^\"]+)"/i); + if (m2 != null && m2.length >= 2 && m2[1] != null) { + val = '' + m2[1]; + } + } + this.presetSelected = val; + if (val == 'custom' || val == '') { + this.log('已选择预设: ' + (val == 'custom' ? '自定义' : '无')); + return; + } + this.optionalServicesInput = val; + this.log('已选择预设服务 UUID: ' + val); + } + catch (err: any) { + this.log('[error] onPresetChange: ' + getErrorMessage(err)); + } + }, + scanDevices() { + try { + this.scanning = true; + this.devices = []; + // prepare optional services: prefer free-form input, otherwise use selected preset (unless preset is 'custom' or empty) + let raw = (this.optionalServicesInput != null ? this.optionalServicesInput : '').trim(); + if (raw.length == 0 && this.presetSelected != null && this.presetSelected !== '' && this.presetSelected !== 'custom') { + raw = this.presetSelected; + } + // normalize helper: expand 16-bit UUIDs like '180F' to full 128-bit UUIDs + const normalize = (s: string): string => { + if (s == null || s.length == 0) + return ''; + const u = s.toLowerCase().replace(/^0x/, '').trim(); + const hex = u.replace(/[^0-9a-f]/g, ''); + if (/^[0-9a-f]{4}$/.test(hex)) + return `0000${hex}-0000-1000-8000-00805f9b34fb`; + return s; + }; + const optionalServices = raw.length > 0 ? raw.split(',').map((s): string => normalize(s.trim())).filter((s): boolean => s.length > 0) : []; + this.log('开始扫描... optionalServices=' + JSON.stringify(optionalServices)); + bluetoothService.scanDevices({ "protocols": ['BLE'], "optionalServices": optionalServices } as ScanDevicesOptions) + .then(() => { + this.log('scanDevices resolved'); + }) + .catch((e) => { + this.log('[error] scanDevices failed: ' + getErrorMessage(e)); + this.scanning = false; + }); + } + catch (err: any) { + this.log('[error] scanDevices thrown: ' + getErrorMessage(err)); + this.scanning = false; + } + }, + connect(deviceId: string) { + this.connecting = true; + this.log(`connect start -> ${deviceId}`); + try { + bluetoothService.connectDevice(deviceId, 'BLE', { timeout: 10000 } as BleConnectOptionsExt).then(() => { + if (!this.connectedIds.includes(deviceId)) + this.connectedIds.push(deviceId); + this.log('连接成功: ' + deviceId); + }).catch((e) => { + this.log('连接失败: ' + getErrorMessage(e!)); + }).finally(() => { + this.connecting = false; + this.log(`connect finished -> ${deviceId}`); + }); + } + catch (err: any) { + this.log('[error] connect thrown: ' + getErrorMessage(err)); + this.connecting = false; + } + }, + disconnect(deviceId: string) { + if (!this.connectedIds.includes(deviceId)) + return; + this.disconnecting = true; + this.log(`disconnect start -> ${deviceId}`); + bluetoothService.disconnectDevice(deviceId, 'BLE').then(() => { + this.log('已断开: ' + deviceId); + this.connectedIds = this.connectedIds.filter((id): boolean => id !== deviceId); + // 清理协议处理器缓存 + this.protocolHandlerMap.delete(deviceId); + }).catch((e) => { + this.log('断开失败: ' + getErrorMessage(e!)); + }).finally(() => { + this.disconnecting = false; + this.log(`disconnect finished -> ${deviceId}`); + }); + }, + showServices(deviceId: string) { + this.showingServicesFor = deviceId; + this.services = []; + this.log(`showServices start -> ${deviceId}`); + bluetoothService.getServices(deviceId).then((list) => { + this.log('showServices result -> ' + this._fmt(list)); + this.services = list as BleService[]; + this.log('服务数: ' + (list != null ? list.length : 0) + ' [' + deviceId + ']'); + }).catch((e) => { + this.log('获取服务失败: ' + getErrorMessage(e!)); + }).finally(() => { + this.log(`showServices finished -> ${deviceId}`); + }); + }, + closeServices() { + this.showingServicesFor = ''; + this.services = []; + }, + showCharacteristics(deviceId: string, serviceId: string) { + this.showingCharacteristicsFor = { deviceId, serviceId } as ShowingCharacteristicsFor; + this.characteristics = []; + bluetoothService.getCharacteristics(deviceId, serviceId).then((list) => { + this.characteristics = list as BleCharacteristic[]; + console.log('特征数: ' + (list != null ? list.length : 0) + ' [' + deviceId + ']', " at pages/akbletest.uvue:462"); + // 自动查找可用的写入和通知特征 + const writeChar = this.characteristics.find((c): boolean => c.properties.write); + const notifyChar = this.characteristics.find((c): boolean => c.properties.notify); + if (writeChar != null && notifyChar != null) { + this.protocolDeviceId = deviceId; + this.protocolServiceId = serviceId; + this.protocolWriteCharId = writeChar.uuid; + this.protocolNotifyCharId = notifyChar.uuid; + let abs = bluetoothService as BluetoothService; + this.protocolHandler = new ProtocolHandler(abs); + let handler = this.protocolHandler!; + handler?.setConnectionParameters(deviceId, serviceId, writeChar.uuid, notifyChar.uuid); + handler?.initialize()?.then(() => { + console.log("协议处理器已初始化,可进行协议测试", " at pages/akbletest.uvue:476"); + })?.catch(e => { + console.log("协议处理器初始化失败: " + getErrorMessage(e!), " at pages/akbletest.uvue:478"); + }); + } + }).catch((e) => { + console.log('获取特征失败: ' + getErrorMessage(e!), " at pages/akbletest.uvue:482"); + }); + // tracking notifying state + // this.$set(this, 'notifyingMap', this.notifyingMap || {}); + }, + closeCharacteristics() { + this.showingCharacteristicsFor = { deviceId: '', serviceId: '' } as ShowingCharacteristicsFor; + this.characteristics = []; + }, + charProps(char: BleCharacteristic): string { + const p = char.properties; + const parts = [] as string[]; + if (p.read) + parts.push('R'); + if (p.write) + parts.push('W'); + if (p.notify) + parts.push('N'); + if (p.indicate) + parts.push('I'); + return parts.join('/'); + // return [p.read ? 'R' : '', p.write ? 'W' : '', p.notify ? 'N' : '', p.indicate ? 'I' : ''].filter(Boolean).join('/') + }, + isNotifying(uuid: string): boolean { + return this.notifyingMap.has(uuid) && this.notifyingMap.get(uuid) == true; + }, + async readCharacteristic(deviceId: string, serviceId: string, charId: string): Promise { + try { + this.log(`readCharacteristic ${charId} ...`); + const buf = await bluetoothService.readCharacteristic(deviceId, serviceId, charId); + let text = ''; + try { + text = new TextDecoder().decode(new Uint8Array(buf)); + } + catch (e: any) { + text = ''; + } + const hex = Array.from(new Uint8Array(buf)).map((b): string => b.toString(16).padStart(2, '0')).join(' '); + console.log(`读取 ${charId}: text='${text}' hex='${hex}'`, " at pages/akbletest.uvue:511"); + this.log(`读取 ${charId}: text='${text}' hex='${hex}'`); + } + catch (e: any) { + this.log('读取特征失败: ' + getErrorMessage(e)); + } + }, + async writeCharacteristic(deviceId: string, serviceId: string, charId: string): Promise { + try { + const payload = new Uint8Array([0x01]); + const ok = await bluetoothService.writeCharacteristic(deviceId, serviceId, charId, payload, null); + if (ok) + this.log(`写入 ${charId} 成功`); + else + this.log(`写入 ${charId} 失败`); + } + catch (e: any) { + this.log('写入特征失败: ' + getErrorMessage(e)); + } + }, + async toggleNotify(deviceId: string, serviceId: string, charId: string): Promise { + try { + const map = this.notifyingMap; + const cur = map.get(charId) == true; + if (cur) { + // unsubscribe + await bluetoothService.unsubscribeCharacteristic(deviceId, serviceId, charId); + map.set(charId, false); + this.log(`取消订阅 ${charId}`); + } + else { + // subscribe with callback + await bluetoothService.subscribeCharacteristic(deviceId, serviceId, charId, (payload: any) => { + let data: ArrayBuffer | null = null; + try { + if (payload instanceof ArrayBuffer) { + data = payload as ArrayBuffer; + } + else if (payload != null && typeof payload == 'string') { + // some runtimes deliver base64 strings + try { + const s = atob(payload as string); + const tmp = new Uint8Array(s.length); + for (let i = 0; i < s.length; i++) { + const ch = s.charCodeAt(i); + tmp[i] = (ch == null) ? 0 : (ch & 0xff); + } + data = tmp.buffer; + } + catch (e: any) { + data = null; + } + } + else if (payload != null && (payload as UTSJSONObject).get('data') instanceof ArrayBuffer) { + data = (payload as UTSJSONObject).get('data') as ArrayBuffer; + } + const arr = data != null ? new Uint8Array(data) : new Uint8Array([]); + const hex = Array.from(arr).map((b): string => b.toString(16).padStart(2, '0')).join(' '); + this.log(`notify ${charId}: ${hex}`); + } + catch (e: any) { + this.log('notify callback error: ' + getErrorMessage(e)); + } + }); + map.set(charId, true); + this.log(`订阅 ${charId}`); + } + } + catch (e: any) { + this.log('订阅/取消订阅失败: ' + getErrorMessage(e)); + } + }, + autoConnect() { + if (this.connecting) + return; + this.connecting = true; + const toConnect = this.devices.filter((d): boolean => !this.connectedIds.includes(d.deviceId)); + if (toConnect.length == 0) { + this.log('没有可自动连接的设备'); + this.connecting = false; + return; + } + let successCount = 0; + let failCount = 0; + let finished = 0; + toConnect.forEach(device => { + bluetoothService.connectDevice(device.deviceId, 'BLE', { timeout: 10000 } as BleConnectOptionsExt).then(() => { + if (!this.connectedIds.includes(device.deviceId)) + this.connectedIds.push(device.deviceId); + this.log('自动连接成功: ' + device.deviceId); + successCount++; + // this.getOrInitProtocolHandler(device.deviceId); + }).catch((e) => { + this.log('自动连接失败: ' + device.deviceId + ' ' + getErrorMessage(e!)); + failCount++; + }).finally(() => { + finished++; + if (finished == toConnect.length) { + this.connecting = false; + this.log(`自动连接完成,成功${successCount},失败${failCount}`); + } + }); + }); + }, + autoDiscoverInterfaces(deviceId: string) { + this.log('自动发现接口中...'); + bluetoothService.getAutoBleInterfaces(deviceId) + .then((res) => { + console.log(res, " at pages/akbletest.uvue:604"); + this.log('自动发现接口成功: ' + JSON.stringify(res)); + }) + .catch((e) => { + console.log(e, " at pages/akbletest.uvue:608"); + this.log('自动发现接口失败: ' + getErrorMessage(e!)); + }); + }, + // 新增:测试电量功能 + async getOrInitProtocolHandler(deviceId: string): Promise { + let handler = this.protocolHandlerMap.get(deviceId); + if (handler == null) { + // 自动发现接口 + const res = await bluetoothService.getAutoBleInterfaces(deviceId); + handler = new ProtocolHandler(bluetoothService as BluetoothService); + handler.setConnectionParameters(deviceId, res.serviceId, res.writeCharId, res.notifyCharId); + await handler.initialize(); + this.protocolHandlerMap.set(deviceId, handler); + this.log(`协议处理器已初始化: ${deviceId}`); + } + return handler!; + }, + async getDeviceInfo(deviceId: string): Promise { + this.log('获取设备信息中...'); + try { + // First try protocol handler (if device exposes custom protocol) + try { + const handler = await this.getOrInitProtocolHandler(deviceId); + // 获取电量 + const battery = await handler.testBatteryLevel(); + this.log('协议: 电量: ' + battery); + // 获取软件/硬件版本 + const swVersion = await handler.testVersionInfo(false); + this.log('协议: 软件版本: ' + swVersion); + const hwVersion = await handler.testVersionInfo(true); + this.log('协议: 硬件版本: ' + hwVersion); + } + catch (protoErr: any) { + this.log('协议处理器不可用或初始化失败,继续使用通用 GATT 查询: ' + ((protoErr != null && protoErr instanceof Error) ? (protoErr as Error).message : this._fmt(protoErr))); + } + // Additionally, attempt to read standard services: Generic Access (0x1800), Generic Attribute (0x1801), Battery (0x180F) + const stdServices = ['1800', '1801', '180f'].map((s): string => { + const hex = s.toLowerCase().replace(/^0x/, ''); + return /^[0-9a-f]{4}$/.test(hex) ? `0000${hex}-0000-1000-8000-00805f9b34fb` : s; + }); + // fetch services once to avoid repeated GATT server queries + const services = await bluetoothService.getServices(deviceId); + for (const svc of stdServices) { + try { + this.log('读取服务: ' + svc); + // find matching service + const found = services.find((x: any): boolean => { + const uuid = (x as UTSJSONObject).get('uuid'); + return uuid != null && uuid.toString().toLowerCase() == svc.toLowerCase(); + }); + if (found == null) { + this.log('未发现服务 ' + svc + '(需重新扫描并包含 optionalServices)'); + continue; + } + const chars = await bluetoothService.getCharacteristics(deviceId, found?.uuid as string); + console.log(`服务 ${svc} 包含 ${chars.length} 个特征`, chars, " at pages/akbletest.uvue:665"); + for (const c of chars) { + try { + if (c.properties?.read == true) { + const buf = await bluetoothService.readCharacteristic(deviceId, found?.uuid as string, c.uuid); + // try to decode as utf8 then hex + let text = ''; + try { + text = new TextDecoder().decode(new Uint8Array(buf)); + } + catch (e: any) { + text = ''; + } + const hex = Array.from(new Uint8Array(buf)).map((b): string => b.toString(16).padStart(2, '0')).join(' '); + console.log(`特征 ${c.uuid} 读取: text='${text}' hex='${hex}'`, " at pages/akbletest.uvue:674"); + } + else { + console.log(`特征 ${c.uuid} 不可读`, " at pages/akbletest.uvue:676"); + } + } + catch (e: any) { + console.log(`读取特征 ${c.uuid} 失败: ${getErrorMessage(e)}`, " at pages/akbletest.uvue:679"); + } + } + } + catch (e: any) { + console.log('查询服务 ' + svc + ' 失败: ' + getErrorMessage(e), " at pages/akbletest.uvue:683"); + } + } + } + catch (e: any) { + console.log('获取设备信息失败: ' + getErrorMessage(e), " at pages/akbletest.uvue:688"); + } + } + } +}); +function getErrorMessage(e: null | string | Error): string { + if (e == null) + return ''; + if (typeof e == 'string') + return e as string; + try { + return JSON.stringify(e); + } + catch (err: any) { + return '' + (e as Error); + } +} +export default __sfc__; +function GenPagesAkbletestRender(this: InstanceType): any | null { + const _ctx = this; + const _cache = this.$.renderCache; + return _cE("scroll-view", _uM({ + direction: "vertical", + class: "container" + }), [ + _cE("view", _uM({ class: "section" }), [ + _cE("button", _uM({ + onClick: _ctx.scanDevices, + disabled: _ctx.scanning + }), _tD(_ctx.scanning ? '正在扫描...' : '扫描设备'), 9 /* TEXT, PROPS */, ["onClick", "disabled"]), + _cE("input", _uM({ + modelValue: _ctx.optionalServicesInput, + onInput: ($event: UniInputEvent) => { (_ctx.optionalServicesInput) = $event.detail.value; }, + placeholder: "可选服务 UUID, 逗号分隔", + style: _nS(_uM({ "margin-left": "12px", "width": "40%" })) + }), null, 44 /* STYLE, PROPS, NEED_HYDRATION */, ["modelValue", "onInput"]), + _cE("button", _uM({ + onClick: _ctx.autoConnect, + disabled: _ctx.connecting || _ctx.devices.length == 0, + style: _nS(_uM({ "margin-left": "12px" })) + }), _tD(_ctx.connecting ? '正在自动连接...' : '自动连接'), 13 /* TEXT, STYLE, PROPS */, ["onClick", "disabled"]), + _cE("view", null, [ + _cE("text", null, "设备计数: " + _tD(_ctx.devices.length), 1 /* TEXT */), + _cE("text", _uM({ + style: _nS(_uM({ "font-size": "12px", "color": "gray" })) + }), _tD(_ctx._fmt(_ctx.devices)), 5 /* TEXT, STYLE */) + ]), + isTrue(_ctx.devices.length) + ? _cE("view", _uM({ key: 0 }), [ + _cE("text", null, "已发现设备:"), + _cE(Fragment, null, RenderHelpers.renderList(_ctx.devices, (item, __key, __index, _cached): any => { + return _cE("view", _uM({ + key: item.deviceId, + class: "device-item" + }), [ + _cE("text", null, _tD(item.name != '' ? item.name : '未知设备') + " (" + _tD(item.deviceId) + ")", 1 /* TEXT */), + _cE("button", _uM({ + onClick: () => { _ctx.connect(item.deviceId); } + }), "连接", 8 /* PROPS */, ["onClick"]), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 0, + onClick: () => { _ctx.disconnect(item.deviceId); }, + disabled: _ctx.disconnecting + }), "断开", 8 /* PROPS */, ["onClick", "disabled"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 1, + onClick: () => { _ctx.showServices(item.deviceId); } + }), "查看服务", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 2, + onClick: () => { _ctx.autoDiscoverInterfaces(item.deviceId); } + }), "自动发现接口", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 3, + onClick: () => { _ctx.getDeviceInfo(item.deviceId); } + }), "设备信息", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 4, + onClick: () => { _ctx.startDfuFlow(item.deviceId); } + }), "DFU 升级", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(_ctx.connectedIds.includes(item.deviceId)) + ? _cE("button", _uM({ + key: 5, + onClick: () => { _ctx.startDfuFlow(item.deviceId, '/static/OmFw2509140009.zip'); } + }), "使用内置固件 DFU", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true) + ]); + }), 128 /* KEYED_FRAGMENT */) + ]) + : _cC("v-if", true) + ]), + _cE("view", _uM({ class: "section" }), [ + _cE("text", null, "日志:"), + _cE("scroll-view", _uM({ + direction: "vertical", + style: _nS(_uM({ "height": "240px" })) + }), [ + _cE(Fragment, null, RenderHelpers.renderList(_ctx.logs, (log, idx, __index, _cached): any => { + return _cE("text", _uM({ + key: idx, + style: _nS(_uM({ "font-size": "12px" })) + }), _tD(log), 5 /* TEXT, STYLE */); + }), 128 /* KEYED_FRAGMENT */) + ], 4 /* STYLE */) + ]), + isTrue(_ctx.showingServicesFor) + ? _cE("view", _uM({ key: 0 }), [ + _cE("view", _uM({ class: "section" }), [ + _cE("text", null, "设备 " + _tD(_ctx.showingServicesFor) + " 的服务:", 1 /* TEXT */), + isTrue(_ctx.services.length) + ? _cE("view", _uM({ key: 0 }), [ + _cE(Fragment, null, RenderHelpers.renderList(_ctx.services, (srv, __key, __index, _cached): any => { + return _cE("view", _uM({ + key: srv.uuid, + class: "service-item" + }), [ + _cE("text", null, _tD(srv.uuid), 1 /* TEXT */), + _cE("button", _uM({ + onClick: () => { _ctx.showCharacteristics(_ctx.showingServicesFor, srv.uuid); } + }), "查看特征", 8 /* PROPS */, ["onClick"]) + ]); + }), 128 /* KEYED_FRAGMENT */) + ]) + : _cE("view", _uM({ key: 1 }), [ + _cE("text", null, "无服务") + ]), + _cE("button", _uM({ onClick: _ctx.closeServices }), "关闭", 8 /* PROPS */, ["onClick"]) + ]) + ]) + : _cC("v-if", true), + isTrue(_ctx.showingCharacteristicsFor) + ? _cE("view", _uM({ key: 1 }), [ + _cE("view", _uM({ class: "section" }), [ + _cE("text", null, "服务 的特征:"), + isTrue(_ctx.characteristics.length) + ? _cE("view", _uM({ key: 0 }), [ + _cE(Fragment, null, RenderHelpers.renderList(_ctx.characteristics, (char, __key, __index, _cached): any => { + return _cE("view", _uM({ + key: char.uuid, + class: "char-item" + }), [ + _cE("text", null, _tD(char.uuid) + " [" + _tD(_ctx.charProps(char)) + "]", 1 /* TEXT */), + _cE("view", _uM({ + style: _nS(_uM({ "display": "flex", "flex-direction": "row", "margin-top": "6px" })) + }), [ + isTrue(char.properties?.read) + ? _cE("button", _uM({ + key: 0, + onClick: () => { _ctx.readCharacteristic(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid); } + }), "读取", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(char.properties?.write) + ? _cE("button", _uM({ + key: 1, + onClick: () => { _ctx.writeCharacteristic(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid); } + }), "写入(测试)", 8 /* PROPS */, ["onClick"]) + : _cC("v-if", true), + isTrue(char.properties?.notify) + ? _cE("button", _uM({ + key: 2, + onClick: () => { _ctx.toggleNotify(_ctx.showingCharacteristicsFor.deviceId, _ctx.showingCharacteristicsFor.serviceId, char.uuid); } + }), _tD(_ctx.isNotifying(char.uuid) ? '取消订阅' : '订阅'), 9 /* TEXT, PROPS */, ["onClick"]) + : _cC("v-if", true) + ], 4 /* STYLE */) + ]); + }), 128 /* KEYED_FRAGMENT */) + ]) + : _cE("view", _uM({ key: 1 }), [ + _cE("text", null, "无特征") + ]), + _cE("button", _uM({ onClick: _ctx.closeCharacteristics }), "关闭", 8 /* PROPS */, ["onClick"]) + ]) + ]) + : _cC("v-if", true) + ]); +} +const GenPagesAkbletestStyles = [_uM([["container", _pS(_uM([["paddingTop", 16], ["paddingRight", 16], ["paddingBottom", 16], ["paddingLeft", 16], ["flex", 1]]))], ["section", _pS(_uM([["marginBottom", 18]]))], ["device-item", _pS(_uM([["display", "flex"], ["flexDirection", "row"], ["flexWrap", "wrap"]]))], ["service-item", _pS(_uM([["marginTop", 6], ["marginRight", 0], ["marginBottom", 6], ["marginLeft", 0]]))], ["char-item", _pS(_uM([["marginTop", 6], ["marginRight", 0], ["marginBottom", 6], ["marginLeft", 0]]))]])]; +//# sourceMappingURL=akbletest.uvue.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/pages/akbletest.uvue.map b/unpackage/dist/dev/.uvue/app-android/pages/akbletest.uvue.map new file mode 100644 index 0000000..c933f6a --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/pages/akbletest.uvue.map @@ -0,0 +1 @@ +{"version":3,"sources":["pages/akbletest.uvue"],"names":[],"mappings":"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","file":"pages/akbletest.uvue","sourcesContent":["\r\n\r\n\r\n\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts new file mode 100644 index 0000000..6191ec8 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts @@ -0,0 +1,276 @@ +import type { BleDevice, BleConnectionState, BleEvent, BleEventCallback, BleEventPayload, BleScanResult, BleConnectOptionsExt, AutoBleInterfaces, BleDataPayload, SendDataPayload, BleOptions, MultiProtocolDevice, ScanHandler, BleProtocolType, ScanDevicesOptions } from '../interface.uts'; +import { ProtocolHandler } from '../protocol_handler.uts'; +import { BluetoothService } from '../interface.uts'; +import { DeviceManager } from './device_manager.uts'; +// Shape used when callers register plain objects as handlers. Using a named +// type keeps member access explicit so the code generator emits valid Kotlin +// member references instead of trying to access properties on Any. +type RawProtocolHandler = { + protocol?: BleProtocolType; + scanDevices?: (options?: ScanDevicesOptions) => Promise; + connect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; + disconnect?: (device: BleDevice) => Promise; + sendData?: (device: BleDevice, payload?: SendDataPayload, options?: BleOptions) => Promise; + autoConnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; +}; +// 设备上下文 +class DeviceContext { + device: BleDevice; + protocol: BleProtocolType; + state: BleConnectionState; + handler: ProtocolHandler; + constructor(device: BleDevice, protocol: BleProtocolType, handler: ProtocolHandler) { + this.device = device; + this.protocol = protocol; + this.state = 0; // DISCONNECTED + this.handler = handler; + } +} +const deviceMap = new Map(); // key: deviceId|protocol +// Single active protocol handler (no multi-protocol registration) +let activeProtocol: BleProtocolType = 'standard'; +let activeHandler: ProtocolHandler | null = null; +// 事件监听注册表 +const eventListeners = new Map>(); +function emit(event: BleEvent, payload: BleEventPayload) { + if (event === 'connectionStateChanged') { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:57', '[AKBLE][LOG] bluetooth_manager.uts emit connectionStateChanged', payload); + } + const listeners = eventListeners.get(event); + if (listeners != null) { + listeners.forEach(cb => { + try { + cb(payload); + } + catch (e: any) { } + }); + } +} +class ProtocolHandlerWrapper extends ProtocolHandler { + private _raw: RawProtocolHandler | null; + constructor(raw?: RawProtocolHandler) { + // pass a lightweight BluetoothService instance to satisfy generators + super(new BluetoothService()); + this._raw = (raw != null) ? raw : null; + } + override async scanDevices(options?: ScanDevicesOptions): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.scanDevices === 'function') { + await rawTyped.scanDevices!(options); + } + return; + } + override async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.connect === 'function') { + await rawTyped.connect!(device, options); + } + return; + } + override async disconnect(device: BleDevice): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.disconnect === 'function') { + await rawTyped.disconnect!(device); + } + return; + } + override async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.sendData === 'function') { + await rawTyped.sendData!(device, payload, options); + } + return; + } + override async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { + const rawTyped = this._raw; + if (rawTyped != null && typeof rawTyped.autoConnect === 'function') { + return await rawTyped.autoConnect!(device, options); + } + return { serviceId: '', writeCharId: '', notifyCharId: '' } as AutoBleInterfaces; + } +} +// Strong runtime detector for plain object handlers (no Type Predicate) +// Note: the UTS bundler doesn't support TypeScript type predicates (x is T), +// and it doesn't accept the 'unknown' type. This returns a boolean and +// callers must cast the value to RawProtocolHandler after the function +// returns true. +function isRawProtocolHandler(x: any): boolean { + if (x == null || typeof x !== 'object') + return false; + const r = x as Record; + if (typeof r['scanDevices'] === 'function') + return true; + if (typeof r['connect'] === 'function') + return true; + if (typeof r['disconnect'] === 'function') + return true; + if (typeof r['sendData'] === 'function') + return true; + if (typeof r['autoConnect'] === 'function') + return true; + if (typeof r['protocol'] === 'string') + return true; + return false; +} +export const registerProtocolHandler = (handler: any) => { + if (handler == null) + return; + // Determine protocol value defensively. Default to 'standard' when unknown. + let proto: BleProtocolType = 'standard'; + if (handler instanceof ProtocolHandler) { + try { + proto = (handler as ProtocolHandler).protocol as BleProtocolType; + } + catch (e: any) { } + activeHandler = handler as ProtocolHandler; + } + else if (isRawProtocolHandler(handler)) { + try { + proto = (handler as RawProtocolHandler).protocol as BleProtocolType; + } + catch (e: any) { } + activeHandler = new ProtocolHandlerWrapper(handler as RawProtocolHandler); + (activeHandler as ProtocolHandler).protocol = proto; + } + else { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:139', '[AKBLE] registerProtocolHandler: unsupported handler type, ignoring', handler); + return; + } + activeProtocol = proto; +}; +export const scanDevices = async (options?: ScanDevicesOptions): Promise => { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:147', '[AKBLE] start scan', options); + // Determine which protocols to run: either user-specified or all registered + // Single active handler flow + if (activeHandler == null) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:151', '[AKBLE] no active scan handler registered'); + return; + } + const handler = activeHandler as ProtocolHandler; + const scanOptions: ScanDevicesOptions = { + onDeviceFound: (device: BleDevice) => emit('deviceFound', { event: 'deviceFound', device } as BleEventPayload), + onScanFinished: () => emit('scanFinished', { event: 'scanFinished' } as BleEventPayload) + }; + try { + await handler.scanDevices(scanOptions); + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:162', '[AKBLE] scanDevices handler error', e); + } +}; +export const connectDevice = async (deviceId: string, protocol: BleProtocolType, options?: BleConnectOptionsExt): Promise => { + const handler = activeHandler; + if (handler == null) + throw new Error('No protocol handler'); + const device: BleDevice = { deviceId, name: '', rssi: 0 }; // 可扩展 + await handler.connect(device, options); + const ctx = new DeviceContext(device, protocol, handler); + ctx.state = 2; // CONNECTED + deviceMap.set(getDeviceKey(deviceId, protocol), ctx); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:175', deviceMap); + emit('connectionStateChanged', { event: 'connectionStateChanged', device, protocol, state: 2 } as BleEventPayload); +}; +export const disconnectDevice = async (deviceId: string, protocol: BleProtocolType): Promise => { + const ctx = deviceMap.get(getDeviceKey(deviceId, protocol)); + if (ctx == null || ctx.handler == null) + return; + await ctx.handler.disconnect(ctx.device); + ctx.state = 0; + emit('connectionStateChanged', { event: 'connectionStateChanged', device: ctx.device, protocol, state: 0 } as BleEventPayload); + deviceMap.delete(getDeviceKey(deviceId, protocol)); +}; +export const sendData = async (payload: SendDataPayload, options?: BleOptions): Promise => { + const ctx = deviceMap.get(getDeviceKey(payload.deviceId, payload.protocol)); + if (ctx == null) + throw new Error('Device not connected'); + // copy to local non-null variable so generator can smart-cast across awaits + const deviceCtx = ctx as DeviceContext; + if (deviceCtx.handler == null) + throw new Error('sendData not supported for this protocol'); + await deviceCtx.handler.sendData(deviceCtx.device, payload, options); + emit('dataSent', { event: 'dataSent', device: deviceCtx.device, protocol: payload.protocol, data: payload.data } as BleEventPayload); +}; +export const getConnectedDevices = (): MultiProtocolDevice[] => { + const result: MultiProtocolDevice[] = []; + deviceMap.forEach((ctx: DeviceContext) => { + const dev: MultiProtocolDevice = { + deviceId: ctx.device.deviceId, + name: ctx.device.name, + rssi: ctx.device.rssi, + protocol: ctx.protocol + }; + result.push(dev); + }); + return result; +}; +export const getConnectionState = (deviceId: string, protocol: BleProtocolType): BleConnectionState => { + const ctx = deviceMap.get(getDeviceKey(deviceId, protocol)); + if (ctx == null) + return 0; + return ctx.state; +}; +export const on = (event: BleEvent, callback: BleEventCallback) => { + if (!eventListeners.has(event)) + eventListeners.set(event, new Set()); + eventListeners.get(event)!.add(callback); +}; +export const off = (event: BleEvent, callback?: BleEventCallback) => { + if (callback == null) { + eventListeners.delete(event); + } + else { + eventListeners.get(event)?.delete(callback as BleEventCallback); + } +}; +function getDeviceKey(deviceId: string, protocol: BleProtocolType): string { + return `${deviceId}|${protocol}`; +} +export const autoConnect = async (deviceId: string, protocol: BleProtocolType, options?: BleConnectOptionsExt): Promise => { + const handler = activeHandler; + if (handler == null) + throw new Error('autoConnect not supported for this protocol'); + const device: BleDevice = { deviceId, name: '', rssi: 0 }; + // safe call - handler.autoConnect exists on ProtocolHandler + return await handler.autoConnect(device, options) as AutoBleInterfaces; +}; +// Ensure there is at least one handler registered so callers can scan/connect +// without needing to import a registry module. This creates a minimal default +// ProtocolHandler backed by a BluetoothService instance. +try { + if (activeHandler == null) { + // Create a DeviceManager-backed raw handler that delegates to native code + const _dm = DeviceManager.getInstance(); + const _raw: RawProtocolHandler = { + protocol: 'standard', + scanDevices: (options?: ScanDevicesOptions): Promise => { + try { + const scanOptions = options != null ? options : {} as ScanDevicesOptions; + _dm.startScan(scanOptions); + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:256', '[AKBLE] DeviceManager.startScan failed', e); + } + return Promise.resolve(); + }, + connect: (device, options?: BleConnectOptionsExt): Promise => { + return _dm.connectDevice(device.deviceId, options); + }, + disconnect: (device): Promise => { + return _dm.disconnectDevice(device.deviceId); + }, + autoConnect: (device, options?: any): Promise => { + // DeviceManager does not provide an autoConnect helper; return default + const result: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' }; + return Promise.resolve(result); + } + }; + const _wrapper = new ProtocolHandlerWrapper(_raw); + activeHandler = _wrapper; + activeProtocol = _raw.protocol as BleProtocolType; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:275', '[AKBLE] default protocol handler (BluetoothService-backed) registered', activeProtocol); + } +} +catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:278', '[AKBLE] failed to register default protocol handler', e); +} +//# sourceMappingURL=bluetooth_manager.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts.map new file mode 100644 index 0000000..b4dda61 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"bluetooth_manager.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts"],"names":[],"mappings":"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","sourcesContent":["import type {\r\n\tBleDevice,\r\n\tBleConnectionState,\r\n\tBleEvent,\r\n\tBleEventCallback,\r\n\tBleEventPayload,\r\n\tBleScanResult,\r\n\tBleConnectOptionsExt,\r\n\tAutoBleInterfaces,\r\n\tBleDataPayload,\r\n\tSendDataPayload,\r\n\tBleOptions,\r\n\tMultiProtocolDevice,\r\n\tScanHandler,\r\n\tBleProtocolType,\r\n\tScanDevicesOptions\r\n} from '../interface.uts';\r\nimport { ProtocolHandler } from '../protocol_handler.uts';\r\nimport { BluetoothService } from '../interface.uts';\r\nimport { DeviceManager } from './device_manager.uts';\r\n\r\n// Shape used when callers register plain objects as handlers. Using a named\r\n// type keeps member access explicit so the code generator emits valid Kotlin\r\n// member references instead of trying to access properties on Any.\r\ntype RawProtocolHandler = {\r\n\tprotocol?: BleProtocolType;\r\n\tscanDevices?: (options?: ScanDevicesOptions) => Promise;\r\n\tconnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise;\r\n\tdisconnect?: (device: BleDevice) => Promise;\r\n\tsendData?: (device: BleDevice, payload?: SendDataPayload, options?: BleOptions) => Promise;\r\n\tautoConnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise;\r\n}\r\n\r\n// 设备上下文\r\nclass DeviceContext {\r\n\tdevice : BleDevice;\r\n\tprotocol : BleProtocolType;\r\n\tstate : BleConnectionState;\r\n\thandler : ProtocolHandler;\r\n\tconstructor(device : BleDevice, protocol : BleProtocolType, handler : ProtocolHandler) {\r\n\t\tthis.device = device;\r\n\t\tthis.protocol = protocol;\r\n\t\tthis.state = 0; // DISCONNECTED\r\n\t\tthis.handler = handler;\r\n\t}\r\n}\r\n\r\nconst deviceMap = new Map(); // key: deviceId|protocol\r\n// Single active protocol handler (no multi-protocol registration)\r\nlet activeProtocol: BleProtocolType = 'standard';\r\nlet activeHandler: ProtocolHandler | null = null;\r\n// 事件监听注册表\r\nconst eventListeners = new Map>();\r\n\r\nfunction emit(event : BleEvent, payload : BleEventPayload) {\r\n\tif (event === 'connectionStateChanged') {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:57','[AKBLE][LOG] bluetooth_manager.uts emit connectionStateChanged', payload)\r\n\t}\r\n\tconst listeners = eventListeners.get(event);\r\n\tif (listeners != null) {\r\n\t\tlisteners.forEach(cb => {\r\n\t\t\ttry { cb(payload); } catch (e) { }\r\n\t\t});\r\n\t}\r\n}\r\nclass ProtocolHandlerWrapper extends ProtocolHandler {\r\n\tprivate _raw: RawProtocolHandler | null;\r\n\tconstructor(raw?: RawProtocolHandler) {\r\n\t\t// pass a lightweight BluetoothService instance to satisfy generators\r\n\t\tsuper(new BluetoothService());\r\n\t\tthis._raw = (raw != null) ? raw : null;\r\n\t}\r\n\toverride async scanDevices(options?: ScanDevicesOptions): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.scanDevices === 'function') {\r\n\t\t\tawait rawTyped.scanDevices(options);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.connect === 'function') {\r\n\t\t\tawait rawTyped.connect(device, options);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async disconnect(device: BleDevice): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.disconnect === 'function') {\r\n\t\t\tawait rawTyped.disconnect(device);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.sendData === 'function') {\r\n\t\t\tawait rawTyped.sendData(device, payload, options);\r\n\t\t}\r\n\t\treturn;\r\n\t}\r\n\toverride async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise {\r\n\t\tconst rawTyped = this._raw;\r\n\t\tif (rawTyped != null && typeof rawTyped.autoConnect === 'function') {\r\n\t\t\treturn await rawTyped.autoConnect(device, options);\r\n\t\t}\r\n\t\treturn { serviceId: '', writeCharId: '', notifyCharId: '' };\r\n\t}\r\n}\r\n\r\n// Strong runtime detector for plain object handlers (no Type Predicate)\r\n// Note: the UTS bundler doesn't support TypeScript type predicates (x is T),\r\n// and it doesn't accept the 'unknown' type. This returns a boolean and\r\n// callers must cast the value to RawProtocolHandler after the function\r\n// returns true.\r\nfunction isRawProtocolHandler(x: any): boolean {\r\n\tif (x == null || typeof x !== 'object') return false;\r\n\tconst r = x as Record;\r\n\tif (typeof r['scanDevices'] === 'function') return true;\r\n\tif (typeof r['connect'] === 'function') return true;\r\n\tif (typeof r['disconnect'] === 'function') return true;\r\n\tif (typeof r['sendData'] === 'function') return true;\r\n\tif (typeof r['autoConnect'] === 'function') return true;\r\n\tif (typeof r['protocol'] === 'string') return true;\r\n\treturn false;\r\n}\r\n\r\nexport const registerProtocolHandler = (handler : any) => {\r\n\tif (handler == null) return;\r\n\t// Determine protocol value defensively. Default to 'standard' when unknown.\r\n\tlet proto: BleProtocolType = 'standard';\r\n\tif (handler instanceof ProtocolHandler) {\r\n\t\ttry { proto = (handler as ProtocolHandler).protocol as BleProtocolType; } catch (e) { }\r\n\t\tactiveHandler = handler as ProtocolHandler;\r\n\t} else if (isRawProtocolHandler(handler)) {\r\n\t\ttry { proto = (handler as RawProtocolHandler).protocol as BleProtocolType; } catch (e) { }\r\n\t\tactiveHandler = new ProtocolHandlerWrapper(handler as RawProtocolHandler);\r\n\t\t(activeHandler as ProtocolHandler).protocol = proto;\r\n\t} else {\r\n\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:139','[AKBLE] registerProtocolHandler: unsupported handler type, ignoring', handler);\r\n\t\treturn;\r\n\t}\r\n\tactiveProtocol = proto;\r\n}\r\n\r\n\r\nexport const scanDevices = async (options ?: ScanDevicesOptions) : Promise => {\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:147','[AKBLE] start scan', options)\r\n\t// Determine which protocols to run: either user-specified or all registered\r\n\t// Single active handler flow\r\n\tif (activeHandler == null) {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:151','[AKBLE] no active scan handler registered')\r\n\t\treturn\r\n\t}\r\n\tconst handler = activeHandler as ProtocolHandler;\r\n\tconst scanOptions : ScanDevicesOptions = {\r\n\t\tonDeviceFound: (device : BleDevice) => emit('deviceFound', { event: 'deviceFound', device }),\r\n\t\tonScanFinished: () => emit('scanFinished', { event: 'scanFinished' })\r\n\t}\r\n\ttry {\r\n\t\tawait handler.scanDevices(scanOptions)\r\n\t} catch (e) {\r\n\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:162','[AKBLE] scanDevices handler error', e)\r\n\t}\r\n}\r\n\r\n\r\nexport const connectDevice = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => {\r\n\tconst handler = activeHandler;\r\n\tif (handler == null) throw new Error('No protocol handler');\r\n\tconst device : BleDevice = { deviceId, name: '', rssi: 0 }; // 可扩展\r\n\tawait handler.connect(device, options);\r\n\tconst ctx = new DeviceContext(device, protocol, handler);\r\n\tctx.state = 2; // CONNECTED\r\n\tdeviceMap.set(getDeviceKey(deviceId, protocol), ctx);\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:175',deviceMap)\r\n\temit('connectionStateChanged', { event: 'connectionStateChanged', device, protocol, state: 2 });\r\n}\r\n\r\nexport const disconnectDevice = async (deviceId : string, protocol : BleProtocolType) : Promise => {\r\n\tconst ctx = deviceMap.get(getDeviceKey(deviceId, protocol));\r\n\tif (ctx == null || ctx.handler == null) return;\r\n\tawait ctx.handler.disconnect(ctx.device);\r\n\tctx.state = 0;\r\n\temit('connectionStateChanged', { event: 'connectionStateChanged', device: ctx.device, protocol, state: 0 });\r\n\tdeviceMap.delete(getDeviceKey(deviceId, protocol));\r\n}\r\nexport const sendData = async (payload : SendDataPayload, options ?: BleOptions) : Promise => {\r\n\tconst ctx = deviceMap.get(getDeviceKey(payload.deviceId, payload.protocol));\r\n\tif (ctx == null) throw new Error('Device not connected');\r\n\t// copy to local non-null variable so generator can smart-cast across awaits\r\n\tconst deviceCtx = ctx as DeviceContext;\r\n\tif (deviceCtx.handler == null) throw new Error('sendData not supported for this protocol');\r\n\tawait deviceCtx.handler.sendData(deviceCtx.device, payload, options);\r\n\temit('dataSent', { event: 'dataSent', device: deviceCtx.device, protocol: payload.protocol, data: payload.data });\r\n}\r\n\r\nexport const getConnectedDevices = () : MultiProtocolDevice[] => {\r\n\tconst result : MultiProtocolDevice[] = [];\r\n\tdeviceMap.forEach((ctx : DeviceContext) => {\r\n\t\tconst dev : MultiProtocolDevice = {\r\n\t\t\tdeviceId: ctx.device.deviceId,\r\n\t\t\tname: ctx.device.name,\r\n\t\t\trssi: ctx.device.rssi,\r\n\t\t\tprotocol: ctx.protocol\r\n\t\t};\r\n\t\tresult.push(dev);\r\n\t});\r\n\treturn result;\r\n}\r\n\r\nexport const getConnectionState = (deviceId : string, protocol : BleProtocolType) : BleConnectionState => {\r\n\tconst ctx = deviceMap.get(getDeviceKey(deviceId, protocol));\r\n\tif (ctx == null) return 0;\r\n\treturn ctx.state;\r\n}\r\n\r\nexport const on = (event : BleEvent, callback : BleEventCallback) => {\r\n\tif (!eventListeners.has(event)) eventListeners.set(event, new Set());\r\n\teventListeners.get(event)!.add(callback);\r\n}\r\n\r\nexport const off = (event : BleEvent, callback ?: BleEventCallback) => {\r\n\tif (callback == null) {\r\n\t\teventListeners.delete(event);\r\n\t} else {\r\n\t\teventListeners.get(event)?.delete(callback as BleEventCallback);\r\n\t}\r\n}\r\n\r\nfunction getDeviceKey(deviceId : string, protocol : BleProtocolType) : string {\r\n\treturn `${deviceId}|${protocol}`;\r\n}\r\n\r\nexport const autoConnect = async (deviceId : string, protocol : BleProtocolType, options ?: BleConnectOptionsExt) : Promise => {\r\n\tconst handler = activeHandler;\r\n\tif (handler == null) throw new Error('autoConnect not supported for this protocol');\r\n\tconst device : BleDevice = { deviceId, name: '', rssi: 0 };\r\n\t// safe call - handler.autoConnect exists on ProtocolHandler\r\n\treturn await handler.autoConnect(device, options) as AutoBleInterfaces;\r\n}\r\n\r\n// Ensure there is at least one handler registered so callers can scan/connect\r\n// without needing to import a registry module. This creates a minimal default\r\n// ProtocolHandler backed by a BluetoothService instance.\r\ntry {\r\n\tif (activeHandler == null) {\r\n\t\t// Create a DeviceManager-backed raw handler that delegates to native code\r\n\t\tconst _dm = DeviceManager.getInstance();\r\n\t\tconst _raw: RawProtocolHandler = {\r\n\t\t\tprotocol: 'standard',\r\n\t\t\tscanDevices: (options?: ScanDevicesOptions) => {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst scanOptions = options != null ? options : {} as ScanDevicesOptions;\r\n\t\t\t\t\t_dm.startScan(scanOptions);\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:256','[AKBLE] DeviceManager.startScan failed', e);\r\n\t\t\t\t}\r\n\t\t\t\treturn Promise.resolve();\r\n\t\t\t},\r\n\t\t\tconnect: (device, options?: BleConnectOptionsExt) => {\r\n\t\t\t\treturn _dm.connectDevice(device.deviceId, options);\r\n\t\t\t},\r\n\t\t\tdisconnect: (device) => {\r\n\t\t\t\treturn _dm.disconnectDevice(device.deviceId);\r\n\t\t\t},\r\n\t\t\tautoConnect: (device, options?: any) => {\r\n\t\t\t\t// DeviceManager does not provide an autoConnect helper; return default\r\n\t\t\t\tconst result: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' };\r\n\t\t\t\treturn Promise.resolve(result);\r\n\t\t\t}\r\n\t\t};\r\n\t\tconst _wrapper = new ProtocolHandlerWrapper(_raw);\r\n\t\tactiveHandler = _wrapper;\r\n\t\tactiveProtocol = _raw.protocol as BleProtocolType;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:275','[AKBLE] default protocol handler (BluetoothService-backed) registered', activeProtocol);\r\n\t}\r\n} catch (e) {\r\n\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/bluetooth_manager.uts:278','[AKBLE] failed to register default protocol handler', e);\r\n}"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts new file mode 100644 index 0000000..0cead57 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts @@ -0,0 +1,301 @@ +import type { BleDevice, BleOptions, BleConnectionState, BleConnectionStateChangeCallback } from '../interface.uts'; +import type { BleConnectOptionsExt } from '../interface.uts'; +import type { ScanDevicesOptions } from '../interface.uts'; +import Context from "android.content.Context"; +import BluetoothAdapter from "android.bluetooth.BluetoothAdapter"; +import BluetoothManager from "android.bluetooth.BluetoothManager"; +import BluetoothDevice from "android.bluetooth.BluetoothDevice"; +import BluetoothGatt from "android.bluetooth.BluetoothGatt"; +import BluetoothGattCallback from "android.bluetooth.BluetoothGattCallback"; +import ScanCallback from "android.bluetooth.le.ScanCallback"; +import ScanResult from "android.bluetooth.le.ScanResult"; +import ScanSettings from "android.bluetooth.le.ScanSettings"; +import Handler from "android.os.Handler"; +import Looper from "android.os.Looper"; +import ContextCompat from "androidx.core.content.ContextCompat"; +import PackageManager from "android.content.pm.PackageManager"; +// 定义 PendingConnect 类型和实现类 +interface PendingConnect { + resolve: () => void; + reject: (err?: any) => void; // Changed to make err optional + timer?: number; +} +class PendingConnectImpl implements PendingConnect { + override resolve: () => void; + override reject: (err?: any) => void; // Changed to make err optional + override timer?: number; + constructor(resolve: () => void, reject: (err?: any) => void, timer?: number) { + this.resolve = resolve; + this.reject = reject; + this.timer = timer; + } +} +// 引入全局回调管理 +import { gattCallback } from './service_manager.uts'; +const pendingConnects = new Map(); +const STATE_DISCONNECTED = 0; +const STATE_CONNECTING = 1; +const STATE_CONNECTED = 2; +const STATE_DISCONNECTING = 3; +export class DeviceManager { + private static instance: DeviceManager | null = null; + private devices = new Map(); + private connectionStates = new Map(); + private connectionStateChangeListeners: BleConnectionStateChangeCallback[] = []; + private gattMap = new Map(); + private scanCallback: ScanCallback | null = null; + private isScanning: boolean = false; + private constructor() { } + static getInstance(): DeviceManager { + if (DeviceManager.instance == null) { + DeviceManager.instance = new DeviceManager(); + } + return DeviceManager.instance!; + } + startScan(options: ScanDevicesOptions): void { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:60', 'ak startscan now'); + const adapter = this.getBluetoothAdapter(); + if (adapter == null) { + throw new Error('未找到蓝牙适配器'); + } + if (!adapter.isEnabled) { + // 尝试请求用户开启蓝牙 + try { + adapter.enable(); // 直接调用,无需可选链和括号 + } + catch (e: any) { + // 某些设备可能不支持 enable + } + setTimeout(() => { + if (!adapter.isEnabled) { + throw new Error('蓝牙未开启'); + } + }, 1500); + throw new Error('正在开启蓝牙,请重试'); + } + const foundDevices = this.devices; // 直接用全局 devices + class MyScanCallback extends ScanCallback { + private foundDevices: Map; + private onDeviceFound: (device: BleDevice) => void; + constructor(foundDevices: Map, onDeviceFound: (device: BleDevice) => void) { + super(); + this.foundDevices = foundDevices; + this.onDeviceFound = onDeviceFound; + } + override onScanResult(callbackType: Int, result: ScanResult): void { + const device = result.getDevice(); + if (device != null) { + const deviceId = device.getAddress(); + let bleDevice = foundDevices.get(deviceId); + if (bleDevice == null) { + bleDevice = { + deviceId, + name: device.getName() ?? 'Unknown', + rssi: result.getRssi(), + lastSeen: Date.now() + } as BleDevice; + foundDevices.set(deviceId, bleDevice); + this.onDeviceFound(bleDevice); + } + else { + // 更新属性(已确保 bleDevice 非空) + bleDevice.rssi = result.getRssi(); + bleDevice.name = device.getName() ?? bleDevice.name; + bleDevice.lastSeen = Date.now(); + } + } + } + override onScanFailed(errorCode: Int): void { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:114', 'ak scan fail'); + } + } + this.scanCallback = new MyScanCallback(foundDevices, options.onDeviceFound ?? ((_device) => { })); + const scanner = adapter.getBluetoothLeScanner(); + if (scanner == null) { + throw new Error('无法获取扫描器'); + } + const scanSettings = new ScanSettings.Builder() + .setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY) + .build(); + scanner.startScan(null, scanSettings, this.scanCallback); + this.isScanning = true; + // 默认10秒后停止扫描 + new Handler(Looper.getMainLooper()).postDelayed(() => { + if (this.isScanning && this.scanCallback != null) { + scanner.stopScan(this.scanCallback); + this.isScanning = false; + // this.devices = foundDevices; + if (options.onScanFinished != null) + options.onScanFinished?.invoke(); + } + }, 40000); + } + async connectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:139', '[AKBLE] connectDevice called, deviceId:', deviceId, 'options:', options, 'connectionStates:'); + const adapter = this.getBluetoothAdapter(); + if (adapter == null) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:142', '[AKBLE] connectDevice failed: 蓝牙适配器不可用'); + throw new Error('蓝牙适配器不可用'); + } + const device = adapter.getRemoteDevice(deviceId); + if (device == null) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:147', '[AKBLE] connectDevice failed: 未找到设备', deviceId); + throw new Error('未找到设备'); + } + this.connectionStates.set(deviceId, STATE_CONNECTING); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:151', '[AKBLE] connectDevice set STATE_CONNECTING, deviceId:', deviceId, 'connectionStates:'); + this.emitConnectionStateChange(deviceId, STATE_CONNECTING); + const activity = UTSAndroid.getUniActivity(); + const timeout = options?.timeout ?? 15000; + const key = `${deviceId}|connect`; + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:158', '[AKBLE] connectDevice 超时:', deviceId); + pendingConnects.delete(key); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + this.gattMap.set(deviceId, null); + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + reject(new Error('连接超时')); + }, timeout); + // 创建一个适配器函数来匹配类型签名 + const resolveAdapter = () => { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:168', '[AKBLE] connectDevice resolveAdapter:', deviceId); + resolve(void 0); + }; + const rejectAdapter = (err?: any) => { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:172', '[AKBLE] connectDevice rejectAdapter:', deviceId, err); + reject(err); + }; + pendingConnects.set(key, new PendingConnectImpl(resolveAdapter, rejectAdapter, timer)); + try { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:178', '[AKBLE] connectGatt 调用前:', deviceId); + const gatt = device.connectGatt(activity, false, gattCallback); + this.gattMap.set(deviceId, gatt); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:181', '[AKBLE] connectGatt 调用后:', deviceId, gatt); + } + catch (e: any) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:183', '[AKBLE] connectGatt 异常:', deviceId, e); + clearTimeout(timer); + pendingConnects.delete(key); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + this.gattMap.set(deviceId, null); + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + reject(e); + } + }); + } + // 统一分发连接回调(应在 gattCallback.onConnectionStateChange 内调用) + static handleConnectionStateChange(deviceId: string, newState: number, error?: any) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:196', '[AKBLE] handleConnectionStateChange:', deviceId, 'newState:', newState, 'error:', error, 'pendingConnects:'); + const key = `${deviceId}|connect`; + const cb = pendingConnects.get(key); + if (cb != null) { + // 修复 timer 的空安全问题,使用临时变量 + const timerValue = cb.timer; + if (timerValue != null) { + clearTimeout(timerValue); + } + // 修复 error 处理 + if (newState === STATE_CONNECTED) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:208', '[AKBLE] handleConnectionStateChange: 连接成功', deviceId); + cb.resolve(); + } + else { + // 正确处理可空值 + const errorToUse = error != null ? error : new Error('连接断开'); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:213', '[AKBLE] handleConnectionStateChange: 连接失败', deviceId, errorToUse); + cb.reject(errorToUse); + } + pendingConnects.delete(key); + } + else { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:218', '[AKBLE] handleConnectionStateChange: 未找到 pendingConnects', deviceId, newState); + } + } + async disconnectDevice(deviceId: string, isActive: boolean = true): Promise { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:223', '[AKBLE] disconnectDevice called, deviceId:', deviceId, 'isActive:', isActive); + let gatt = this.gattMap.get(deviceId); + if (gatt != null) { + gatt.disconnect(); + gatt.close(); + // gatt=null; + this.gattMap.set(deviceId, null); + this.connectionStates.set(deviceId, STATE_DISCONNECTED); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:231', '[AKBLE] disconnectDevice set STATE_DISCONNECTED, deviceId:', deviceId, 'connectionStates:'); + this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED); + return; + } + else { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:235', '[AKBLE] disconnectDevice: gatt is null, deviceId:', deviceId); + return; + } + } + async reconnectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise { + let attempts = 0; + const maxAttempts = options?.maxAttempts ?? 3; + const interval = options?.interval ?? 3000; + while (attempts < maxAttempts) { + try { + await this.disconnectDevice(deviceId, false); + await this.connectDevice(deviceId, options); + return; + } + catch (e: any) { + attempts++; + if (attempts >= maxAttempts) + throw new Error('重连失败'); + // 修复 setTimeout 问题,使用旧式 Promise + setTimeout 解决 + await new Promise((resolve, _reject) => { + setTimeout(() => { + resolve(void 0); + }, interval); + }); + } + } + } + getConnectedDevices(): BleDevice[] { + // 创建一个空数组来存储结果 + const result: BleDevice[] = []; + // 遍历 devices Map 并检查连接状态 + this.devices.forEach((device, deviceId) => { + if (this.connectionStates.get(deviceId) === STATE_CONNECTED) { + result.push(device); + } + }); + return result; + } + onConnectionStateChange(listener: BleConnectionStateChangeCallback) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:277', '[AKBLE][LOG] onConnectionStateChange 注册, 当前监听数:', this.connectionStateChangeListeners.length + 1, listener); + this.connectionStateChangeListeners.push(listener); + } + protected emitConnectionStateChange(deviceId: string, state: BleConnectionState) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:282', '[AKBLE][LOG] emitConnectionStateChange', deviceId, state, 'listeners:', this.connectionStateChangeListeners.length, 'connectionStates:', this.connectionStates); + for (const listener of this.connectionStateChangeListeners) { + try { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:285', '[AKBLE][LOG] emitConnectionStateChange 调用 listener', listener); + listener(deviceId, state); + } + catch (e: any) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:288', '[AKBLE][LOG] emitConnectionStateChange listener error', e); + } + } + } + getGattInstance(deviceId: string): BluetoothGatt | null { + return this.gattMap.get(deviceId) ?? null; + } + private getBluetoothAdapter(): BluetoothAdapter | null { + const context = UTSAndroid.getAppContext(); + if (context == null) + return null; + const manager = context?.getSystemService(Context.BLUETOOTH_SERVICE) as BluetoothManager; + return manager.getAdapter(); + } + /** + * 获取指定ID的设备(如果存在) + */ + public getDevice(deviceId: string): BleDevice | null { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:308', deviceId, this.devices); + return this.devices.get(deviceId) ?? null; + } +} +//# sourceMappingURL=device_manager.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts.map new file mode 100644 index 0000000..95ae0d6 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"device_manager.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts"],"names":[],"mappings":"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","sourcesContent":["import type { BleDevice, BleOptions, BleConnectionState, BleConnectionStateChangeCallback } from '../interface.uts'\r\nimport type { BleConnectOptionsExt } from '../interface.uts'\r\nimport type { ScanDevicesOptions } from '../interface.uts';\r\nimport Context from \"android.content.Context\";\r\nimport BluetoothAdapter from \"android.bluetooth.BluetoothAdapter\";\r\nimport BluetoothManager from \"android.bluetooth.BluetoothManager\";\r\nimport BluetoothDevice from \"android.bluetooth.BluetoothDevice\";\r\nimport BluetoothGatt from \"android.bluetooth.BluetoothGatt\";\r\nimport BluetoothGattCallback from \"android.bluetooth.BluetoothGattCallback\";\r\nimport ScanCallback from \"android.bluetooth.le.ScanCallback\";\r\nimport ScanResult from \"android.bluetooth.le.ScanResult\";\r\nimport ScanSettings from \"android.bluetooth.le.ScanSettings\";\r\nimport Handler from \"android.os.Handler\";\r\nimport Looper from \"android.os.Looper\";\r\nimport ContextCompat from \"androidx.core.content.ContextCompat\";\r\nimport PackageManager from \"android.content.pm.PackageManager\";\r\n// 定义 PendingConnect 类型和实现类\r\ninterface PendingConnect {\r\n resolve: () => void;\r\n reject: (err?: any) => void; // Changed to make err optional\r\n timer?: number;\r\n}\r\n\r\nclass PendingConnectImpl implements PendingConnect {\r\n resolve: () => void;\r\n reject: (err?: any) => void; // Changed to make err optional\r\n timer?: number;\r\n \r\n constructor(resolve: () => void, reject: (err?: any) => void, timer?: number) {\r\n this.resolve = resolve;\r\n this.reject = reject;\r\n this.timer = timer;\r\n }\r\n}\r\n// 引入全局回调管理\r\nimport { gattCallback } from './service_manager.uts'\r\nconst pendingConnects = new Map();\r\n\r\nconst STATE_DISCONNECTED = 0;\r\nconst STATE_CONNECTING = 1;\r\nconst STATE_CONNECTED = 2;\r\nconst STATE_DISCONNECTING = 3;\r\n\r\nexport class DeviceManager {\r\n private static instance: DeviceManager | null = null;\r\n private devices = new Map();\r\n private connectionStates = new Map();\r\n private connectionStateChangeListeners: BleConnectionStateChangeCallback[] = []\r\n private gattMap = new Map();\r\n private scanCallback: ScanCallback | null = null\r\n private isScanning: boolean = false\r\n private constructor() {}\r\n static getInstance(): DeviceManager {\r\n if (DeviceManager.instance == null) {\r\n DeviceManager.instance = new DeviceManager();\r\n }\r\n return DeviceManager.instance!;\r\n }\r\n startScan(options: ScanDevicesOptions): void {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:60','ak startscan now')\r\n const adapter = this.getBluetoothAdapter();\r\n if (adapter == null) {\r\n throw new Error('未找到蓝牙适配器');\r\n }\r\n if (!adapter.isEnabled) {\r\n // 尝试请求用户开启蓝牙\r\n try {\r\n adapter.enable(); // 直接调用,无需可选链和括号\r\n } catch (e) {\r\n // 某些设备可能不支持 enable\r\n }\r\n setTimeout(() => {\r\n if (!adapter.isEnabled) {\r\n throw new Error('蓝牙未开启');\r\n }\r\n }, 1500);\r\n throw new Error('正在开启蓝牙,请重试');\r\n }\r\n const foundDevices = this.devices; // 直接用全局 devices\r\n \r\n class MyScanCallback extends ScanCallback {\r\n private foundDevices: Map;\r\n private onDeviceFound: (device: BleDevice) => void;\r\n constructor(foundDevices: Map, onDeviceFound: (device: BleDevice) => void) {\r\n super();\r\n this.foundDevices = foundDevices;\r\n this.onDeviceFound = onDeviceFound;\r\n }\r\n override onScanResult(callbackType: Int, result: ScanResult): void {\r\n const device = result.getDevice();\r\n if (device != null) {\r\n const deviceId = device.getAddress();\r\n let bleDevice = foundDevices.get(deviceId);\r\n if (bleDevice == null) {\r\n bleDevice = {\r\n deviceId,\r\n name: device.getName() ?? 'Unknown',\r\n rssi: result.getRssi(),\r\n lastSeen: Date.now()\r\n };\r\n foundDevices.set(deviceId, bleDevice);\r\n this.onDeviceFound(bleDevice);\r\n } else {\r\n // 更新属性(已确保 bleDevice 非空)\r\n bleDevice.rssi = result.getRssi();\r\n bleDevice.name = device.getName() ?? bleDevice.name;\r\n bleDevice.lastSeen = Date.now();\r\n }\r\n }\r\n }\r\n \r\n \r\n override onScanFailed(errorCode: Int): void {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:114','ak scan fail')\r\n }\r\n }\r\n this.scanCallback = new MyScanCallback(foundDevices, options.onDeviceFound ?? (() => {}));\r\n const scanner = adapter.getBluetoothLeScanner();\r\n if (scanner == null) {\r\n throw new Error('无法获取扫描器');\r\n }\r\n const scanSettings = new ScanSettings.Builder()\r\n .setScanMode(ScanSettings.SCAN_MODE_LOW_LATENCY)\r\n .build();\r\n scanner.startScan(null, scanSettings, this.scanCallback);\r\n this.isScanning = true;\r\n // 默认10秒后停止扫描\r\n new Handler(Looper.getMainLooper()).postDelayed(() => {\r\n if (this.isScanning && this.scanCallback != null) {\r\n scanner.stopScan(this.scanCallback);\r\n this.isScanning = false;\r\n // this.devices = foundDevices;\r\n if (options.onScanFinished != null) options.onScanFinished?.invoke();\r\n }\r\n }, 40000);\r\n }\r\n\r\n async connectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:139','[AKBLE] connectDevice called, deviceId:', deviceId, 'options:', options, 'connectionStates:')\r\n const adapter = this.getBluetoothAdapter();\r\n if (adapter == null) {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:142','[AKBLE] connectDevice failed: 蓝牙适配器不可用')\r\n throw new Error('蓝牙适配器不可用');\r\n }\r\n const device = adapter.getRemoteDevice(deviceId);\r\n if (device == null) {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:147','[AKBLE] connectDevice failed: 未找到设备', deviceId)\r\n throw new Error('未找到设备');\r\n }\r\n this.connectionStates.set(deviceId, STATE_CONNECTING);\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:151','[AKBLE] connectDevice set STATE_CONNECTING, deviceId:', deviceId, 'connectionStates:')\r\n this.emitConnectionStateChange(deviceId, STATE_CONNECTING);\r\n const activity = UTSAndroid.getUniActivity();\r\n const timeout = options?.timeout ?? 15000;\r\n const key = `${deviceId}|connect`;\r\n return new Promise((resolve, reject) => {\r\n const timer = setTimeout(() => {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:158','[AKBLE] connectDevice 超时:', deviceId)\r\n pendingConnects.delete(key);\r\n this.connectionStates.set(deviceId, STATE_DISCONNECTED);\r\n this.gattMap.set(deviceId, null);\r\n this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED);\r\n reject(new Error('连接超时'));\r\n }, timeout);\r\n \r\n // 创建一个适配器函数来匹配类型签名\r\n const resolveAdapter = () => { \r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:168','[AKBLE] connectDevice resolveAdapter:', deviceId)\r\n resolve(); \r\n };\r\n const rejectAdapter = (err?: any) => { \r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:172','[AKBLE] connectDevice rejectAdapter:', deviceId, err)\r\n reject(err); \r\n };\r\n \r\n pendingConnects.set(key, new PendingConnectImpl(resolveAdapter, rejectAdapter, timer));\r\n try {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:178','[AKBLE] connectGatt 调用前:', deviceId)\r\n const gatt = device.connectGatt(activity, false, gattCallback);\r\n this.gattMap.set(deviceId, gatt);\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:181','[AKBLE] connectGatt 调用后:', deviceId, gatt)\r\n } catch (e) {\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:183','[AKBLE] connectGatt 异常:', deviceId, e)\r\n clearTimeout(timer);\r\n pendingConnects.delete(key);\r\n this.connectionStates.set(deviceId, STATE_DISCONNECTED);\r\n this.gattMap.set(deviceId, null);\r\n this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED);\r\n reject(e);\r\n }\r\n });\r\n }\r\n\r\n // 统一分发连接回调(应在 gattCallback.onConnectionStateChange 内调用)\r\n static handleConnectionStateChange(deviceId: string, newState: number, error?: any) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:196','[AKBLE] handleConnectionStateChange:', deviceId, 'newState:', newState, 'error:', error, 'pendingConnects:')\r\n const key = `${deviceId}|connect`;\r\n const cb = pendingConnects.get(key);\r\n if (cb != null) {\r\n // 修复 timer 的空安全问题,使用临时变量\r\n const timerValue = cb.timer;\r\n if (timerValue != null) {\r\n clearTimeout(timerValue);\r\n }\r\n \r\n // 修复 error 处理\r\n if (newState === STATE_CONNECTED) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:208','[AKBLE] handleConnectionStateChange: 连接成功', deviceId)\r\n cb.resolve();\r\n } else {\r\n // 正确处理可空值\r\n const errorToUse = error != null ? error : new Error('连接断开');\r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:213','[AKBLE] handleConnectionStateChange: 连接失败', deviceId, errorToUse)\r\n cb.reject(errorToUse);\r\n }\r\n pendingConnects.delete(key);\r\n } else {\r\n __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:218','[AKBLE] handleConnectionStateChange: 未找到 pendingConnects', deviceId, newState)\r\n }\r\n }\r\n\r\n async disconnectDevice(deviceId: string, isActive: boolean = true): Promise {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:223','[AKBLE] disconnectDevice called, deviceId:', deviceId, 'isActive:', isActive)\r\n let gatt = this.gattMap.get(deviceId);\r\n if (gatt != null) {\r\n gatt.disconnect();\r\n gatt.close();\r\n // gatt=null;\r\n this.gattMap.set(deviceId, null);\r\n this.connectionStates.set(deviceId, STATE_DISCONNECTED);\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:231','[AKBLE] disconnectDevice set STATE_DISCONNECTED, deviceId:', deviceId, 'connectionStates:')\r\n this.emitConnectionStateChange(deviceId, STATE_DISCONNECTED);\r\n return;\r\n } else {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:235','[AKBLE] disconnectDevice: gatt is null, deviceId:', deviceId)\r\n return;\r\n }\r\n }\r\n\r\n async reconnectDevice(deviceId: string, options?: BleConnectOptionsExt): Promise {\r\n let attempts = 0;\r\n const maxAttempts = options?.maxAttempts ?? 3;\r\n const interval = options?.interval ?? 3000;\r\n while (attempts < maxAttempts) {\r\n try {\r\n await this.disconnectDevice(deviceId, false);\r\n await this.connectDevice(deviceId, options);\r\n return;\r\n } catch (e) {\r\n attempts++;\r\n if (attempts >= maxAttempts) throw new Error('重连失败');\r\n // 修复 setTimeout 问题,使用旧式 Promise + setTimeout 解决\r\n await new Promise((resolve) => {\r\n setTimeout(() => {\r\n resolve();\r\n }, interval);\r\n });\r\n }\r\n }\r\n }\r\n\r\n getConnectedDevices(): BleDevice[] {\r\n // 创建一个空数组来存储结果\r\n const result: BleDevice[] = [];\r\n \r\n // 遍历 devices Map 并检查连接状态\r\n this.devices.forEach((device, deviceId) => {\r\n if (this.connectionStates.get(deviceId) === STATE_CONNECTED) {\r\n result.push(device);\r\n }\r\n });\r\n \r\n return result;\r\n }\r\n\r\n onConnectionStateChange(listener: BleConnectionStateChangeCallback) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:277','[AKBLE][LOG] onConnectionStateChange 注册, 当前监听数:', this.connectionStateChangeListeners.length + 1, listener)\r\n this.connectionStateChangeListeners.push(listener)\r\n }\r\n\r\n protected emitConnectionStateChange(deviceId: string, state: BleConnectionState) {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:282','[AKBLE][LOG] emitConnectionStateChange', deviceId, state, 'listeners:', this.connectionStateChangeListeners.length, 'connectionStates:', this.connectionStates)\r\n for (const listener of this.connectionStateChangeListeners) {\r\n try { \r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:285','[AKBLE][LOG] emitConnectionStateChange 调用 listener', listener)\r\n listener(deviceId, state) \r\n } catch (e) { \r\n __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:288','[AKBLE][LOG] emitConnectionStateChange listener error', e) \r\n }\r\n }\r\n }\r\n\r\n getGattInstance(deviceId: string): BluetoothGatt | null {\r\n return this.gattMap.get(deviceId) ?? null;\r\n }\r\n\r\n private getBluetoothAdapter(): BluetoothAdapter | null {\r\n const context = UTSAndroid.getAppContext();\r\n if (context == null) return null;\r\n const manager = context?.getSystemService(Context.BLUETOOTH_SERVICE) as BluetoothManager;\r\n return manager.getAdapter();\r\n }\r\n\r\n /**\r\n * 获取指定ID的设备(如果存在)\r\n */\r\n public getDevice(deviceId: string): BleDevice | null {\r\n\t __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/device_manager.uts:308',deviceId,this.devices)\r\n return this.devices.get(deviceId) ?? null;\r\n }\r\n}\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts new file mode 100644 index 0000000..1cf6b24 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts @@ -0,0 +1,808 @@ +import { BleService } from '../interface.uts'; +import type { WriteCharacteristicOptions, DfuOptions, ControlParserResult } from '../interface.uts'; +import { DeviceManager } from './device_manager.uts'; +import { ServiceManager } from './service_manager.uts'; +import BluetoothGatt from 'android.bluetooth.BluetoothGatt'; +import BluetoothGattCharacteristic from 'android.bluetooth.BluetoothGattCharacteristic'; +import BluetoothGattDescriptor from 'android.bluetooth.BluetoothGattDescriptor'; +import UUID from 'java.util.UUID'; +// 通用 Nordic DFU UUIDs (常见设备可能使用这些;如厂商自定义请替换) +const DFU_SERVICE_UUID = '0000fe59-0000-1000-8000-00805f9b34fb'; +const DFU_CONTROL_POINT_UUID = '8ec90001-f315-4f60-9fb8-838830daea50'; +const DFU_PACKET_UUID = '8ec90002-f315-4f60-9fb8-838830daea50'; +type DfuSession = { + resolve: () => void; + reject: (err?: any) => void; + onProgress?: (p: number) => void; + onLog?: (s: string) => void; + controlParser?: (data: Uint8Array) => ControlParserResult | null; + // Nordic 专用字段 + bytesSent?: number; + totalBytes?: number; + useNordic?: boolean; + // PRN (packet receipt notification) support + prn?: number; + packetsSincePrn?: number; + prnResolve?: () => void; + prnReject?: (err?: any) => void; +}; +export class DfuManager { + // 会话表,用于把 control-point 通知路由到当前 DFU 流程 + private sessions: Map = new Map(); + // 简化:只实现最基本的 GATT-based DFU 上传逻辑,需按设备协议调整 control point 的命令/解析 + // Emit a DFU lifecycle event for a session. name should follow Nordic listener names + private _emitDfuEvent(deviceId: string, name: string, payload?: any) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:42', '[DFU][Event]', name, deviceId, payload ?? ''); + const s = this.sessions.get(deviceId); + if (s == null) + return; + if (typeof s.onLog == 'function') { + try { + const logFn = s.onLog as (msg: string) => void; + logFn(`[${name}] ${payload != null ? JSON.stringify(payload) : ''}`); + } + catch (e: any) { } + } + if (name == 'onProgress' && typeof s.onProgress == 'function' && typeof payload == 'number') { + try { + s.onProgress!(payload as number); + } + catch (e: any) { } + } + } + async startDfu(deviceId: string, firmwareBytes: Uint8Array, options?: DfuOptions): Promise { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:57', 'startDfu 0'); + const deviceManager = DeviceManager.getInstance(); + const serviceManager = ServiceManager.getInstance(); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:60', 'startDfu 1'); + const gatt: BluetoothGatt | null = deviceManager.getGattInstance(deviceId); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:62', 'startDfu 2'); + if (gatt == null) + throw new Error('Device not connected'); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:64', '[DFU] startDfu start deviceId=', deviceId, 'firmwareBytes=', firmwareBytes != null ? firmwareBytes.length : 0, 'options=', options); + try { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:66', '[DFU] requesting high connection priority for', deviceId); + gatt.requestConnectionPriority(BluetoothGatt.CONNECTION_PRIORITY_HIGH); + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:69', '[DFU] requestConnectionPriority failed', e); + } + // 发现服务并特征 + // ensure services discovered before accessing GATT; serviceManager exposes Promise-based API + await serviceManager.getServices(deviceId, null); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:75', '[DFU] services ensured for', deviceId); + const dfuService = gatt.getService(UUID.fromString(DFU_SERVICE_UUID)); + if (dfuService == null) + throw new Error('DFU service not found'); + const controlChar = dfuService.getCharacteristic(UUID.fromString(DFU_CONTROL_POINT_UUID)); + const packetChar = dfuService.getCharacteristic(UUID.fromString(DFU_PACKET_UUID)); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:80', '[DFU] dfuService=', dfuService != null ? dfuService.getUuid().toString() : null, 'controlChar=', controlChar != null ? controlChar.getUuid().toString() : null, 'packetChar=', packetChar != null ? packetChar.getUuid().toString() : null); + if (controlChar == null || packetChar == null) + throw new Error('DFU characteristics missing'); + const packetProps = packetChar.getProperties(); + const supportsWriteWithResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE) != 0; + const supportsWriteNoResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) != 0; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:85', '[DFU] packet characteristic props mask=', packetProps, 'supportsWithResponse=', supportsWriteWithResponse, 'supportsNoResponse=', supportsWriteNoResponse); + // Allow caller to request a desired MTU via options for higher throughput + const desiredMtu = (options != null && typeof options.mtu == 'number') ? options.mtu! : 247; + try { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:90', '[DFU] requesting MTU=', desiredMtu, 'for', deviceId); + await this._requestMtu(gatt, desiredMtu, 8000); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:92', '[DFU] requestMtu completed for', deviceId); + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:94', '[DFU] requestMtu failed or timed out, continue with default.', e); + } + const mtu = desiredMtu; // 假定成功或使用期望值 + const chunkSize = Math.max(20, mtu - 3); + // small helper to convert a byte (possibly signed) to a two-digit hex string + const byteToHex = (b: number): string => { + const v = (b < 0) ? (b + 256) : b; + let s = v.toString(16); + if (s.length < 2) + s = '0' + s; + return s; + }; + // Parameterize PRN window and timeout via options early so they are available + // for session logging. Defaults: prn = 12 packets, prnTimeoutMs = 10000 ms + let prnWindow = 0; + if (options != null && typeof options.prn == 'number') { + prnWindow = Math.max(0, Math.floor(options.prn!)); + } + const prnTimeoutMs = (options != null && typeof options.prnTimeoutMs == 'number') ? Math.max(1000, Math.floor(options.prnTimeoutMs!)) : 8000; + const disablePrnOnTimeout = !(options != null && options.disablePrnOnTimeout == false); + // 订阅 control point 通知并将通知路由到会话处理器 + const controlHandler = (data: Uint8Array) => { + // 交给会话处理器解析并触发事件 + try { + const hexParts: string[] = []; + for (let i = 0; i < data.length; i++) { + const v = data[i] as number; + hexParts.push(byteToHex(v)); + } + const hex = hexParts.join(' '); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:126', '[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data), 'hex=', hex); + } + catch (e: any) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:128', '[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data)); + } + this._handleControlNotification(deviceId, data); + }; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:132', '[DFU] subscribing control point for', deviceId); + await serviceManager.subscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, controlHandler); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:134', '[DFU] subscribeCharacteristic returned for', deviceId); + // 保存会话回调(用于 waitForControlEvent); 支持 Nordic 模式追踪已发送字节 + this.sessions.set(deviceId, { + resolve: () => { }, + reject: (err?: any) => { __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:139', err); }, + onProgress: null, + onLog: null, + controlParser: (data: Uint8Array): ControlParserResult | null => this._defaultControlParser(data), + bytesSent: 0, + totalBytes: firmwareBytes.length, + useNordic: options != null && options.useNordic == true, + prn: null, + packetsSincePrn: 0, + prnResolve: null, + prnReject: null + } as DfuSession); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:151', '[DFU] session created for', deviceId, 'totalBytes=', firmwareBytes.length); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:152', '[DFU] DFU session details:', { deviceId: deviceId, totalBytes: firmwareBytes.length, chunkSize: chunkSize, prnWindow: prnWindow, prnTimeoutMs: prnTimeoutMs }); + // wire options callbacks into the session (if provided) + const sessRef = this.sessions.get(deviceId); + if (sessRef != null) { + sessRef.onProgress = (options != null && typeof options.onProgress == 'function') ? options.onProgress! : null; + sessRef.onLog = (options != null && typeof options.onLog == 'function') ? options.onLog! : null; + } + // emit initial lifecycle events (Nordic-like) + this._emitDfuEvent(deviceId, 'onDeviceConnecting', null); + // 写入固件数据(非常保守的实现:逐包写入并等待短延迟) + // --- PRN setup (optional, Nordic-style flow) --- + // Parameterize PRN window and timeout via options: options.prn, options.prnTimeoutMs + // Defaults were set earlier; build PRN payload using arithmetic to avoid + // bitwise operators which don't map cleanly to generated Kotlin. + if (prnWindow > 0) { + try { + // send Set PRN to device (format: [OP_CODE_SET_PRN, prn LSB, prn MSB]) + // WARNING: Ensure your device uses the same opcode/format; change if needed. + const prnLsb = prnWindow % 256; + const prnMsb = Math.floor(prnWindow / 256) % 256; + const prnPayload = new Uint8Array([0x02, prnLsb, prnMsb]); + await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, prnPayload, null); + const sess0 = this.sessions.get(deviceId); + if (sess0 != null) { + sess0.useNordic = true; + sess0.prn = prnWindow; + sess0.packetsSincePrn = 0; + sess0.controlParser = (data: Uint8Array): ControlParserResult | null => this._nordicControlParser(data); + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:184', '[DFU] Set PRN sent (prn=', prnWindow, ') for', deviceId); + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:186', '[DFU] Set PRN failed (continuing without PRN):', e); + const sessFallback = this.sessions.get(deviceId); + if (sessFallback != null) + sessFallback.prn = 0; + } + } + else { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:191', '[DFU] PRN disabled (prnWindow=', prnWindow, ') for', deviceId); + } + // 写入固件数据(逐包写入并根据 options.waitForResponse 选择是否等待响应) + let offset = 0; + const total = firmwareBytes.length; + this._emitDfuEvent(deviceId, 'onDfuProcessStarted', null); + this._emitDfuEvent(deviceId, 'onUploadingStarted', null); + // Track outstanding write operations when using fire-and-forget mode so we can + // log and throttle if the Android stack becomes overwhelmed. + let outstandingWrites = 0; + // read tuning parameters from options in a safe, generator-friendly way + let configuredMaxOutstanding = 2; + let writeSleepMs = 0; + let writeRetryDelay = 100; + let writeMaxAttempts = 12; + let writeGiveupTimeout = 60000; + let drainOutstandingTimeout = 3000; + let failureBackoffMs = 0; + // throughput measurement + let throughputWindowBytes = 0; + let lastThroughputTime = Date.now(); + function _logThroughputIfNeeded(force?: boolean) { + try { + const now = Date.now(); + const elapsed = now - lastThroughputTime; + if (force == true || elapsed >= 1000) { + const bytes = throughputWindowBytes; + const bps = Math.floor((bytes * 1000) / Math.max(1, elapsed)); + // reset window + throughputWindowBytes = 0; + lastThroughputTime = now; + const human = `${bps} B/s`; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:225', '[DFU] throughput:', human, 'elapsedMs=', elapsed); + const s = this.sessions.get(deviceId); + if (s != null && typeof s.onLog == 'function') { + try { + s.onLog?.invoke('[DFU] throughput: ' + human); + } + catch (e: any) { } + } + } + } + catch (e: any) { } + } + function _safeErr(e?: any): any { + try { + if (e == null) + return ''; + if (typeof e == 'string') + return e as string; + try { + return JSON.stringify(e); + } + catch (e2: any) { } + try { + return (e as any).toString(); + } + catch (e3: any) { } + return ''; + } + catch (e4: any) { + return ''; + } + } + try { + if (options != null) { + try { + if (options.maxOutstanding != null) { + const parsed = Math.floor(options.maxOutstanding as number); + if (!isNaN(parsed) && parsed > 0) + configuredMaxOutstanding = parsed; + } + } + catch (e: any) { } + try { + if (options.writeSleepMs != null) { + const parsedWs = Math.floor(options.writeSleepMs as number); + if (!isNaN(parsedWs) && parsedWs >= 0) + writeSleepMs = parsedWs; + } + } + catch (e: any) { } + try { + if (options.writeRetryDelayMs != null) { + const parsedRetry = Math.floor(options.writeRetryDelayMs as number); + if (!isNaN(parsedRetry) && parsedRetry >= 0) + writeRetryDelay = parsedRetry; + } + } + catch (e: any) { } + try { + if (options.writeMaxAttempts != null) { + const parsedAttempts = Math.floor(options.writeMaxAttempts as number); + if (!isNaN(parsedAttempts) && parsedAttempts > 0) + writeMaxAttempts = parsedAttempts; + } + } + catch (e: any) { } + try { + if (options.writeGiveupTimeoutMs != null) { + const parsedGiveupTimeout = Math.floor(options.writeGiveupTimeoutMs as number); + if (!isNaN(parsedGiveupTimeout) && parsedGiveupTimeout > 0) + writeGiveupTimeout = parsedGiveupTimeout; + } + } + catch (e: any) { } + try { + if (options.drainOutstandingTimeoutMs != null) { + const parsedDrain = Math.floor(options.drainOutstandingTimeoutMs as number); + if (!isNaN(parsedDrain) && parsedDrain >= 0) + drainOutstandingTimeout = parsedDrain; + } + } + catch (e: any) { } + } + if (configuredMaxOutstanding < 1) + configuredMaxOutstanding = 1; + if (writeSleepMs < 0) + writeSleepMs = 0; + } + catch (e: any) { } + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + if (configuredMaxOutstanding > 1) + configuredMaxOutstanding = 1; + if (writeSleepMs < 15) + writeSleepMs = 15; + if (writeRetryDelay < 150) + writeRetryDelay = 150; + if (writeMaxAttempts < 40) + writeMaxAttempts = 40; + if (writeGiveupTimeout < 120000) + writeGiveupTimeout = 120000; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:291', '[DFU] packet char only supports WRITE_NO_RESPONSE; serializing writes with conservative pacing'); + } + const maxOutstandingCeiling = configuredMaxOutstanding; + let adaptiveMaxOutstanding = configuredMaxOutstanding; + const minOutstandingWindow = 1; + while (offset < total) { + const end = Math.min(offset + chunkSize, total); + const slice = firmwareBytes.subarray(offset, end); + // Decide whether to wait for response per-chunk. Honor characteristic support. + // Generator-friendly: avoid 'undefined' and use explicit boolean check. + let finalWaitForResponse = true; + if (options != null) { + try { + const maybe = options.waitForResponse; + if (maybe == true && supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + // caller requested response but characteristic cannot provide it; keep true to ensure we await the write promise. + finalWaitForResponse = true; + } + else if (maybe == false) { + finalWaitForResponse = false; + } + else if (maybe == true) { + finalWaitForResponse = true; + } + } + catch (e: any) { + finalWaitForResponse = true; + } + } + const writeOpts: WriteCharacteristicOptions = { + waitForResponse: finalWaitForResponse, + retryDelayMs: writeRetryDelay, + maxAttempts: writeMaxAttempts, + giveupTimeoutMs: writeGiveupTimeout, + forceWriteTypeNoResponse: finalWaitForResponse == false + }; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:324', '[DFU] writing packet chunk offset=', offset, 'len=', slice.length, 'waitForResponse=', finalWaitForResponse, 'outstanding=', outstandingWrites); + // Fire-and-forget path: do not await the write if waitForResponse == false. + if (finalWaitForResponse == false) { + if (failureBackoffMs > 0) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:329', '[DFU] applying failure backoff', failureBackoffMs, 'ms before next write for', deviceId); + await this._sleep(failureBackoffMs); + failureBackoffMs = Math.floor(failureBackoffMs / 2); + } + while (outstandingWrites >= adaptiveMaxOutstanding) { + await this._sleep(Math.max(1, writeSleepMs)); + } + // increment outstanding counter and kick the write without awaiting. + outstandingWrites = outstandingWrites + 1; + // fire-and-forget: start the write but don't await its Promise + const writeOffset = offset; + serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts).then((res) => { + outstandingWrites = Math.max(0, outstandingWrites - 1); + if (res == true) { + if (adaptiveMaxOutstanding < maxOutstandingCeiling) { + adaptiveMaxOutstanding = Math.min(maxOutstandingCeiling, adaptiveMaxOutstanding + 1); + } + if (failureBackoffMs > 0) + failureBackoffMs = Math.floor(failureBackoffMs / 2); + } + // log occasional completions + if ((outstandingWrites & 0x1f) == 0) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:350', '[DFU] write completion callback, outstandingWrites=', outstandingWrites, 'adaptiveWindow=', adaptiveMaxOutstanding, 'device=', deviceId); + } + // detect write failure signaled by service manager + if (res !== true) { + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)); + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:356', '[DFU] writeCharacteristic returned false for device=', deviceId, 'offset=', writeOffset, 'adaptiveWindow now=', adaptiveMaxOutstanding); + try { + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: 'write returned false' }); + } + catch (e: any) { } + } + }).catch((e) => { + outstandingWrites = Math.max(0, outstandingWrites - 1); + adaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2)); + failureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay))); + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:363', '[DFU] fire-and-forget write failed for device=', deviceId, e, 'adaptiveWindow now=', adaptiveMaxOutstanding); + try { + const errMsg = '[DFU] fire-and-forget write failed for device='; + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: errMsg }); + } + catch (e2: any) { } + }); + // account bytes for throughput + throughputWindowBytes += slice.length; + _logThroughputIfNeeded(false); + } + else { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:373', '[DFU] awaiting write for chunk offset=', offset); + try { + const writeResult = await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts); + if (writeResult !== true) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:377', '[DFU] writeCharacteristic(await) returned false at offset=', offset, 'device=', deviceId); + try { + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: 'write returned false' }); + } + catch (e: any) { } + // abort DFU by throwing + throw new Error('write failed'); + } + } + catch (e: any) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:383', '[DFU] awaiting write failed at offset=', offset, 'device=', deviceId, e); + try { + const errMsg = '[DFU] awaiting write failed '; + this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: errMsg }); + } + catch (e2: any) { } + throw e; + } + // account bytes for throughput + throughputWindowBytes += slice.length; + _logThroughputIfNeeded(false); + } + // update PRN counters and wait when window reached + const sessAfter = this.sessions.get(deviceId); + if (sessAfter != null && sessAfter.useNordic == true && typeof sessAfter.prn == 'number' && (sessAfter.prn ?? 0) > 0) { + sessAfter.packetsSincePrn = (sessAfter.packetsSincePrn ?? 0) + 1; + if ((sessAfter.packetsSincePrn ?? 0) >= (sessAfter.prn ?? 0) && (sessAfter.prn ?? 0) > 0) { + // wait for PRN (device notification) before continuing + try { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:401', '[DFU] reached PRN window, waiting for PRN for', deviceId, 'packetsSincePrn=', sessAfter.packetsSincePrn, 'prn=', sessAfter.prn); + await this._waitForPrn(deviceId, prnTimeoutMs); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:403', '[DFU] PRN received, resuming transfer for', deviceId); + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:405', '[DFU] PRN wait failed/timed out, continuing anyway for', deviceId, e); + if (disablePrnOnTimeout) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:407', '[DFU] disabling PRN waits after timeout for', deviceId); + sessAfter.prn = 0; + } + } + // reset counter + sessAfter.packetsSincePrn = 0; + } + } + offset = end; + // 如果启用 nordic 模式,统计已发送字节 + const sess = this.sessions.get(deviceId); + if (sess != null && typeof sess.bytesSent == 'number') { + sess.bytesSent = (sess.bytesSent ?? 0) + slice.length; + } + // 简单节流与日志,避免过快。默认睡眠非常短以提高吞吐量; 可在设备上调节 + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:422', '[DFU] wrote chunk for', deviceId, 'offset=', offset, '/', total, 'chunkSize=', slice.length, 'bytesSent=', sess != null ? sess.bytesSent : null, 'outstanding=', outstandingWrites); + // emit upload progress event (percent) if available + if (sess != null && typeof sess.bytesSent == 'number' && typeof sess.totalBytes == 'number') { + const p = Math.floor((sess.bytesSent! / sess.totalBytes!) * 100); + this._emitDfuEvent(deviceId, 'onProgress', p); + } + // yield to event loop and avoid starving the Android BLE stack + await this._sleep(Math.max(0, writeSleepMs)); + } + // wait for outstanding writes to drain before continuing with control commands + if (outstandingWrites > 0) { + const drainStart = Date.now(); + while (outstandingWrites > 0 && (Date.now() - drainStart) < drainOutstandingTimeout) { + await this._sleep(Math.max(0, writeSleepMs)); + } + if (outstandingWrites > 0) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:438', '[DFU] outstandingWrites remain after drain timeout, continuing with', outstandingWrites); + } + else { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:440', '[DFU] outstandingWrites drained before control phase'); + } + } + this._emitDfuEvent(deviceId, 'onUploadingCompleted', null); + // force final throughput log before activate/validate + _logThroughputIfNeeded(true); + // 发送 activate/validate 命令到 control point(需根据设备协议实现) + // 下面为占位:请替换为实际的 opcode + // 在写入前先启动控制结果等待,防止设备快速响应导致丢失通知 + const controlTimeout = 20000; + const controlResultPromise = this._waitForControlResult(deviceId, controlTimeout); + try { + // control writes: pass undefined options explicitly to satisfy the generator/typechecker + const activatePayload = new Uint8Array([0x04]); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:456', '[DFU] sending activate/validate payload=', Array.from(activatePayload)); + await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, activatePayload, null); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:458', '[DFU] activate/validate write returned for', deviceId); + } + catch (e: any) { + // 写入失败时取消控制等待,避免悬挂定时器 + try { + const sessOnWriteFail = this.sessions.get(deviceId); + if (sessOnWriteFail != null && typeof sessOnWriteFail.reject == 'function') { + sessOnWriteFail.reject(e); + } + } + catch (rejectErr: any) { } + await controlResultPromise.catch(() => { }); + try { + await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); + } + catch (e2: any) { } + this.sessions.delete(deviceId); + throw e; + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:472', '[DFU] sent control activate/validate command to control point for', deviceId); + this._emitDfuEvent(deviceId, 'onValidating', null); + // 等待 control-point 返回最终结果(成功或失败),超时可配置 + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:476', '[DFU] waiting for control result (timeout=', controlTimeout, ') for', deviceId); + try { + await controlResultPromise; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:479', '[DFU] control result resolved for', deviceId); + } + catch (err: any) { + // 清理订阅后抛出 + try { + await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); + } + catch (e: any) { } + this.sessions.delete(deviceId); + throw err; + } + // 取消订阅 + try { + await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); + } + catch (e: any) { } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:491', '[DFU] unsubscribed control point for', deviceId); + // 清理会话 + this.sessions.delete(deviceId); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:495', '[DFU] session cleared for', deviceId); + return; + } + async _requestMtu(gatt: BluetoothGatt, mtu: number, timeoutMs: number): Promise { + return new Promise((resolve, reject) => { + // 在当前项目,BluetoothGattCallback.onMtuChanged 未被封装;简单发起请求并等待短超时 + try { + const ok = gatt.requestMtu(Math.floor(mtu) as Int); + if (!ok) { + return reject(new Error('requestMtu failed')); + } + } + catch (e: any) { + return reject(e); + } + // 无 callback 监听时退回,等待一小段时间以便成功 + setTimeout(() => resolve(void 0), Math.min(2000, timeoutMs)); + }); + } + _sleep(ms: number): Promise { + return new Promise((r, _reject) => { setTimeout(() => { r(void 0); }, ms); }); + } + _waitForPrn(deviceId: string, timeoutMs: number): Promise { + const session = this.sessions.get(deviceId); + if (session == null) + return Promise.reject(new Error('no dfu session')); + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + // timeout waiting for PRN + // clear pending handlers + session.prnResolve = null; + session.prnReject = null; + reject(new Error('PRN timeout')); + }, timeoutMs); + const prnResolve = () => { + clearTimeout(timer); + resolve(void 0); + }; + const prnReject = (err?: any) => { + clearTimeout(timer); + reject(err); + }; + session.prnResolve = prnResolve; + session.prnReject = prnReject; + }); + } + // 默认 control point 解析器(非常通用的尝试解析:如果设备发送 progress byte 或成功码) + _defaultControlParser(data: Uint8Array): ControlParserResult | null { + // 假设协议:第一个字节为 opcode, 第二字节可为状态或进度 + if (data == null || data.length === 0) + return null; + const op = data[0]; + // Nordic-style response: [0x10, requestOp, resultCode] + if (op === 0x10 && data.length >= 3) { + const requestOp = data[1]; + const resultCode = data[2]; + if (resultCode === 0x01) { + return { type: 'success' } as ControlParserResult; + } + return { type: 'error', error: { requestOp: requestOp, resultCode: resultCode, raw: Array.from(data) } } as ControlParserResult; + } + // Nordic PRN notification: [0x11, LSB, MSB] -> return as progress (bytes received) + if (op === 0x11 && data.length >= 3) { + const lsb = data[1]; + const msb = data[2]; + const received = (msb << 8) | lsb; + return { type: 'progress', progress: received } as ControlParserResult; + } + // vendor-specific opcode example: 0x60 may mean 'response/progress' for some firmwares + if (op === 0x60) { + if (data.length >= 3) { + const requestOp = data[1]; + const status = data[2]; + // Known success/status codes observed in field devices + if (status === 0x00 || status === 0x01 || status === 0x0A) { + return { type: 'success' } as ControlParserResult; + } + return { type: 'error', error: { requestOp: requestOp, resultCode: status, raw: Array.from(data) } } as ControlParserResult; + } + if (data.length >= 2) { + return { type: 'progress', progress: data[1] } as ControlParserResult; + } + } + // 通用进度回退:若第二字节位于 0-100 之间,当作百分比 + if (data.length >= 2) { + const maybeProgress = data[1]; + if (maybeProgress >= 0 && maybeProgress <= 100) { + return { type: 'progress', progress: maybeProgress } as ControlParserResult; + } + } + // 若找到明显的 success opcode (示例 0x01) 或 error 0xFF + if (op === 0x01) + return { type: 'success' } as ControlParserResult; + if (op === 0xFF) + return { type: 'error', error: data } as ControlParserResult; + return { type: 'info' } as ControlParserResult; + } + // Nordic DFU control-parser(支持 Response and Packet Receipt Notification) + _nordicControlParser(data: Uint8Array): ControlParserResult | null { + // Nordic opcodes (简化): + // - 0x10 : Response (opcode, requestOp, resultCode) + // - 0x11 : Packet Receipt Notification (opcode, value LSB, value MSB) + if (data == null || data.length == 0) + return null; + const op = data[0]; + if (op == 0x11 && data.length >= 3) { + // packet receipt notif: bytes received (little endian) + const lsb = data[1]; + const msb = data[2]; + const received = (msb << 8) | lsb; + // Return received bytes as progress value; parser does not resolve device-specific session here. + return { type: 'progress', progress: received } as ControlParserResult; + } + // Nordic vendor-specific progress/response opcode (example 0x60) + if (op == 0x60) { + if (data.length >= 3) { + const requestOp = data[1]; + const status = data[2]; + if (status == 0x00 || status == 0x01 || status == 0x0A) { + return { type: 'success' } as ControlParserResult; + } + return { type: 'error', error: { requestOp, resultCode: status, raw: Array.from(data) } } as ControlParserResult; + } + if (data.length >= 2) { + return { type: 'progress', progress: data[1] } as ControlParserResult; + } + } + // Response: check result code for success (0x01 may indicate success in some stacks) + if (op == 0x10 && data.length >= 3) { + const requestOp = data[1]; + const resultCode = data[2]; + // Nordic resultCode 0x01 = SUCCESS typically + if (resultCode == 0x01) + return { type: 'success' } as ControlParserResult; + else + return { type: 'error', error: { requestOp, resultCode } } as ControlParserResult; + } + return null; + } + _handleControlNotification(deviceId: string, data: Uint8Array) { + const session = this.sessions.get(deviceId); + if (session == null) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:636', '[DFU] control notification received but no session for', deviceId, 'data=', Array.from(data)); + return; + } + try { + // human readable opcode mapping + let opcodeName = 'unknown'; + switch (data[0]) { + case 0x10: + opcodeName = 'Response'; + break; + case 0x11: + opcodeName = 'PRN'; + break; + case 0x60: + opcodeName = 'VendorProgress'; + break; + case 0x01: + opcodeName = 'SuccessOpcode'; + break; + case 0xFF: + opcodeName = 'ErrorOpcode'; + break; + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:649', '[DFU] _handleControlNotification deviceId=', deviceId, 'opcode=0x' + data[0].toString(16), 'name=', opcodeName, 'raw=', Array.from(data)); + const parsed = session.controlParser != null ? session.controlParser!(data) : null; + if (session.onLog != null) + session.onLog!('DFU control notify: ' + Array.from(data).join(',')); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:652', '[DFU] parsed control result=', parsed); + if (parsed == null) + return; + if (parsed.type == 'progress' && parsed.progress != null) { + // 如果在 nordic 模式 parsed.progress 可能是已接收字节数,则转换为百分比 + if (session.useNordic == true && session.totalBytes != null && session.totalBytes! > 0) { + const percent = Math.floor((parsed.progress! / session.totalBytes!) * 100); + session.onProgress?.(percent); + // If we have written all bytes locally, log that event + if (session.bytesSent != null && session.totalBytes != null && session.bytesSent! >= session.totalBytes!) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:661', '[DFU] all bytes written locally for', deviceId, 'bytesSent=', session.bytesSent, 'total=', session.totalBytes); + // emit uploading completed once + this._emitDfuEvent(deviceId, 'onUploadingCompleted', null); + } + // If a PRN wait is pending, resolve it (PRN indicates device received packets) + if (typeof session.prnResolve == 'function') { + try { + session.prnResolve!(); + } + catch (e: any) { } + session.prnResolve = null; + session.prnReject = null; + session.packetsSincePrn = 0; + } + } + else { + const progress = parsed.progress!; + if (progress != null) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:675', '[DFU] progress for', deviceId, 'progress=', progress); + session.onProgress?.(progress); + // also resolve PRN if was waiting (in case device reports numeric progress) + if (typeof session.prnResolve == 'function') { + try { + session.prnResolve!(); + } + catch (e: any) { } + session.prnResolve = null; + session.prnReject = null; + session.packetsSincePrn = 0; + } + } + } + } + else if (parsed.type == 'success') { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:687', '[DFU] parsed success for', deviceId, 'resolving session'); + session.resolve(); + // Log final device-acknowledged success + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:690', '[DFU] device reported DFU success for', deviceId); + this._emitDfuEvent(deviceId, 'onDfuCompleted', null); + } + else if (parsed.type == 'error') { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:693', '[DFU] parsed error for', deviceId, parsed.error); + session.reject(parsed.error ?? new Error('DFU device error')); + this._emitDfuEvent(deviceId, 'onError', parsed.error ?? {}); + } + else { + // info - just log + } + } + catch (e: any) { + session.onLog?.('control parse error: ' + e); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:701', '[DFU] control parse exception for', deviceId, e); + } + } + _waitForControlResult(deviceId: string, timeoutMs: number): Promise { + const session = this.sessions.get(deviceId); + if (session == null) + return Promise.reject(new Error('no dfu session')); + return new Promise((resolve, reject) => { + // wrap resolve/reject to clear timer + const timer = setTimeout(() => { + // 超时 + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:712', '[DFU] _waitForControlResult timeout for', deviceId); + reject(new Error('DFU control timeout')); + }, timeoutMs); + const origResolve = () => { + clearTimeout(timer); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:717', '[DFU] _waitForControlResult resolved for', deviceId); + resolve(void 0); + }; + const origReject = (err?: any) => { + clearTimeout(timer); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:722', '[DFU] _waitForControlResult rejected for', deviceId, 'err=', err); + reject(err); + }; + // replace session handlers temporarily (guard nullable) + if (session != null) { + session.resolve = origResolve; + session.reject = origReject; + } + }); + } +} +export const dfuManager = new DfuManager(); +//# sourceMappingURL=dfu_manager.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts.map new file mode 100644 index 0000000..7ff761c --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"dfu_manager.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts"],"names":[],"mappings":"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","sourcesContent":["import { BleService } from '../interface.uts'\r\nimport type { WriteCharacteristicOptions, DfuOptions, ControlParserResult } from '../interface.uts'\r\nimport { DeviceManager } from './device_manager.uts'\r\nimport { ServiceManager } from './service_manager.uts'\r\nimport BluetoothGatt from 'android.bluetooth.BluetoothGatt'\r\nimport BluetoothGattCharacteristic from 'android.bluetooth.BluetoothGattCharacteristic'\r\nimport BluetoothGattDescriptor from 'android.bluetooth.BluetoothGattDescriptor'\r\nimport UUID from 'java.util.UUID'\r\n\r\n// 通用 Nordic DFU UUIDs (常见设备可能使用这些;如厂商自定义请替换)\r\nconst DFU_SERVICE_UUID = '0000fe59-0000-1000-8000-00805f9b34fb'\r\nconst DFU_CONTROL_POINT_UUID = '8ec90001-f315-4f60-9fb8-838830daea50'\r\nconst DFU_PACKET_UUID = '8ec90002-f315-4f60-9fb8-838830daea50'\r\n\r\ntype DfuSession = {\r\n\tresolve : () => void;\r\n\treject : (err ?: any) => void;\r\n\tonProgress ?: (p : number) => void;\r\n\tonLog ?: (s : string) => void;\r\n\tcontrolParser ?: (data : Uint8Array) => ControlParserResult | null;\r\n\t// Nordic 专用字段\r\n\tbytesSent ?: number;\r\n\ttotalBytes ?: number;\r\n\tuseNordic ?: boolean;\r\n\t// PRN (packet receipt notification) support\r\n\tprn ?: number;\r\n\tpacketsSincePrn ?: number;\r\n\tprnResolve ?: () => void;\r\n\tprnReject ?: (err ?: any) => void;\r\n}\r\n\r\n\r\n\r\nexport class DfuManager {\r\n\t// 会话表,用于把 control-point 通知路由到当前 DFU 流程\r\n\tprivate sessions : Map = new Map();\r\n\r\n\t// 简化:只实现最基本的 GATT-based DFU 上传逻辑,需按设备协议调整 control point 的命令/解析\r\n\r\n\t// Emit a DFU lifecycle event for a session. name should follow Nordic listener names\r\n\tprivate _emitDfuEvent(deviceId : string, name : string, payload ?: any) {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:42','[DFU][Event]', name, deviceId, payload ?? '');\r\n\t\tconst s = this.sessions.get(deviceId);\r\n\t\tif (s == null) return;\r\n\t\tif (typeof s.onLog == 'function') {\r\n\t\t\ttry {\r\n\t\t\t\tconst logFn = s.onLog as (msg : string) => void;\r\n\t\t\t\tlogFn(`[${name}] ${payload != null ? JSON.stringify(payload) : ''}`);\r\n\t\t\t} catch (e) { }\r\n\t\t}\r\n\t\tif (name == 'onProgress' && typeof s.onProgress == 'function' && typeof payload == 'number') {\r\n\t\t\ttry { s.onProgress(payload); } catch (e) { }\r\n\t\t}\r\n\t}\r\n\r\n\tasync startDfu(deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) : Promise {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:57','startDfu 0')\r\n\t\tconst deviceManager = DeviceManager.getInstance();\r\n\t\tconst serviceManager = ServiceManager.getInstance();\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:60','startDfu 1')\r\n\t\tconst gatt : BluetoothGatt | null = deviceManager.getGattInstance(deviceId);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:62','startDfu 2')\r\n\t\tif (gatt == null) throw new Error('Device not connected');\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:64','[DFU] startDfu start deviceId=', deviceId, 'firmwareBytes=', firmwareBytes != null ? firmwareBytes.length : 0, 'options=', options);\r\n\t\ttry {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:66','[DFU] requesting high connection priority for', deviceId);\r\n\t\t\tgatt.requestConnectionPriority(BluetoothGatt.CONNECTION_PRIORITY_HIGH);\r\n\t\t} catch (e) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:69','[DFU] requestConnectionPriority failed', e);\r\n\t\t}\r\n\r\n\t\t// 发现服务并特征\r\n\t\t// ensure services discovered before accessing GATT; serviceManager exposes Promise-based API\r\n\t\tawait serviceManager.getServices(deviceId, null);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:75','[DFU] services ensured for', deviceId);\r\n\t\tconst dfuService = gatt.getService(UUID.fromString(DFU_SERVICE_UUID));\r\n\t\tif (dfuService == null) throw new Error('DFU service not found');\r\n\t\tconst controlChar = dfuService.getCharacteristic(UUID.fromString(DFU_CONTROL_POINT_UUID));\r\n\t\tconst packetChar = dfuService.getCharacteristic(UUID.fromString(DFU_PACKET_UUID));\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:80','[DFU] dfuService=', dfuService != null ? dfuService.getUuid().toString() : null, 'controlChar=', controlChar != null ? controlChar.getUuid().toString() : null, 'packetChar=', packetChar != null ? packetChar.getUuid().toString() : null);\r\n\t\tif (controlChar == null || packetChar == null) throw new Error('DFU characteristics missing');\r\n\t\tconst packetProps = packetChar.getProperties();\r\n\t\tconst supportsWriteWithResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE) != 0;\r\n\t\tconst supportsWriteNoResponse = (packetProps & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) != 0;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:85','[DFU] packet characteristic props mask=', packetProps, 'supportsWithResponse=', supportsWriteWithResponse, 'supportsNoResponse=', supportsWriteNoResponse);\r\n\r\n\t// Allow caller to request a desired MTU via options for higher throughput\r\n\tconst desiredMtu = (options != null && typeof options.mtu == 'number') ? options.mtu : 247;\r\n\t\ttry {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:90','[DFU] requesting MTU=', desiredMtu, 'for', deviceId);\r\n\t\t\tawait this._requestMtu(gatt, desiredMtu, 8000);\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:92','[DFU] requestMtu completed for', deviceId);\r\n\t\t} catch (e) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:94','[DFU] requestMtu failed or timed out, continue with default.', e);\r\n\t\t}\r\n\t\tconst mtu = desiredMtu; // 假定成功或使用期望值\r\n\tconst chunkSize = Math.max(20, mtu - 3);\r\n\r\n\t\t// small helper to convert a byte (possibly signed) to a two-digit hex string\r\n\t\tconst byteToHex = (b : number) => {\r\n\t\t\tconst v = (b < 0) ? (b + 256) : b;\r\n\t\t\tlet s = v.toString(16);\r\n\t\t\tif (s.length < 2) s = '0' + s;\r\n\t\t\treturn s;\r\n\t\t};\r\n\r\n\t// Parameterize PRN window and timeout via options early so they are available\r\n\t\t// for session logging. Defaults: prn = 12 packets, prnTimeoutMs = 10000 ms\r\n\t\tlet prnWindow = 0;\r\n\t\tif (options != null && typeof options.prn == 'number') {\r\n\t\t\tprnWindow = Math.max(0, Math.floor(options.prn));\r\n\t\t}\r\n\t\tconst prnTimeoutMs = (options != null && typeof options.prnTimeoutMs == 'number') ? Math.max(1000, Math.floor(options.prnTimeoutMs)) : 8000;\r\n\t\tconst disablePrnOnTimeout = !(options != null && options.disablePrnOnTimeout == false);\r\n\r\n\t\t// 订阅 control point 通知并将通知路由到会话处理器\r\n\t\tconst controlHandler = (data : Uint8Array) => {\r\n\t\t\t// 交给会话处理器解析并触发事件\r\n\t\t\ttry {\r\n\t\t\t\tconst hexParts: string[] = [];\r\n\t\t\t\tfor (let i = 0; i < data.length; i++) {\r\n\t\t\t\t\tconst v = data[i] as number;\r\n\t\t\t\t\thexParts.push(byteToHex(v));\r\n\t\t\t\t}\r\n\t\t\t\tconst hex = hexParts.join(' ');\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:126','[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data), 'hex=', hex);\r\n\t\t\t} catch (e) {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:128','[DFU] control notification callback invoked for', deviceId, 'raw=', Array.from(data));\r\n\t\t\t}\r\n\t\t\tthis._handleControlNotification(deviceId, data);\r\n\t\t};\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:132','[DFU] subscribing control point for', deviceId);\r\n\t\tawait serviceManager.subscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, controlHandler);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:134','[DFU] subscribeCharacteristic returned for', deviceId);\r\n\r\n\t\t// 保存会话回调(用于 waitForControlEvent); 支持 Nordic 模式追踪已发送字节\r\n\t\tthis.sessions.set(deviceId, {\r\n\t\t\tresolve: () => { },\r\n\t\t\treject: (err ?: any) => {__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:139',err) },\r\n\t\t\tonProgress: null,\r\n\t\t\tonLog: null,\r\n\t\t\tcontrolParser: (data : Uint8Array) => this._defaultControlParser(data),\r\n\t\t\tbytesSent: 0,\r\n\t\t\ttotalBytes: firmwareBytes.length,\r\n\t\t\tuseNordic: options != null && options.useNordic == true,\r\n\t\t\tprn: null,\r\n\t\t\tpacketsSincePrn: 0,\r\n\t\t\tprnResolve: null,\r\n\t\t\tprnReject: null\r\n\t\t});\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:151','[DFU] session created for', deviceId, 'totalBytes=', firmwareBytes.length);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:152','[DFU] DFU session details:', { deviceId: deviceId, totalBytes: firmwareBytes.length, chunkSize: chunkSize, prnWindow: prnWindow, prnTimeoutMs: prnTimeoutMs });\r\n\r\n\t\t// wire options callbacks into the session (if provided)\r\n\t\tconst sessRef = this.sessions.get(deviceId);\r\n\t\tif (sessRef != null) {\r\n\t\t\tsessRef.onProgress = (options != null && typeof options.onProgress == 'function') ? options.onProgress : null;\r\n\t\t\tsessRef.onLog = (options != null && typeof options.onLog == 'function') ? options.onLog : null;\r\n\t\t}\r\n\r\n\t\t// emit initial lifecycle events (Nordic-like)\r\n\tthis._emitDfuEvent(deviceId, 'onDeviceConnecting', null);\r\n\r\n\t\t// 写入固件数据(非常保守的实现:逐包写入并等待短延迟)\r\n\t\t// --- PRN setup (optional, Nordic-style flow) ---\r\n\t\t// Parameterize PRN window and timeout via options: options.prn, options.prnTimeoutMs\r\n\t\t// Defaults were set earlier; build PRN payload using arithmetic to avoid\r\n\t\t// bitwise operators which don't map cleanly to generated Kotlin.\r\n\t\tif (prnWindow > 0) {\r\n\t\t\ttry {\r\n\t\t\t\t// send Set PRN to device (format: [OP_CODE_SET_PRN, prn LSB, prn MSB])\r\n\t\t\t\t// WARNING: Ensure your device uses the same opcode/format; change if needed.\r\n\t\t\t\tconst prnLsb = prnWindow % 256;\r\n\t\t\t\tconst prnMsb = Math.floor(prnWindow / 256) % 256;\r\n\t\t\t\tconst prnPayload = new Uint8Array([0x02, prnLsb, prnMsb]);\r\n\t\t\t\tawait serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, prnPayload, null);\r\n\t\t\t\tconst sess0 = this.sessions.get(deviceId);\r\n\t\t\t\tif (sess0 != null) {\r\n\t\t\t\t\tsess0.useNordic = true;\r\n\t\t\t\t\tsess0.prn = prnWindow;\r\n\t\t\t\t\tsess0.packetsSincePrn = 0;\r\n\t\t\t\t\tsess0.controlParser = (data : Uint8Array) => this._nordicControlParser(data);\r\n\t\t\t\t}\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:184','[DFU] Set PRN sent (prn=', prnWindow, ') for', deviceId);\r\n\t\t\t} catch (e) {\r\n\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:186','[DFU] Set PRN failed (continuing without PRN):', e);\r\n\t\t\t\tconst sessFallback = this.sessions.get(deviceId);\r\n\t\t\t\tif (sessFallback != null) sessFallback.prn = 0;\r\n\t\t\t}\r\n\t\t} else {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:191','[DFU] PRN disabled (prnWindow=', prnWindow, ') for', deviceId);\r\n\t\t}\r\n\r\n\t// 写入固件数据(逐包写入并根据 options.waitForResponse 选择是否等待响应)\r\n\t\tlet offset = 0;\r\n\t\tconst total = firmwareBytes.length;\r\n\tthis._emitDfuEvent(deviceId, 'onDfuProcessStarted', null);\r\n\tthis._emitDfuEvent(deviceId, 'onUploadingStarted', null);\r\n\t\t// Track outstanding write operations when using fire-and-forget mode so we can\r\n\t\t// log and throttle if the Android stack becomes overwhelmed.\r\n\t\tlet outstandingWrites = 0;\r\n\t\t// read tuning parameters from options in a safe, generator-friendly way\r\n\t\tlet configuredMaxOutstanding = 2;\r\n\t\tlet writeSleepMs = 0;\r\n\t\tlet writeRetryDelay = 100;\r\n\t\tlet writeMaxAttempts = 12;\r\n\t\tlet writeGiveupTimeout = 60000;\r\n\t\tlet drainOutstandingTimeout = 3000;\r\n\t\tlet failureBackoffMs = 0;\r\n\r\n\t\t// throughput measurement\r\n\t\tlet throughputWindowBytes = 0;\r\n\t\tlet lastThroughputTime = Date.now();\r\n\t\tfunction _logThroughputIfNeeded(force ?: boolean) {\r\n\t\t\ttry {\r\n\t\t\t\tconst now = Date.now();\r\n\t\t\t\tconst elapsed = now - lastThroughputTime;\r\n\t\t\t\tif (force == true || elapsed >= 1000) {\r\n\t\t\t\t\tconst bytes = throughputWindowBytes;\r\n\t\t\t\t\tconst bps = Math.floor((bytes * 1000) / Math.max(1, elapsed));\r\n\t\t\t\t\t// reset window\r\n\t\t\t\t\tthroughputWindowBytes = 0;\r\n\t\t\t\t\tlastThroughputTime = now;\r\n\t\t\t\t\tconst human = `${bps} B/s`;\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:225','[DFU] throughput:', human, 'elapsedMs=', elapsed);\r\n\t\t\t\t\tconst s = this.sessions.get(deviceId);\r\n\t\t\t\t\tif (s != null && typeof s.onLog == 'function') {\r\n\t\t\t\t\t\ttry { s.onLog?.invoke('[DFU] throughput: ' + human); } catch (e) { }\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t}\r\n\r\n\t\tfunction _safeErr(e ?: any) {\r\n\t\t\ttry {\r\n\t\t\t\tif (e == null) return '';\r\n\t\t\t\tif (typeof e == 'string') return e;\r\n\t\t\t\ttry { return JSON.stringify(e); } catch (e2) { }\r\n\t\t\t\ttry { return (e as any).toString(); } catch (e3) { }\r\n\t\t\t\treturn '';\r\n\t\t\t} catch (e4) { return ''; }\r\n\t\t}\r\n\t\ttry {\r\n\t\t\tif (options != null) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.maxOutstanding != null) {\r\n\t\t\t\t\t\tconst parsed = Math.floor(options.maxOutstanding as number);\r\n\t\t\t\t\t\tif (!isNaN(parsed) && parsed > 0) configuredMaxOutstanding = parsed;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeSleepMs != null) {\r\n\t\t\t\t\t\tconst parsedWs = Math.floor(options.writeSleepMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedWs) && parsedWs >= 0) writeSleepMs = parsedWs;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeRetryDelayMs != null) {\r\n\t\t\t\t\t\tconst parsedRetry = Math.floor(options.writeRetryDelayMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedRetry) && parsedRetry >= 0) writeRetryDelay = parsedRetry;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeMaxAttempts != null) {\r\n\t\t\t\t\t\tconst parsedAttempts = Math.floor(options.writeMaxAttempts as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedAttempts) && parsedAttempts > 0) writeMaxAttempts = parsedAttempts;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.writeGiveupTimeoutMs != null) {\r\n\t\t\t\t\t\tconst parsedGiveupTimeout = Math.floor(options.writeGiveupTimeoutMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedGiveupTimeout) && parsedGiveupTimeout > 0) writeGiveupTimeout = parsedGiveupTimeout;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (options.drainOutstandingTimeoutMs != null) {\r\n\t\t\t\t\t\tconst parsedDrain = Math.floor(options.drainOutstandingTimeoutMs as number);\r\n\t\t\t\t\t\tif (!isNaN(parsedDrain) && parsedDrain >= 0) drainOutstandingTimeout = parsedDrain;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { }\r\n\t\t\t}\r\n\t\t\tif (configuredMaxOutstanding < 1) configuredMaxOutstanding = 1;\r\n\t\t\tif (writeSleepMs < 0) writeSleepMs = 0;\r\n\t\t} catch (e) { }\r\n\t\t\tif (supportsWriteWithResponse == false && supportsWriteNoResponse == true) {\r\n\t\t\t\tif (configuredMaxOutstanding > 1) configuredMaxOutstanding = 1;\r\n\t\t\t\tif (writeSleepMs < 15) writeSleepMs = 15;\r\n\t\t\t\tif (writeRetryDelay < 150) writeRetryDelay = 150;\r\n\t\t\t\tif (writeMaxAttempts < 40) writeMaxAttempts = 40;\r\n\t\t\t\tif (writeGiveupTimeout < 120000) writeGiveupTimeout = 120000;\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:291','[DFU] packet char only supports WRITE_NO_RESPONSE; serializing writes with conservative pacing');\r\n\t\t\t}\r\n\t\tconst maxOutstandingCeiling = configuredMaxOutstanding;\r\n\t\tlet adaptiveMaxOutstanding = configuredMaxOutstanding;\r\n\t\tconst minOutstandingWindow = 1;\r\n\r\n\t\twhile (offset < total) {\r\n\t\t\tconst end = Math.min(offset + chunkSize, total);\r\n\t\t\tconst slice = firmwareBytes.subarray(offset, end);\r\n\t\t\t// Decide whether to wait for response per-chunk. Honor characteristic support.\r\n\t\t\t// Generator-friendly: avoid 'undefined' and use explicit boolean check.\r\n\t\t\tlet finalWaitForResponse = true;\r\n\t\t\tif (options != null) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst maybe = options.waitForResponse;\r\n\t\t\t\t\tif (maybe == true && supportsWriteWithResponse == false && supportsWriteNoResponse == true) {\r\n\t\t\t\t\t\t// caller requested response but characteristic cannot provide it; keep true to ensure we await the write promise.\r\n\t\t\t\t\t\tfinalWaitForResponse = true;\r\n\t\t\t\t\t} else if (maybe == false) {\r\n\t\t\t\t\t\tfinalWaitForResponse = false;\r\n\t\t\t\t\t} else if (maybe == true) {\r\n\t\t\t\t\t\tfinalWaitForResponse = true;\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) { finalWaitForResponse = true; }\r\n\t\t\t}\r\n\r\n\t\t\tconst writeOpts: WriteCharacteristicOptions = {\r\n\t\t\t\twaitForResponse: finalWaitForResponse,\r\n\t\t\t\tretryDelayMs: writeRetryDelay,\r\n\t\t\t\tmaxAttempts: writeMaxAttempts,\r\n\t\t\t\tgiveupTimeoutMs: writeGiveupTimeout,\r\n\t\t\t\tforceWriteTypeNoResponse: finalWaitForResponse == false\r\n\t\t\t};\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:324','[DFU] writing packet chunk offset=', offset, 'len=', slice.length, 'waitForResponse=', finalWaitForResponse, 'outstanding=', outstandingWrites);\r\n\r\n\t\t\t// Fire-and-forget path: do not await the write if waitForResponse == false.\r\n\t\t\tif (finalWaitForResponse == false) {\r\n\t\t\t\tif (failureBackoffMs > 0) {\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:329','[DFU] applying failure backoff', failureBackoffMs, 'ms before next write for', deviceId);\r\n\t\t\t\t\tawait this._sleep(failureBackoffMs);\r\n\t\t\t\t\tfailureBackoffMs = Math.floor(failureBackoffMs / 2);\r\n\t\t\t\t}\r\n\t\t\t\twhile (outstandingWrites >= adaptiveMaxOutstanding) {\r\n\t\t\t\t\tawait this._sleep(Math.max(1, writeSleepMs));\r\n\t\t\t\t}\r\n\t\t\t\t// increment outstanding counter and kick the write without awaiting.\r\n\t\t\t\toutstandingWrites = outstandingWrites + 1;\r\n\t\t\t\t// fire-and-forget: start the write but don't await its Promise\r\n\t\t\t\tconst writeOffset = offset;\r\n\t\t\t\tserviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts).then((res) => {\r\n\t\t\t\t\toutstandingWrites = Math.max(0, outstandingWrites - 1);\r\n\t\t\t\t\tif (res == true) {\r\n\t\t\t\t\t\tif (adaptiveMaxOutstanding < maxOutstandingCeiling) {\r\n\t\t\t\t\t\t\tadaptiveMaxOutstanding = Math.min(maxOutstandingCeiling, adaptiveMaxOutstanding + 1);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (failureBackoffMs > 0) failureBackoffMs = Math.floor(failureBackoffMs / 2);\r\n\t\t\t\t\t}\r\n\t\t\t\t\t// log occasional completions\r\n\t\t\t\t\tif ((outstandingWrites & 0x1f) == 0) {\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:350','[DFU] write completion callback, outstandingWrites=', outstandingWrites, 'adaptiveWindow=', adaptiveMaxOutstanding, 'device=', deviceId);\r\n\t\t\t\t\t}\r\n\t\t\t\t\t// detect write failure signaled by service manager\r\n\t\t\t\t\tif (res !== true) {\r\n\t\t\t\t\t\tadaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2));\r\n\t\t\t\t\t\tfailureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay)));\r\n\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:356','[DFU] writeCharacteristic returned false for device=', deviceId, 'offset=', writeOffset, 'adaptiveWindow now=', adaptiveMaxOutstanding);\r\n\t\t\t\t\t\ttry { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: 'write returned false' }); } catch (e) { }\r\n\t\t\t\t\t}\r\n\t\t\t\t}).catch((e) => {\r\n\t\t\t\t\toutstandingWrites = Math.max(0, outstandingWrites - 1);\r\n\t\t\t\t\tadaptiveMaxOutstanding = Math.max(minOutstandingWindow, Math.floor(adaptiveMaxOutstanding / 2));\r\n\t\t\t\t\tfailureBackoffMs = Math.min(200, Math.max(failureBackoffMs, Math.max(5, writeRetryDelay)));\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:363','[DFU] fire-and-forget write failed for device=', deviceId, e, 'adaptiveWindow now=', adaptiveMaxOutstanding);\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tconst errMsg ='[DFU] fire-and-forget write failed for device=';\r\n\t\t\t\t\t\tthis._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: writeOffset, reason: errMsg });\r\n\t\t\t\t\t} catch (e2) { }\r\n\t\t\t\t});\r\n\t\t\t\t// account bytes for throughput\r\n\t\t\t\tthroughputWindowBytes += slice.length;\r\n\t\t\t\t_logThroughputIfNeeded(false);\r\n\t\t\t} else {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:373','[DFU] awaiting write for chunk offset=', offset);\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst writeResult = await serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_PACKET_UUID, slice, writeOpts);\r\n\t\t\t\t\tif (writeResult !== true) {\r\n\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:377','[DFU] writeCharacteristic(await) returned false at offset=', offset, 'device=', deviceId);\r\n\t\t\t\t\t\ttry { this._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: 'write returned false' }); } catch (e) { }\r\n\t\t\t\t\t\t// abort DFU by throwing\r\n\t\t\t\t\t\tthrow new Error('write failed');\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:383','[DFU] awaiting write failed at offset=', offset, 'device=', deviceId, e);\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tconst errMsg = '[DFU] awaiting write failed ';\r\n\t\t\t\t\t\tthis._emitDfuEvent(deviceId, 'onError', { phase: 'write', offset: offset, reason: errMsg });\r\n\t\t\t\t\t} catch (e2) { }\r\n\t\t\t\t\tthrow e;\r\n\t\t\t\t}\r\n\t\t\t\t// account bytes for throughput\r\n\t\t\t\tthroughputWindowBytes += slice.length;\r\n\t\t\t\t_logThroughputIfNeeded(false);\r\n\t\t\t}\r\n\t\t\t// update PRN counters and wait when window reached\r\n\t\t\tconst sessAfter = this.sessions.get(deviceId);\r\n\t\t\tif (sessAfter != null && sessAfter.useNordic == true && typeof sessAfter.prn == 'number' && (sessAfter.prn ?? 0) > 0) {\r\n\t\t\t\tsessAfter.packetsSincePrn = (sessAfter.packetsSincePrn ?? 0) + 1;\r\n\t\t\t\tif ((sessAfter.packetsSincePrn ?? 0) >= (sessAfter.prn ?? 0) && (sessAfter.prn ?? 0) > 0) {\r\n\t\t\t\t\t// wait for PRN (device notification) before continuing\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:401','[DFU] reached PRN window, waiting for PRN for', deviceId, 'packetsSincePrn=', sessAfter.packetsSincePrn, 'prn=', sessAfter.prn);\r\n\t\t\t\t\t\tawait this._waitForPrn(deviceId, prnTimeoutMs);\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:403','[DFU] PRN received, resuming transfer for', deviceId);\r\n\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:405','[DFU] PRN wait failed/timed out, continuing anyway for', deviceId, e);\r\n\t\t\t\t\t\tif (disablePrnOnTimeout) {\r\n\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:407','[DFU] disabling PRN waits after timeout for', deviceId);\r\n\t\t\t\t\t\t\tsessAfter.prn = 0;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t\t// reset counter\r\n\t\t\t\t\tsessAfter.packetsSincePrn = 0;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\toffset = end;\r\n\t\t\t// 如果启用 nordic 模式,统计已发送字节\r\n\t\t\tconst sess = this.sessions.get(deviceId);\r\n\t\t\tif (sess != null && typeof sess.bytesSent == 'number') {\r\n\t\t\t\tsess.bytesSent = (sess.bytesSent ?? 0) + slice.length;\r\n\t\t\t}\r\n\t\t\t// 简单节流与日志,避免过快。默认睡眠非常短以提高吞吐量; 可在设备上调节\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:422','[DFU] wrote chunk for', deviceId, 'offset=', offset, '/', total, 'chunkSize=', slice.length, 'bytesSent=', sess != null ? sess.bytesSent : null, 'outstanding=', outstandingWrites);\r\n\t\t\t// emit upload progress event (percent) if available\r\n\t\t\tif (sess != null && typeof sess.bytesSent == 'number' && typeof sess.totalBytes == 'number') {\r\n\t\t\t\tconst p = Math.floor((sess.bytesSent / sess.totalBytes) * 100);\r\n\t\t\t\tthis._emitDfuEvent(deviceId, 'onProgress', p);\r\n\t\t\t}\r\n\t\t\t// yield to event loop and avoid starving the Android BLE stack\r\n\t\t\tawait this._sleep(Math.max(0, writeSleepMs));\r\n\t\t}\r\n\t// wait for outstanding writes to drain before continuing with control commands\r\n\tif (outstandingWrites > 0) {\r\n\t\tconst drainStart = Date.now();\r\n\t\twhile (outstandingWrites > 0 && (Date.now() - drainStart) < drainOutstandingTimeout) {\r\n\t\t\tawait this._sleep(Math.max(0, writeSleepMs));\r\n\t\t}\r\n\t\tif (outstandingWrites > 0) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:438','[DFU] outstandingWrites remain after drain timeout, continuing with', outstandingWrites);\r\n\t\t} else {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:440','[DFU] outstandingWrites drained before control phase');\r\n\t\t}\r\n\t}\r\n\tthis._emitDfuEvent(deviceId, 'onUploadingCompleted', null);\r\n\r\n\t\t\t// force final throughput log before activate/validate\r\n\t\t\t_logThroughputIfNeeded(true);\r\n\r\n\t\t// 发送 activate/validate 命令到 control point(需根据设备协议实现)\r\n\t\t// 下面为占位:请替换为实际的 opcode\r\n\t\t// 在写入前先启动控制结果等待,防止设备快速响应导致丢失通知\r\n\t\tconst controlTimeout = 20000;\r\n\t\tconst controlResultPromise = this._waitForControlResult(deviceId, controlTimeout);\r\n\t\ttry {\r\n\t\t\t// control writes: pass undefined options explicitly to satisfy the generator/typechecker\r\n\t\t\tconst activatePayload = new Uint8Array([0x04]);\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:456','[DFU] sending activate/validate payload=', Array.from(activatePayload));\r\n\t\t\tawait serviceManager.writeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID, activatePayload, null);\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:458','[DFU] activate/validate write returned for', deviceId);\r\n\t\t} catch (e) {\r\n\t\t\t// 写入失败时取消控制等待,避免悬挂定时器\r\n\t\t\ttry {\r\n\t\t\t\tconst sessOnWriteFail = this.sessions.get(deviceId);\r\n\t\t\t\tif (sessOnWriteFail != null && typeof sessOnWriteFail.reject == 'function') {\r\n\t\t\t\t\tsessOnWriteFail.reject(e);\r\n\t\t\t\t}\r\n\t\t\t} catch (rejectErr) { }\r\n\t\t\tawait controlResultPromise.catch(() => { });\r\n\t\t\ttry { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e2) { }\r\n\t\t\tthis.sessions.delete(deviceId);\r\n\t\t\tthrow e;\r\n\t\t}\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:472','[DFU] sent control activate/validate command to control point for', deviceId);\r\n\t\tthis._emitDfuEvent(deviceId, 'onValidating', null);\r\n\r\n\t// 等待 control-point 返回最终结果(成功或失败),超时可配置\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:476','[DFU] waiting for control result (timeout=', controlTimeout, ') for', deviceId);\r\n\ttry {\r\n\t\tawait controlResultPromise;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:479','[DFU] control result resolved for', deviceId);\r\n\t} catch (err) {\r\n\t\t// 清理订阅后抛出\r\n\t\ttry { await serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID); } catch (e) { }\r\n\t\tthis.sessions.delete(deviceId);\r\n\t\tthrow err;\r\n\t}\r\n\r\n\t\t// 取消订阅\r\n\t\ttry {\r\n\t\t\tawait serviceManager.unsubscribeCharacteristic(deviceId, DFU_SERVICE_UUID, DFU_CONTROL_POINT_UUID);\r\n\t\t} catch (e) { }\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:491','[DFU] unsubscribed control point for', deviceId);\r\n\r\n\t\t// 清理会话\r\n\t\tthis.sessions.delete(deviceId);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:495','[DFU] session cleared for', deviceId);\r\n\r\n\t\treturn;\r\n\t}\r\n\r\n\tasync _requestMtu(gatt : BluetoothGatt, mtu : number, timeoutMs : number) : Promise {\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\t// 在当前项目,BluetoothGattCallback.onMtuChanged 未被封装;简单发起请求并等待短超时\r\n\t\t\ttry {\r\n\t\t\t\tconst ok = gatt.requestMtu(Math.floor(mtu) as Int);\r\n\t\t\t\tif (!ok) {\r\n\t\t\t\t\treturn reject(new Error('requestMtu failed'));\r\n\t\t\t\t}\r\n\t\t\t} catch (e) {\r\n\t\t\t\treturn reject(e);\r\n\t\t\t}\r\n\t\t\t// 无 callback 监听时退回,等待一小段时间以便成功\r\n\t\t\tsetTimeout(() => resolve(), Math.min(2000, timeoutMs));\r\n\t\t});\r\n\t}\r\n\r\n\t_sleep(ms : number) {\r\n\t\treturn new Promise((r) => { setTimeout(() => { r() }, ms); });\r\n\t}\r\n\r\n\t_waitForPrn(deviceId : string, timeoutMs : number) : Promise {\r\n\t\tconst session = this.sessions.get(deviceId);\r\n\t\tif (session == null) return Promise.reject(new Error('no dfu session'));\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\tconst timer = setTimeout(() => {\r\n\t\t\t\t// timeout waiting for PRN\r\n\t\t\t\t// clear pending handlers\r\n\t\t\t\tsession.prnResolve = null;\r\n\t\t\t\tsession.prnReject = null;\r\n\t\t\t\treject(new Error('PRN timeout'));\r\n\t\t\t}, timeoutMs);\r\n\t\t\tconst prnResolve = () => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\tresolve();\r\n\t\t\t};\r\n\t\t\tconst prnReject = (err ?: any) => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\treject(err);\r\n\t\t\t};\r\n\t\t\tsession.prnResolve = prnResolve;\r\n\t\t\tsession.prnReject = prnReject;\r\n\t\t});\r\n\t}\r\n\r\n\t// 默认 control point 解析器(非常通用的尝试解析:如果设备发送 progress byte 或成功码)\r\n\t_defaultControlParser(data : Uint8Array) : ControlParserResult | null {\r\n\t\t// 假设协议:第一个字节为 opcode, 第二字节可为状态或进度\r\n\t\tif (data == null || data.length === 0) return null;\r\n\t\tconst op = data[0];\r\n\t\t// Nordic-style response: [0x10, requestOp, resultCode]\r\n\t\tif (op === 0x10 && data.length >= 3) {\r\n\t\t\tconst requestOp = data[1];\r\n\t\t\tconst resultCode = data[2];\r\n\t\t\tif (resultCode === 0x01) {\r\n\t\t\t\treturn { type: 'success' };\r\n\t\t\t}\r\n\t\t\treturn { type: 'error', error: { requestOp: requestOp, resultCode: resultCode, raw: Array.from(data) } };\r\n\t\t}\r\n\t\t// Nordic PRN notification: [0x11, LSB, MSB] -> return as progress (bytes received)\r\n\t\tif (op === 0x11 && data.length >= 3) {\r\n\t\t\tconst lsb = data[1];\r\n\t\t\tconst msb = data[2];\r\n\t\t\tconst received = (msb << 8) | lsb;\r\n\t\t\treturn { type: 'progress', progress: received };\r\n\t\t}\r\n\t\t// vendor-specific opcode example: 0x60 may mean 'response/progress' for some firmwares\r\n\t\tif (op === 0x60) {\r\n\t\t\tif (data.length >= 3) {\r\n\t\t\t\tconst requestOp = data[1];\r\n\t\t\t\tconst status = data[2];\r\n\t\t\t\t// Known success/status codes observed in field devices\r\n\t\t\t\tif (status === 0x00 || status === 0x01 || status === 0x0A) {\r\n\t\t\t\t\treturn { type: 'success' };\r\n\t\t\t\t}\r\n\t\t\t\treturn { type: 'error', error: { requestOp: requestOp, resultCode: status, raw: Array.from(data) } };\r\n\t\t\t}\r\n\t\t\tif (data.length >= 2) {\r\n\t\t\t\treturn { type: 'progress', progress: data[1] };\r\n\t\t\t}\r\n\t\t}\r\n\t\t// 通用进度回退:若第二字节位于 0-100 之间,当作百分比\r\n\t\tif (data.length >= 2) {\r\n\t\t\tconst maybeProgress = data[1];\r\n\t\t\tif (maybeProgress >= 0 && maybeProgress <= 100) {\r\n\t\t\t\treturn { type: 'progress', progress: maybeProgress };\r\n\t\t\t}\r\n\t\t}\r\n\t\t// 若找到明显的 success opcode (示例 0x01) 或 error 0xFF\r\n\t\tif (op === 0x01) return { type: 'success' };\r\n\t\tif (op === 0xFF) return { type: 'error', error: data };\r\n\t\treturn { type: 'info' };\r\n\t}\r\n\r\n\t// Nordic DFU control-parser(支持 Response and Packet Receipt Notification)\r\n\t_nordicControlParser(data : Uint8Array) : ControlParserResult | null {\r\n\t\t// Nordic opcodes (简化):\r\n\t\t// - 0x10 : Response (opcode, requestOp, resultCode)\r\n\t\t// - 0x11 : Packet Receipt Notification (opcode, value LSB, value MSB)\r\n\t\tif (data == null || data.length == 0) return null;\r\n\t\tconst op = data[0];\r\n\t\tif (op == 0x11 && data.length >= 3) {\r\n\t\t\t// packet receipt notif: bytes received (little endian)\r\n\t\t\tconst lsb = data[1];\r\n\t\t\tconst msb = data[2];\r\n\t\t\tconst received = (msb << 8) | lsb;\r\n\t\t\t// Return received bytes as progress value; parser does not resolve device-specific session here.\r\n\t\t\treturn { type: 'progress', progress: received };\r\n\t\t}\r\n\t\t// Nordic vendor-specific progress/response opcode (example 0x60)\r\n\t\tif (op == 0x60) {\r\n\t\t\tif (data.length >= 3) {\r\n\t\t\t\tconst requestOp = data[1];\r\n\t\t\t\tconst status = data[2];\r\n\t\t\t\tif (status == 0x00 || status == 0x01 || status == 0x0A) {\r\n\t\t\t\t\treturn { type: 'success' };\r\n\t\t\t\t}\r\n\t\t\t\treturn { type: 'error', error: { requestOp, resultCode: status, raw: Array.from(data) } };\r\n\t\t\t}\r\n\t\t\tif (data.length >= 2) {\r\n\t\t\t\treturn { type: 'progress', progress: data[1] };\r\n\t\t\t}\r\n\t\t}\r\n\t\t// Response: check result code for success (0x01 may indicate success in some stacks)\r\n\t\tif (op == 0x10 && data.length >= 3) {\r\n\t\t\tconst requestOp = data[1];\r\n\t\t\tconst resultCode = data[2];\r\n\t\t\t// Nordic resultCode 0x01 = SUCCESS typically\r\n\t\t\tif (resultCode == 0x01) return { type: 'success' };\r\n\t\t\telse return { type: 'error', error: { requestOp, resultCode } };\r\n\t\t}\r\n\t\treturn null;\r\n\t}\r\n\r\n\t_handleControlNotification(deviceId : string, data : Uint8Array) {\r\n\t\tconst session = this.sessions.get(deviceId);\r\n\t\tif (session == null) {\r\n\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:636','[DFU] control notification received but no session for', deviceId, 'data=', Array.from(data));\r\n\t\t\treturn;\r\n\t\t}\r\n\t\ttry {\r\n\t\t\t// human readable opcode mapping\r\n\t\t\tlet opcodeName = 'unknown';\r\n\t\t\tswitch (data[0]) {\r\n\t\t\t\tcase 0x10: opcodeName = 'Response'; break;\r\n\t\t\t\tcase 0x11: opcodeName = 'PRN'; break;\r\n\t\t\t\tcase 0x60: opcodeName = 'VendorProgress'; break;\r\n\t\t\t\tcase 0x01: opcodeName = 'SuccessOpcode'; break;\r\n\t\t\t\tcase 0xFF: opcodeName = 'ErrorOpcode'; break;\r\n\t\t\t}\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:649','[DFU] _handleControlNotification deviceId=', deviceId, 'opcode=0x' + data[0].toString(16), 'name=', opcodeName, 'raw=', Array.from(data));\r\n\t\t\tconst parsed = session.controlParser != null ? session.controlParser(data) : null;\r\n\t\t\tif (session.onLog != null) session.onLog('DFU control notify: ' + Array.from(data).join(','));\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:652','[DFU] parsed control result=', parsed);\r\n\t\t\tif (parsed == null) return;\r\n\t\t\tif (parsed.type == 'progress' && parsed.progress != null) {\r\n\t\t\t\t// 如果在 nordic 模式 parsed.progress 可能是已接收字节数,则转换为百分比\r\n\t\t\t\tif (session.useNordic == true && session.totalBytes != null && session.totalBytes > 0) {\r\n\t\t\t\t\t\tconst percent = Math.floor((parsed.progress / session.totalBytes) * 100);\r\n\t\t\t\t\tsession.onProgress?.(percent);\r\n\t\t\t\t\t\t// If we have written all bytes locally, log that event\r\n\t\t\t\t\t\tif (session.bytesSent != null && session.totalBytes != null && session.bytesSent >= session.totalBytes) {\r\n\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:661','[DFU] all bytes written locally for', deviceId, 'bytesSent=', session.bytesSent, 'total=', session.totalBytes);\r\n\t\t\t\t\t\t\t// emit uploading completed once\r\n\t\t\t\t\t\t\tthis._emitDfuEvent(deviceId, 'onUploadingCompleted', null);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t// If a PRN wait is pending, resolve it (PRN indicates device received packets)\r\n\t\t\t\t\tif (typeof session.prnResolve == 'function') {\r\n\t\t\t\t\t\ttry { session.prnResolve(); } catch (e) { }\r\n\t\t\t\t\t\tsession.prnResolve = null;\r\n\t\t\t\t\t\tsession.prnReject = null;\r\n\t\t\t\t\t\tsession.packetsSincePrn = 0;\r\n\t\t\t\t\t}\r\n\t\t\t\t} else {\r\n\t\t\t\t\tconst progress = parsed.progress\r\n\t\t\t\t\tif (progress != null) {\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:675','[DFU] progress for', deviceId, 'progress=', progress);\r\n\t\t\t\t\t\tsession.onProgress?.(progress);\r\n\t\t\t\t\t\t// also resolve PRN if was waiting (in case device reports numeric progress)\r\n\t\t\t\t\t\tif (typeof session.prnResolve == 'function') {\r\n\t\t\t\t\t\t\ttry { session.prnResolve(); } catch (e) { }\r\n\t\t\t\t\t\t\tsession.prnResolve = null;\r\n\t\t\t\t\t\t\tsession.prnReject = null;\r\n\t\t\t\t\t\t\tsession.packetsSincePrn = 0;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t} else if (parsed.type == 'success') {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:687','[DFU] parsed success for', deviceId, 'resolving session');\r\n\t\t\t\tsession.resolve();\r\n\t\t\t\t// Log final device-acknowledged success\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:690','[DFU] device reported DFU success for', deviceId);\r\n\t\t\t\tthis._emitDfuEvent(deviceId, 'onDfuCompleted', null);\r\n\t\t\t} else if (parsed.type == 'error') {\r\n\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:693','[DFU] parsed error for', deviceId, parsed.error);\r\n\t\t\t\tsession.reject(parsed.error ?? new Error('DFU device error'));\r\n\t\t\t\tthis._emitDfuEvent(deviceId, 'onError', parsed.error ?? {});\r\n\t\t\t} else {\r\n\t\t\t\t// info - just log\r\n\t\t\t}\r\n\t\t} catch (e) {\r\n\t\t\tsession.onLog?.('control parse error: ' + e);\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:701','[DFU] control parse exception for', deviceId, e);\r\n\t\t}\r\n\t}\r\n\r\n\t_waitForControlResult(deviceId : string, timeoutMs : number) : Promise {\r\n\t\tconst session = this.sessions.get(deviceId);\r\n\t\tif (session == null) return Promise.reject(new Error('no dfu session'));\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\t// wrap resolve/reject to clear timer\r\n\t\t\tconst timer = setTimeout(() => {\r\n\t\t\t\t// 超时\r\n\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:712','[DFU] _waitForControlResult timeout for', deviceId);\r\n\t\t\t\treject(new Error('DFU control timeout'));\r\n\t\t\t}, timeoutMs);\r\n\t\t\tconst origResolve = () => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:717','[DFU] _waitForControlResult resolved for', deviceId);\r\n\t\t\t\tresolve();\r\n\t\t\t};\r\n\t\t\tconst origReject = (err ?: any) => {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/dfu_manager.uts:722','[DFU] _waitForControlResult rejected for', deviceId, 'err=', err);\r\n\t\t\t\treject(err);\r\n\t\t\t};\r\n\t\t\t// replace session handlers temporarily (guard nullable)\r\n\t\t\tif (session != null) {\r\n\t\t\t\tsession.resolve = origResolve;\r\n\t\t\t\tsession.reject = origReject;\r\n\t\t\t}\r\n\t\t});\r\n\t}\r\n}\r\n\r\nexport const dfuManager = new DfuManager();"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts new file mode 100644 index 0000000..5e8d55a --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts @@ -0,0 +1,113 @@ +import * as BluetoothManager from './bluetooth_manager.uts'; +import { ServiceManager } from './service_manager.uts'; +import type { ScanDevicesOptions, BleConnectOptionsExt, MultiProtocolDevice, BleEvent, BleEventCallback, BleService, BleCharacteristic, WriteCharacteristicOptions, AutoBleInterfaces, BleDataReceivedCallback } from '../interface.uts'; +import { DeviceManager } from './device_manager.uts'; +const serviceManager = ServiceManager.getInstance(); +export class BluetoothService { + scanDevices(options?: ScanDevicesOptions): Promise { return BluetoothManager.scanDevices(options); } + connectDevice(deviceId: string, protocol: string, options?: BleConnectOptionsExt): Promise { return BluetoothManager.connectDevice(deviceId, protocol, options); } + disconnectDevice(deviceId: string, protocol: string): Promise { return BluetoothManager.disconnectDevice(deviceId, protocol); } + getConnectedDevices(): MultiProtocolDevice[] { return BluetoothManager.getConnectedDevices(); } + on(event: BleEvent, callback: BleEventCallback) { return BluetoothManager.on(event, callback); } + off(event: BleEvent, callback?: BleEventCallback) { return BluetoothManager.off(event, callback); } + getServices(deviceId: string): Promise { + return new Promise((resolve, reject) => { + serviceManager.getServices(deviceId, (list, err) => { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:18', 'getServices:', list, err); // 新增日志 + if (err != null) + reject(err); + else + resolve((list as BleService[]) ?? []); + }); + }); + } + getCharacteristics(deviceId: string, serviceId: string): Promise { + return new Promise((resolve, reject) => { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:26', deviceId, serviceId); + serviceManager.getCharacteristics(deviceId, serviceId, (list, err) => { + if (err != null) + reject(err); + else + resolve((list as BleCharacteristic[]) ?? []); + }); + }); + } + /** + * 自动发现服务和特征,返回可用的写入和通知特征ID + * @param deviceId 设备ID + * @returns {Promise} + */ + async getAutoBleInterfaces(deviceId: string): Promise { + // 1. 获取服务列表 + const services = await this.getServices(deviceId); + if (services == null || services.length == 0) + throw new Error('未发现服务'); + // 2. 选择目标服务(优先bae前缀,可根据需要调整) + let serviceId = ''; + for (let i = 0; i < services.length; i++) { + const s = services[i]; + const uuidCandidate: string | null = (s.uuid != null ? s.uuid : null); + const uuid: string = uuidCandidate != null ? uuidCandidate : ''; + // prefer regex test to avoid nullable receiver calls in generated Kotlin + if (/^bae/i.test(uuid)) { + serviceId = uuid; + break; + } + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:55', serviceId); + if (serviceId == null || serviceId == '') + serviceId = services[0].uuid; + // 3. 获取特征列表 + const characteristics = await this.getCharacteristics(deviceId, serviceId); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:60', characteristics); + if (characteristics == null || characteristics.length == 0) + throw new Error('未发现特征值'); + // 4. 筛选write和notify特征 + let writeCharId = ''; + let notifyCharId = ''; + for (let i = 0; i < characteristics.length; i++) { + const c = characteristics[i]; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:69', c); + if ((writeCharId == null || writeCharId == '') && c.properties != null && (c.properties.write || c.properties.writeWithoutResponse == true)) + writeCharId = c.uuid; + if ((notifyCharId == null || notifyCharId == '') && c.properties != null && (c.properties.notify || c.properties.indicate)) + notifyCharId = c.uuid; + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:73', serviceId, writeCharId, notifyCharId); + if ((writeCharId == null || writeCharId == '') || (notifyCharId == null || notifyCharId == '')) + throw new Error('未找到合适的写入或通知特征'); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:75', serviceId, writeCharId, notifyCharId); + // // 发现服务和特征后 + const deviceManager = DeviceManager.getInstance(); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:78', deviceManager); + const device = deviceManager.getDevice(deviceId); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:80', deviceId, device); + device!.serviceId = serviceId; + device!.writeCharId = writeCharId; + device!.notifyCharId = notifyCharId; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:84', device); + return { serviceId, writeCharId, notifyCharId } as AutoBleInterfaces; + } + async subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, onData: BleDataReceivedCallback): Promise { + return serviceManager.subscribeCharacteristic(deviceId, serviceId, characteristicId, onData); + } + async readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + return serviceManager.readCharacteristic(deviceId, serviceId, characteristicId); + } + async writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, data: Uint8Array, options?: WriteCharacteristicOptions): Promise { + return serviceManager.writeCharacteristic(deviceId, serviceId, characteristicId, data, options); + } + async unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + return serviceManager.unsubscribeCharacteristic(deviceId, serviceId, characteristicId); + } + async autoDiscoverAll(deviceId: string): Promise { + return serviceManager.autoDiscoverAll(deviceId); + } + async subscribeAllNotifications(deviceId: string, onData: BleDataReceivedCallback): Promise { + return serviceManager.subscribeAllNotifications(deviceId, onData); + } +} +export const bluetoothService = new BluetoothService(); +// Ensure protocol handlers are registered when this module is imported. +// import './protocol_registry.uts'; +//# sourceMappingURL=index.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts.map new file mode 100644 index 0000000..b67c8bf --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/index.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"index.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/app-android/index.uts"],"names":[],"mappings":"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","sourcesContent":["import * as BluetoothManager from './bluetooth_manager.uts';\r\nimport { ServiceManager } from './service_manager.uts';\r\nimport type { ScanDevicesOptions, BleConnectOptionsExt, MultiProtocolDevice, BleEvent, BleEventCallback, BleService, BleCharacteristic, WriteCharacteristicOptions, AutoBleInterfaces, BleDataReceivedCallback } from '../interface.uts';\r\nimport { DeviceManager } from './device_manager.uts';\r\n\r\nconst serviceManager = ServiceManager.getInstance();\r\n\r\nexport class BluetoothService {\r\n scanDevices(options?: ScanDevicesOptions) { return BluetoothManager.scanDevices(options); }\r\n connectDevice(deviceId: string, protocol: string, options?: BleConnectOptionsExt) { return BluetoothManager.connectDevice(deviceId, protocol, options); }\r\n disconnectDevice(deviceId: string, protocol: string) { return BluetoothManager.disconnectDevice(deviceId, protocol); }\r\n getConnectedDevices(): MultiProtocolDevice[] { return BluetoothManager.getConnectedDevices(); }\r\n on(event: BleEvent, callback: BleEventCallback) { return BluetoothManager.on(event, callback); }\r\n off(event: BleEvent, callback?: BleEventCallback) { return BluetoothManager.off(event, callback); }\r\n getServices(deviceId: string): Promise {\r\n return new Promise((resolve, reject) => {\r\n serviceManager.getServices(deviceId, (list, err) => {\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:18','getServices:', list, err); // 新增日志\r\n if (err != null) reject(err);\r\n else resolve((list as BleService[]) ?? []);\r\n });\r\n });\r\n }\r\n getCharacteristics(deviceId: string, serviceId: string): Promise {\r\n return new Promise((resolve, reject) => {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:26',deviceId,serviceId)\r\n serviceManager.getCharacteristics(deviceId, serviceId, (list, err) => {\r\n if (err != null) reject(err);\r\n else resolve((list as BleCharacteristic[]) ?? []);\r\n });\r\n });\r\n }\r\n /**\r\n * 自动发现服务和特征,返回可用的写入和通知特征ID\r\n * @param deviceId 设备ID\r\n * @returns {Promise}\r\n */\r\n async getAutoBleInterfaces(deviceId: string): Promise {\r\n // 1. 获取服务列表\r\n const services = await this.getServices(deviceId);\r\n if (services == null || services.length == 0) throw new Error('未发现服务');\r\n\r\n // 2. 选择目标服务(优先bae前缀,可根据需要调整)\r\n let serviceId = '';\r\n for (let i = 0; i < services.length; i++) {\r\n const s = services[i];\r\n const uuidCandidate: string | null = (s.uuid != null ? s.uuid : null)\r\n const uuid: string = uuidCandidate != null ? uuidCandidate : ''\r\n // prefer regex test to avoid nullable receiver calls in generated Kotlin\r\n if (/^bae/i.test(uuid)) {\r\n serviceId = uuid\r\n break;\r\n }\r\n }\r\n __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:55',serviceId)\r\n if (serviceId == null || serviceId == '') serviceId = services[0].uuid;\r\n\r\n // 3. 获取特征列表\r\n const characteristics = await this.getCharacteristics(deviceId, serviceId);\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:60',characteristics)\r\n if (characteristics == null || characteristics.length == 0) throw new Error('未发现特征值');\r\n\r\n // 4. 筛选write和notify特征\r\n let writeCharId = '';\r\n let notifyCharId = '';\r\n for (let i = 0; i < characteristics.length; i++) {\r\n\t\t\r\n const c = characteristics[i];\r\n\t __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:69',c)\r\n if ((writeCharId == null || writeCharId == '') && c.properties != null && (c.properties.write || c.properties.writeWithoutResponse==true)) writeCharId = c.uuid;\r\n if ((notifyCharId == null || notifyCharId == '') && c.properties != null && (c.properties.notify || c.properties.indicate)) notifyCharId = c.uuid;\r\n }\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:73',serviceId, writeCharId, notifyCharId);\r\n if ((writeCharId == null || writeCharId == '') || (notifyCharId == null || notifyCharId == '')) throw new Error('未找到合适的写入或通知特征');\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:75',serviceId, writeCharId, notifyCharId);\r\n // // 发现服务和特征后\r\n\tconst deviceManager = DeviceManager.getInstance();\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:78',deviceManager);\r\n const device = deviceManager.getDevice(deviceId);\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:80',deviceId,device)\r\n device!.serviceId = serviceId;\r\n device!.writeCharId = writeCharId;\r\n device!.notifyCharId = notifyCharId;\r\n\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/index.uts:84',device);\r\n return { serviceId, writeCharId, notifyCharId };\r\n }\r\n async subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, onData: BleDataReceivedCallback): Promise {\r\n return serviceManager.subscribeCharacteristic(deviceId, serviceId, characteristicId, onData);\r\n }\r\n async readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise {\r\n return serviceManager.readCharacteristic(deviceId, serviceId, characteristicId);\r\n }\r\n async writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, data: Uint8Array, options?: WriteCharacteristicOptions): Promise {\r\n return serviceManager.writeCharacteristic(deviceId, serviceId, characteristicId, data, options);\r\n }\r\n async unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise {\r\n return serviceManager.unsubscribeCharacteristic(deviceId, serviceId, characteristicId);\r\n }\r\n async autoDiscoverAll(deviceId: string): Promise {\r\n return serviceManager.autoDiscoverAll(deviceId);\r\n }\r\n async subscribeAllNotifications(deviceId: string, onData: BleDataReceivedCallback): Promise {\r\n return serviceManager.subscribeAllNotifications(deviceId, onData);\r\n }\r\n}\r\n\r\nexport const bluetoothService = new BluetoothService();\r\n\r\n// Ensure protocol handlers are registered when this module is imported.\r\n // import './protocol_registry.uts';\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts new file mode 100644 index 0000000..dee1aec --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts @@ -0,0 +1,711 @@ +import type { BleService, BleCharacteristic, BleDataReceivedCallback, BleCharacteristicProperties, WriteCharacteristicOptions, ByteArray } from '../interface.uts'; +import BluetoothGatt from "android.bluetooth.BluetoothGatt"; +import BluetoothGattService from "android.bluetooth.BluetoothGattService"; +import BluetoothGattCharacteristic from "android.bluetooth.BluetoothGattCharacteristic"; +import BluetoothGattDescriptor from "android.bluetooth.BluetoothGattDescriptor"; +import BluetoothGattCallback from "android.bluetooth.BluetoothGattCallback"; +import UUID from "java.util.UUID"; +import { DeviceManager } from './device_manager.uts'; +import { AkBleErrorImpl, AkBluetoothErrorCode } from '../unierror.uts'; +import { AutoDiscoverAllResult } from '../interface.uts'; +// 补全UUID格式,将短格式转换为标准格式 +function getFullUuid(shortUuid: string): string { + return `0000${shortUuid}-0000-1000-8000-00805f9b34fb`; +} +const deviceWriteQueues = new Map>(); +function enqueueDeviceWrite(deviceId: string, work: () => Promise): Promise { + const previous = deviceWriteQueues.get(deviceId) ?? Promise.resolve(); + const next = (async (): Promise => { + try { + await previous; + } + catch (e: any) { /* ignore previous rejection to keep queue alive */ } + return await work(); + })(); + const queued = next.then(() => { }, () => { }); + deviceWriteQueues.set(deviceId, queued); + return next.finally(() => { + if (deviceWriteQueues.get(deviceId) == queued) { + deviceWriteQueues.delete(deviceId); + } + }); +} +function createCharProperties(props: number): BleCharacteristicProperties { + const result: BleCharacteristicProperties = { + read: false, + write: false, + notify: false, + indicate: false, + canRead: false, + canWrite: false, + canNotify: false, + writeWithoutResponse: false + }; + result.read = (props & BluetoothGattCharacteristic.PROPERTY_READ) !== 0; + result.write = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0; + result.notify = (props & BluetoothGattCharacteristic.PROPERTY_NOTIFY) !== 0; + result.indicate = (props & BluetoothGattCharacteristic.PROPERTY_INDICATE) !== 0; + result.writeWithoutResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0; + result.canRead = result.read; + const writeWithoutResponse = result.writeWithoutResponse!; + result.canWrite = (result.write != null && result.write) || (writeWithoutResponse != null && writeWithoutResponse); + result.canNotify = result.notify; + return result; +} +// 定义 PendingCallback 类型和实现类 +interface PendingCallback { + resolve: (data: any) => void; + reject: (err?: any) => void; + timer?: number; // Changed from any to number +} +class PendingCallbackImpl implements PendingCallback { + override resolve: (data: any) => void; + override reject: (err?: any) => void; + override timer?: number; // Changed from any to number + constructor(resolve: (data: any) => void, reject: (err?: any) => void, timer?: number) { + this.resolve = resolve; + this.reject = reject; + this.timer = timer; + } +} +// 全局回调管理(必须在类外部声明) +let pendingCallbacks: Map; +let notifyCallbacks: Map; +// 在全局范围内初始化 +pendingCallbacks = new Map(); +notifyCallbacks = new Map(); +// 服务发现等待队列:deviceId -> 回调数组 +const serviceDiscoveryWaiters = new Map void)[]>(); +// 服务发现状态:deviceId -> 是否已发现 +const serviceDiscovered = new Map(); +// 特征发现等待队列:deviceId|serviceId -> 回调数组 +const characteristicDiscoveryWaiters = new Map void)[]>(); +class GattCallback extends BluetoothGattCallback { + constructor() { + super(); + } + override onServicesDiscovered(gatt: BluetoothGatt, status: Int): void { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:108', 'ak onServicesDiscovered'); + const deviceId = gatt.getDevice().getAddress(); + if (status == BluetoothGatt.GATT_SUCCESS) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:111', `服务发现成功: ${deviceId}`); + serviceDiscovered.set(deviceId, true); + // 统一回调所有等待 getServices 的调用 + const waiters = serviceDiscoveryWaiters.get(deviceId); + if (waiters != null && waiters.length > 0) { + const services = gatt.getServices(); + const result: BleService[] = []; + if (services != null) { + const servicesList = services; + const size = servicesList.size; + for (let i = 0; i < size; i++) { + const service = servicesList.get(i as Int); + if (service != null) { + const bleService: BleService = { + uuid: service.getUuid().toString(), + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + result.push(bleService); + } + } + } + for (let i = 0; i < waiters.length; i++) { + const cb = waiters[i]; + if (cb != null) { + cb(result, null); + } + } + serviceDiscoveryWaiters.delete(deviceId); + } + } + else { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:139', `服务发现失败: ${deviceId}, status: ${status}`); + // 失败时也要通知等待队列 + const waiters = serviceDiscoveryWaiters.get(deviceId); + if (waiters != null && waiters.length > 0) { + for (let i = 0; i < waiters.length; i++) { + const cb = waiters[i]; + if (cb != null) { + cb(null, new Error('服务发现失败')); + } + } + serviceDiscoveryWaiters.delete(deviceId); + } + } + } + override onConnectionStateChange(gatt: BluetoothGatt, status: Int, newState: Int): void { + const deviceId = gatt.getDevice().getAddress(); + if (newState == BluetoothGatt.STATE_CONNECTED) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:154', `设备已连接: ${deviceId}`); + DeviceManager.handleConnectionStateChange(deviceId, 2, null); // 2 = STATE_CONNECTED + } + else if (newState == BluetoothGatt.STATE_DISCONNECTED) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:157', `设备已断开: ${deviceId}`); + serviceDiscovered.delete(deviceId); + DeviceManager.handleConnectionStateChange(deviceId, 0, null); // 0 = STATE_DISCONNECTED + } + } + override onCharacteristicChanged(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic): void { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:163', 'ak onCharacteristicChanged'); + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|notify`; + const callback = notifyCallbacks.get(key); + const value = characteristic.getValue(); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:170', '[onCharacteristicChanged]', key, value); + if (callback != null && value != null) { + const valueLength = value.size; + const arr = new Uint8Array(valueLength); + for (let i = 0 as Int; i < valueLength; i++) { + const v = value[i as Int]; + arr[i] = v != null ? v : 0; + } + // 保存接收日志 + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:179', ` + INSERT INTO ble_data_log (device_id, service_id, char_id, direction, data, timestamp) + VALUES ('${deviceId}', '${serviceId}', '${charId}', 'recv', '${Array.from(arr).join(',')}', ${Date.now()}) + `); + callback(arr); + } + } + override onCharacteristicRead(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int): void { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:188', 'ak onCharacteristicRead', status); + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|read`; + const pending = pendingCallbacks.get(key); + const value = characteristic.getValue(); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:195', '[onCharacteristicRead]', key, 'status=', status, 'value=', value); + if (pending != null) { + try { + const timer = pending.timer; + if (timer != null) { + clearTimeout(timer); + pending.timer = null; + } + pendingCallbacks.delete(key); + if (status == BluetoothGatt.GATT_SUCCESS && value != null) { + const valueLength = value.size; + const arr = new Uint8Array(valueLength); + for (let i = 0 as Int; i < valueLength; i++) { + const v = value[i as Int]; + arr[i] = v != null ? v : 0; + } + // resolve with ArrayBuffer + pending.resolve(arr.buffer as ArrayBuffer); + } + else { + pending.reject(new Error('Characteristic read failed')); + } + } + catch (e: any) { + try { + pending.reject(e); + } + catch (e2: any) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:218', e2); + } + } + } + } + override onCharacteristicWrite(gatt: BluetoothGatt, characteristic: BluetoothGattCharacteristic, status: Int): void { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:224', 'ak onCharacteristicWrite', status); + const deviceId = gatt.getDevice().getAddress(); + const serviceId = characteristic.getService().getUuid().toString(); + const charId = characteristic.getUuid().toString(); + const key = `${deviceId}|${serviceId}|${charId}|write`; + const pending = pendingCallbacks.get(key); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:230', '[onCharacteristicWrite]', key, 'status=', status); + if (pending != null) { + try { + const timer = pending.timer; + if (timer != null) { + clearTimeout(timer); + } + pendingCallbacks.delete(key); + if (status == BluetoothGatt.GATT_SUCCESS) { + pending.resolve('ok'); + } + else { + pending.reject(new Error('Characteristic write failed')); + } + } + catch (e: any) { + try { + pending.reject(e); + } + catch (e2: any) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:244', e2); + } + } + } + } +} +// 导出单例实例供外部使用 +export const gattCallback = new GattCallback(); +export class ServiceManager { + private static instance: ServiceManager | null = null; + private services = new Map(); + private characteristics = new Map>(); + private deviceManager = DeviceManager.getInstance(); + private constructor() { } + static getInstance(): ServiceManager { + if (ServiceManager.instance == null) { + ServiceManager.instance = new ServiceManager(); + } + return ServiceManager.instance!; + } + getServices(deviceId: string, callback?: (services: BleService[] | null, error?: Error) => void): any | Promise { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:267', 'ak start getservice', deviceId); + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) { + if (callback != null) { + callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); + } + return Promise.reject(new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:273', 'ak serviceDiscovered', gatt); + // 如果服务已发现,直接返回 + if (serviceDiscovered.get(deviceId) == true) { + const services = gatt.getServices(); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:277', services); + const result: BleService[] = []; + if (services != null) { + const servicesList = services; + const size = servicesList.size; + if (size > 0) { + for (let i = 0 as Int; i < size; i++) { + const service = servicesList != null ? servicesList.get(i) : servicesList[i]; + if (service != null) { + const bleService: BleService = { + uuid: service.getUuid().toString(), + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + result.push(bleService); + if (bleService.uuid == getFullUuid('0001')) { + const device = this.deviceManager.getDevice(deviceId); + if (device != null) { + device.serviceId = bleService.uuid; + this.getCharacteristics(deviceId, device.serviceId!, (chars, err) => { + if (err == null && chars != null) { + const writeChar = chars.find((c): boolean => c.uuid == getFullUuid('0010')); + const notifyChar = chars.find((c): boolean => c.uuid == getFullUuid('0011')); + if (writeChar != null) + device.writeCharId = writeChar.uuid; + if (notifyChar != null) + device.notifyCharId = notifyChar.uuid; + } + }); + } + } + } + } + } + } + if (callback != null) { + callback(result, null); + } + return Promise.resolve(result); + } + // 未发现则发起服务发现并加入等待队列 + if (!serviceDiscoveryWaiters.has(deviceId)) { + serviceDiscoveryWaiters.set(deviceId, []); + gatt.discoverServices(); + } + return new Promise((resolve, reject) => { + const cb = (services: BleService[] | null, error?: Error) => { + if (error != null) + reject(error); + else + resolve(services ?? []); + if (callback != null) + callback(services, error); + }; + const arr = serviceDiscoveryWaiters.get(deviceId); + if (arr != null) + arr.push(cb); + }); + } + getCharacteristics(deviceId: string, serviceId: string, callback: (characteristics: BleCharacteristic[] | null, error?: Error) => void): void { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) + return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", "")); + // 如果服务还没发现,等待服务发现后再查特征 + if (serviceDiscovered.get(deviceId) !== true) { + // 先注册到服务发现等待队列 + this.getServices(deviceId, (services, err) => { + if (err != null) { + callback(null, err); + } + else { + this.getCharacteristics(deviceId, serviceId, callback); + } + }); + return; + } + // 服务已发现,正常获取特征 + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) + return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", "")); + const chars = service.getCharacteristics(); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:347', chars); + const result: BleCharacteristic[] = []; + if (chars != null) { + const characteristicsList = chars; + const size = characteristicsList.size; + const bleService: BleService = { + uuid: serviceId, + isPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY + }; + for (let i = 0 as Int; i < size; i++) { + const char = characteristicsList != null ? characteristicsList.get(i as Int) : characteristicsList[i]; + if (char != null) { + const props = char.getProperties(); + try { + const charUuid = char.getUuid() != null ? char.getUuid().toString() : ''; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:362', '[ServiceManager] characteristic uuid=', charUuid); + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:363', '[ServiceManager] failed to read char uuid', e); + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:364', props); + const bleCharacteristic: BleCharacteristic = { + uuid: char.getUuid().toString(), + service: bleService, + properties: createCharProperties(props) + }; + result.push(bleCharacteristic); + } + } + } + callback(result, null); + } + public async readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|read`; + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:385', key); + return new Promise((resolve, reject) => { + const timer = setTimeout(() => { + pendingCallbacks.delete(key); + reject(new AkBleErrorImpl(AkBluetoothErrorCode.ConnectionTimeout, "Connection timeout", "")); + }, 5000); + const resolveAdapter = (data: any) => { __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:391', 'read resolve:', data); resolve(data as ArrayBuffer); }; + const rejectAdapter = (err?: any) => { reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")); }; + pendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)); + if (gatt.readCharacteristic(char) == false) { + clearTimeout(timer); + pendingCallbacks.delete(key); + reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Unknown error occurred", "")); + } + else { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:400', 'read should be succeed', key); + } + }); + } + public async writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, data: Uint8Array, options?: WriteCharacteristicOptions): Promise { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:406', '[writeCharacteristic] deviceId:', deviceId, 'serviceId:', serviceId, 'characteristicId:', characteristicId, 'data:', data); + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:409', '[writeCharacteristic] gatt is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + } + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:414', '[writeCharacteristic] service is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + } + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:419', '[writeCharacteristic] characteristic is null'); + throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + } + const key = `${deviceId}|${serviceId}|${characteristicId}|write`; + const wantsNoResponse = options != null && options.waitForResponse == false; + let retryMaxAttempts = 20; + let retryDelay = 100; + let giveupTimeout = 20000; + if (options != null) { + try { + if (options.maxAttempts != null) { + const parsedAttempts = Math.floor(options.maxAttempts as number); + if (!isNaN(parsedAttempts) && parsedAttempts > 0) + retryMaxAttempts = parsedAttempts; + } + } + catch (e: any) { } + try { + if (options.retryDelayMs != null) { + const parsedDelay = Math.floor(options.retryDelayMs as number); + if (!isNaN(parsedDelay) && parsedDelay >= 0) + retryDelay = parsedDelay; + } + } + catch (e: any) { } + try { + if (options.giveupTimeoutMs != null) { + const parsedGiveup = Math.floor(options.giveupTimeoutMs as number); + if (!isNaN(parsedGiveup) && parsedGiveup > 0) + giveupTimeout = parsedGiveup; + } + } + catch (e: any) { } + } + const gattInstance = gatt; + const executeWrite = (): Promise => { + return new Promise((resolve, _reject) => { + const initialTimeout = Math.max(giveupTimeout + 5000, 10000); + let timer = setTimeout(() => { + pendingCallbacks.delete(key); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:454', '[writeCharacteristic] timeout'); + resolve(false); + }, initialTimeout); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:457', '[writeCharacteristic] initial timeout set to', initialTimeout, 'ms for', key); + const resolveAdapter = (data: any) => { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:459', '[writeCharacteristic] resolveAdapter called'); + resolve(true); + }; + const rejectAdapter = (err?: any) => { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:463', '[writeCharacteristic] rejectAdapter called', err); + resolve(false); + }; + pendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer)); + const byteArray = new ByteArray(data.length as Int); + for (let i = 0 as Int; i < data.length; i++) { + byteArray[i] = data[i].toByte(); + } + const forceWriteTypeNoResponse = options != null && options.forceWriteTypeNoResponse == true; + let usesNoResponse = forceWriteTypeNoResponse || wantsNoResponse; + try { + const props = char.getProperties(); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:475', '[writeCharacteristic] characteristic properties mask=', props); + if (usesNoResponse == false) { + const supportsWriteWithResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0; + const supportsWriteNoResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0; + if (supportsWriteWithResponse == false && supportsWriteNoResponse == true) { + usesNoResponse = true; + } + } + if (usesNoResponse) { + try { + char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_NO_RESPONSE); + } + catch (e: any) { } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:485', '[writeCharacteristic] using WRITE_TYPE_NO_RESPONSE'); + } + else { + try { + char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT); + } + catch (e: any) { } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:488', '[writeCharacteristic] using WRITE_TYPE_DEFAULT'); + } + } + catch (e: any) { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:491', '[writeCharacteristic] failed to inspect/set write type', e); + } + const maxAttempts = retryMaxAttempts; + function attemptWrite(att: Int): void { + try { + let setOk = true; + try { + const setRes = char.setValue(byteArray); + if (typeof setRes == 'boolean' && setRes == false) { + setOk = false; + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:501', '[writeCharacteristic] setValue returned false for', key, 'attempt', att); + } + } + catch (e: any) { + setOk = false; + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:505', '[writeCharacteristic] setValue threw for', key, 'attempt', att, e); + } + if (setOk == false) { + if (att >= maxAttempts) { + try { + clearTimeout(timer); + } + catch (e: any) { } + pendingCallbacks.delete(key); + resolve(false); + return; + } + setTimeout(() => { attemptWrite((att + 1) as Int); }, retryDelay); + return; + } + try { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:518', '[writeCharacteristic] attempt', att, 'calling gatt.writeCharacteristic'); + const r = gattInstance.writeCharacteristic(char); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:520', '[writeCharacteristic] attempt', att, 'result=', r); + if (r == true) { + if (usesNoResponse) { + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:523', '[writeCharacteristic] WRITE_TYPE_NO_RESPONSE success for', key); + try { + clearTimeout(timer); + } + catch (e: any) { } + pendingCallbacks.delete(key); + resolve(true); + return; + } + try { + clearTimeout(timer); + } + catch (e: any) { } + const extra = 20000; + timer = setTimeout(() => { + pendingCallbacks.delete(key); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:533', '[writeCharacteristic] timeout after write initiated'); + resolve(false); + }, extra); + const pendingEntry = pendingCallbacks.get(key); + if (pendingEntry != null) + pendingEntry.timer = timer; + return; + } + } + catch (e: any) { + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:541', '[writeCharacteristic] attempt', att, 'exception when calling writeCharacteristic', e); + } + if (att < maxAttempts) { + const nextAtt = (att + 1) as Int; + setTimeout(() => { attemptWrite(nextAtt); }, retryDelay); + return; + } + if (usesNoResponse) { + try { + clearTimeout(timer); + } + catch (e: any) { } + pendingCallbacks.delete(key); + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:551', '[writeCharacteristic] all attempts failed with WRITE_NO_RESPONSE for', key); + resolve(false); + return; + } + try { + clearTimeout(timer); + } + catch (e: any) { } + const giveupTimeoutLocal = giveupTimeout; + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:557', '[writeCharacteristic] all attempts failed; waiting for late callback up to', giveupTimeoutLocal, 'ms for', key); + const giveupTimer = setTimeout(() => { + pendingCallbacks.delete(key); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:560', '[writeCharacteristic] giveup timeout expired for', key); + resolve(false); + }, giveupTimeoutLocal); + const pendingEntryAfter = pendingCallbacks.get(key); + if (pendingEntryAfter != null) + pendingEntryAfter.timer = giveupTimer; + } + catch (e: any) { + clearTimeout(timer); + pendingCallbacks.delete(key); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:568', '[writeCharacteristic] Exception in attemptWrite', e); + resolve(false); + } + } + try { + attemptWrite(1 as Int); + } + catch (e: any) { + clearTimeout(timer); + pendingCallbacks.delete(key); + __f__('error', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:578', '[writeCharacteristic] Exception before attempting write', e); + resolve(false); + } + }); + }; + return enqueueDeviceWrite(deviceId, executeWrite); + } + public async subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, onData: BleDataReceivedCallback): Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|notify`; + notifyCallbacks.set(key, onData); + if (gatt.setCharacteristicNotification(char, true) == false) { + notifyCallbacks.delete(key); + throw new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", ""); + } + else { + // 写入 CCCD 描述符,启用 notify + const descriptor = char.getDescriptor(UUID.fromString("00002902-0000-1000-8000-00805f9b34fb")); + if (descriptor != null) { + // 设置描述符值 + const value = BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE; + descriptor.setValue(value); + const writedescript = gatt.writeDescriptor(descriptor); + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:608', 'subscribeCharacteristic: CCCD written for notify', writedescript); + } + else { + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:610', 'subscribeCharacteristic: CCCD descriptor not found!'); + } + __f__('log', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:612', 'subscribeCharacteristic ok!!'); + } + } + public async unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { + const gatt = this.deviceManager.getGattInstance(deviceId); + if (gatt == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, "Device not found", ""); + const service = gatt.getService(UUID.fromString(serviceId)); + if (service == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, "Service not found", ""); + const char = service.getCharacteristic(UUID.fromString(characteristicId)); + if (char == null) + throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, "Characteristic not found", ""); + const key = `${deviceId}|${serviceId}|${characteristicId}|notify`; + notifyCallbacks.delete(key); + if (gatt.setCharacteristicNotification(char, false) == false) { + throw new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, "Failed to unsubscribe characteristic", ""); + } + } + // 自动发现所有服务和特征 + public async autoDiscoverAll(deviceId: string): Promise { + const services = await this.getServices(deviceId, null) as BleService[]; + const allCharacteristics: BleCharacteristic[] = []; + for (const service of services) { + await new Promise((resolve, reject) => { + this.getCharacteristics(deviceId, service.uuid, (chars, err) => { + if (err != null) + reject(err); + else { + if (chars != null) + allCharacteristics.push(...chars); + resolve(void 0); + } + }); + }); + } + return { services, characteristics: allCharacteristics } as AutoDiscoverAllResult; + } + // 自动订阅所有支持 notify/indicate 的特征 + public async subscribeAllNotifications(deviceId: string, onData: BleDataReceivedCallback): Promise { + const { services, characteristics } = await this.autoDiscoverAll(deviceId); + for (const char of characteristics) { + if (char.properties.notify || char.properties.indicate) { + try { + await this.subscribeCharacteristic(deviceId, char.service.uuid, char.uuid, onData); + } + catch (e: any) { + // 可以选择忽略单个特征订阅失败 + __f__('warn', 'at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:658', `订阅特征 ${char.uuid} 失败:`, e); + } + } + } + } +} +//# sourceMappingURL=service_manager.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts.map new file mode 100644 index 0000000..e173886 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"service_manager.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts"],"names":[],"mappings":"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","sourcesContent":["import type { BleService, BleCharacteristic, BleDataReceivedCallback, BleCharacteristicProperties, WriteCharacteristicOptions, ByteArray } from '../interface.uts'\r\nimport BluetoothGatt from \"android.bluetooth.BluetoothGatt\";\r\nimport BluetoothGattService from \"android.bluetooth.BluetoothGattService\";\r\nimport BluetoothGattCharacteristic from \"android.bluetooth.BluetoothGattCharacteristic\";\r\nimport BluetoothGattDescriptor from \"android.bluetooth.BluetoothGattDescriptor\";\r\nimport BluetoothGattCallback from \"android.bluetooth.BluetoothGattCallback\";\r\n\r\nimport UUID from \"java.util.UUID\";\r\nimport { DeviceManager } from './device_manager.uts'\r\nimport { AkBleErrorImpl, AkBluetoothErrorCode } from '../unierror.uts'\r\nimport { AutoDiscoverAllResult } from '../interface.uts'\r\n\r\n\r\n\r\n\r\n// 补全UUID格式,将短格式转换为标准格式\r\nfunction getFullUuid(shortUuid : string) : string {\r\n\treturn `0000${shortUuid}-0000-1000-8000-00805f9b34fb`\r\n}\r\n\r\n\r\nconst deviceWriteQueues = new Map>();\r\n\r\nfunction enqueueDeviceWrite(deviceId : string, work : () => Promise) : Promise {\r\n\tconst previous = deviceWriteQueues.get(deviceId) ?? Promise.resolve();\r\n\tconst next = (async () : Promise => {\r\n\t\ttry {\r\n\t\t\tawait previous;\r\n\t\t} catch (e) { /* ignore previous rejection to keep queue alive */ }\r\n\t\treturn await work();\r\n\t})();\r\n\tconst queued = next.then(() => { }, () => { });\r\n\tdeviceWriteQueues.set(deviceId, queued);\r\n\treturn next.finally(() => {\r\n\t\tif (deviceWriteQueues.get(deviceId) == queued) {\r\n\t\t\tdeviceWriteQueues.delete(deviceId);\r\n\t\t}\r\n\t});\r\n}\r\n\r\n\r\n\r\nfunction createCharProperties(props : number) : BleCharacteristicProperties {\r\n\tconst result : BleCharacteristicProperties = {\r\n\t\tread: false,\r\n\t\twrite: false,\r\n\t\tnotify: false,\r\n\t\tindicate: false,\r\n\t\tcanRead: false,\r\n\t\tcanWrite: false,\r\n\t\tcanNotify: false,\r\n\t\twriteWithoutResponse: false\r\n\t};\r\n\tresult.read = (props & BluetoothGattCharacteristic.PROPERTY_READ) !== 0;\r\n\tresult.write = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0;\r\n\tresult.notify = (props & BluetoothGattCharacteristic.PROPERTY_NOTIFY) !== 0;\r\n\tresult.indicate = (props & BluetoothGattCharacteristic.PROPERTY_INDICATE) !== 0;\r\n\tresult.writeWithoutResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0;\r\n\r\n\tresult.canRead = result.read;\r\n\tconst writeWithoutResponse = result.writeWithoutResponse;\r\n\tresult.canWrite = (result.write != null && result.write) || (writeWithoutResponse != null && writeWithoutResponse);\r\n\tresult.canNotify = result.notify;\r\n\treturn result;\r\n}\r\n\r\n// 定义 PendingCallback 类型和实现类\r\ninterface PendingCallback {\r\n\tresolve : (data : any) => void;\r\n\treject : (err ?: any) => void;\r\n\ttimer ?: number; // Changed from any to number\r\n}\r\n\r\nclass PendingCallbackImpl implements PendingCallback {\r\n\tresolve : (data : any) => void;\r\n\treject : (err ?: any) => void;\r\n\ttimer ?: number; // Changed from any to number\r\n\r\n\tconstructor(resolve : (data : any) => void, reject : (err ?: any) => void, timer ?: number) {\r\n\t\tthis.resolve = resolve;\r\n\t\tthis.reject = reject;\r\n\t\tthis.timer = timer;\r\n\t}\r\n}\r\n\r\n// 全局回调管理(必须在类外部声明)\r\nlet pendingCallbacks : Map;\r\nlet notifyCallbacks : Map;\r\n\r\n// 在全局范围内初始化\r\npendingCallbacks = new Map();\r\nnotifyCallbacks = new Map();\r\n\r\n// 服务发现等待队列:deviceId -> 回调数组\r\nconst serviceDiscoveryWaiters = new Map void)[]>();\r\n// 服务发现状态:deviceId -> 是否已发现\r\nconst serviceDiscovered = new Map();\r\n\r\n// 特征发现等待队列:deviceId|serviceId -> 回调数组\r\nconst characteristicDiscoveryWaiters = new Map void)[]>();\r\n\r\nclass GattCallback extends BluetoothGattCallback {\r\n\tconstructor() {\r\n\t\tsuper();\r\n\t}\r\n\r\n\toverride onServicesDiscovered(gatt : BluetoothGatt, status : Int) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:108','ak onServicesDiscovered')\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tif (status == BluetoothGatt.GATT_SUCCESS) {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:111',`服务发现成功: ${deviceId}`);\r\n\t\t\tserviceDiscovered.set(deviceId, true);\r\n\t\t\t// 统一回调所有等待 getServices 的调用\r\n\t\t\tconst waiters = serviceDiscoveryWaiters.get(deviceId);\r\n\t\t\tif (waiters != null && waiters.length > 0) {\r\n\t\t\t\tconst services = gatt.getServices();\r\n\t\t\t\tconst result : BleService[] = [];\r\n\t\t\t\tif (services != null) {\r\n\t\t\t\t\tconst servicesList = services;\r\n\t\t\t\t\tconst size = servicesList.size;\r\n\t\t\t\t\tfor (let i = 0; i < size; i++) {\r\n\t\tconst service = servicesList.get(i as Int);\r\n\t\t\t\t\t\tif (service != null) {\r\n\t\t\t\t\t\t\tconst bleService : BleService = {\r\n\t\t\t\t\t\t\t\tuuid: service.getUuid().toString(),\r\n\t\t\t\t\t\t\t\tisPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY\r\n\t\t\t\t\t\t\t};\r\n\t\t\t\t\t\t\tresult.push(bleService);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\tfor (let i = 0; i < waiters.length; i++) {\r\n\t\t\t\t\tconst cb = waiters[i];\r\n\t\t\t\t\tif (cb != null) { cb(result, null); }\r\n\t\t\t\t}\r\n\t\t\t\tserviceDiscoveryWaiters.delete(deviceId);\r\n\t\t\t}\r\n\t\t} else {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:139',`服务发现失败: ${deviceId}, status: ${status}`);\r\n\t\t\t// 失败时也要通知等待队列\r\n\t\t\tconst waiters = serviceDiscoveryWaiters.get(deviceId);\r\n\t\t\tif (waiters != null && waiters.length > 0) {\r\n\t\t\t\tfor (let i = 0; i < waiters.length; i++) {\r\n\t\t\t\t\tconst cb = waiters[i];\r\n\t\t\t\t\tif (cb != null) { cb(null, new Error('服务发现失败')); }\r\n\t\t\t\t}\r\n\t\t\t\tserviceDiscoveryWaiters.delete(deviceId);\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\toverride onConnectionStateChange(gatt : BluetoothGatt, status : Int, newState : Int) : void {\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\tif (newState == BluetoothGatt.STATE_CONNECTED) {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:154',`设备已连接: ${deviceId}`);\r\n\t\t\tDeviceManager.handleConnectionStateChange(deviceId, 2, null); // 2 = STATE_CONNECTED\r\n\t} else if (newState == BluetoothGatt.STATE_DISCONNECTED) {\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:157',`设备已断开: ${deviceId}`);\r\n\t\t\tserviceDiscovered.delete(deviceId);\r\n\t\t\tDeviceManager.handleConnectionStateChange(deviceId, 0, null); // 0 = STATE_DISCONNECTED\r\n\t\t}\r\n\t}\r\n\t\toverride onCharacteristicChanged(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:163','ak onCharacteristicChanged')\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tconst serviceId = characteristic.getService().getUuid().toString();\r\n\t\tconst charId = characteristic.getUuid().toString();\r\n\t\tconst key = `${deviceId}|${serviceId}|${charId}|notify`;\r\n\t\tconst callback = notifyCallbacks.get(key);\r\n\t\tconst value = characteristic.getValue();\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:170','[onCharacteristicChanged]', key, value);\r\n\t\tif (callback != null && value != null) {\r\n\t\t\tconst valueLength = value.size;\r\n\t\t\tconst arr = new Uint8Array(valueLength);\r\n\t\t\tfor (let i = 0 as Int; i < valueLength; i++) {\r\n\t\t\t\tconst v = value[i as Int];\r\n\t\t\t\tarr[i] = v != null ? v : 0;\r\n\t\t\t}\r\n\t\t\t// 保存接收日志\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:179',`\r\n INSERT INTO ble_data_log (device_id, service_id, char_id, direction, data, timestamp)\r\n VALUES ('${deviceId}', '${serviceId}', '${charId}', 'recv', '${Array.from(arr).join(',')}', ${Date.now()})\r\n `)\r\n\r\n\t\t\tcallback(arr);\r\n\t\t}\r\n\t}\r\n\t\toverride onCharacteristicRead(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:188','ak onCharacteristicRead', status)\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tconst serviceId = characteristic.getService().getUuid().toString();\r\n\t\tconst charId = characteristic.getUuid().toString();\r\n\t\tconst key = `${deviceId}|${serviceId}|${charId}|read`;\r\n\t\tconst pending = pendingCallbacks.get(key);\r\n\t\tconst value = characteristic.getValue();\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:195','[onCharacteristicRead]', key, 'status=', status, 'value=', value);\r\n\t\tif (pending != null) {\r\n\t\t\ttry {\r\n\t\t\t\tconst timer = pending.timer;\r\n\t\t\t\tif (timer != null) {\r\n\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t\tpending.timer = null;\r\n\t\t\t\t}\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\tif (status == BluetoothGatt.GATT_SUCCESS && value != null) {\r\n\t\t\t\t\tconst valueLength = value.size\r\n\t\t\t\t\tconst arr = new Uint8Array(valueLength);\r\n\t\t\t\t\tfor (let i = 0 as Int; i < valueLength; i++) {\r\n\t\t\t\t\t\tconst v = value[i as Int];\r\n\t\t\t\t\t\tarr[i] = v != null ? v : 0;\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\t// resolve with ArrayBuffer\r\n\t\t\t\t\tpending.resolve(arr.buffer as ArrayBuffer);\r\n\t\t\t\t} else {\r\n\t\t\t\t\tpending.reject(new Error('Characteristic read failed'));\r\n\t\t\t\t}\r\n\t\t\t} catch (e) {\r\n\t\t\t\ttry { pending.reject(e); } catch (e2) { __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:218',e2); }\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\toverride onCharacteristicWrite(gatt : BluetoothGatt, characteristic : BluetoothGattCharacteristic, status : Int) : void {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:224','ak onCharacteristicWrite', status)\r\n\t\tconst deviceId = gatt.getDevice().getAddress();\r\n\t\tconst serviceId = characteristic.getService().getUuid().toString();\r\n\t\tconst charId = characteristic.getUuid().toString();\r\n\t\tconst key = `${deviceId}|${serviceId}|${charId}|write`;\r\n\t\tconst pending = pendingCallbacks.get(key);\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:230','[onCharacteristicWrite]', key, 'status=', status);\r\n\t\tif (pending != null) {\r\n\t\t\ttry {\r\n\t\t\t\tconst timer = pending.timer;\r\n\t\t\t\tif (timer != null) {\r\n\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t}\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\tif (status == BluetoothGatt.GATT_SUCCESS) {\r\n\t\t\t\t\tpending.resolve('ok');\r\n\t\t\t\t} else {\r\n\t\t\t\t\tpending.reject(new Error('Characteristic write failed'));\r\n\t\t\t\t}\r\n\t\t\t} catch (e) {\r\n\t\t\t\ttry { pending.reject(e); } catch (e2) { __f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:244',e2); }\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n}\r\n\r\n// 导出单例实例供外部使用\r\nexport const gattCallback = new GattCallback();\r\n\r\nexport class ServiceManager {\r\n\tprivate static instance : ServiceManager | null = null;\r\n\tprivate services = new Map();\r\n\tprivate characteristics = new Map>();\r\n\tprivate deviceManager = DeviceManager.getInstance();\r\n\tprivate constructor() { }\r\n\tstatic getInstance() : ServiceManager {\r\n\t\tif (ServiceManager.instance == null) {\r\n\t\t\tServiceManager.instance = new ServiceManager();\r\n\t\t}\r\n\t\treturn ServiceManager.instance!;\r\n\t}\r\n\r\n\tgetServices(deviceId : string, callback ?: (services : BleService[] | null, error ?: Error) => void) : any | Promise {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:267','ak start getservice', deviceId);\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) {\r\n\t\t\tif (callback != null) { callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\")); }\r\n\t\t\treturn Promise.reject(new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\"));\r\n\t\t}\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:273','ak serviceDiscovered', gatt)\r\n\t\t// 如果服务已发现,直接返回\r\n\t\tif (serviceDiscovered.get(deviceId) == true) {\r\n\t\t\tconst services = gatt.getServices();\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:277',services)\r\n\t\t\tconst result : BleService[] = [];\r\n\t\t\tif (services != null) {\r\n\t\t\t\tconst servicesList = services;\r\n\t\t\t\tconst size = servicesList.size;\r\n\t\t\t\tif (size > 0) {\r\n\t\t\tfor (let i = 0 as Int; i < size; i++) {\r\n\t\t\t\tconst service = servicesList != null ? servicesList.get(i) : servicesList[i];\r\n\t\t\t\t\t\tif (service != null) {\r\n\t\t\t\t\t\t\tconst bleService : BleService = {\r\n\t\t\t\t\t\t\t\tuuid: service.getUuid().toString(),\r\n\t\t\t\t\t\t\t\tisPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY\r\n\t\t\t\t\t\t\t};\r\n\t\t\t\t\t\t\tresult.push(bleService);\r\n\r\n\t\t\t\t\t\t\tif (bleService.uuid == getFullUuid('0001')) {\r\n\t\t\t\t\t\t\t\tconst device = this.deviceManager.getDevice(deviceId);\r\n\t\t\t\t\t\t\t\tif (device != null) {\r\n\t\t\t\t\t\t\t\t\tdevice.serviceId = bleService.uuid;\r\n\t\t\t\t\t\t\t\t\tthis.getCharacteristics(deviceId, device.serviceId, (chars, err) => {\r\n\t\t\t\t\t\t\t\t\t\tif (err == null && chars != null) {\r\n\t\t\t\t\t\t\t\t\t\t\tconst writeChar = chars.find(c => c.uuid == getFullUuid('0010'));\r\n\t\t\t\t\t\t\t\t\t\t\tconst notifyChar = chars.find(c => c.uuid == getFullUuid('0011'));\r\n\t\t\t\t\t\t\t\t\t\t\tif (writeChar != null) device.writeCharId = writeChar.uuid;\r\n\t\t\t\t\t\t\t\t\t\t\tif (notifyChar != null) device.notifyCharId = notifyChar.uuid;\r\n\t\t\t\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\t\t\t});\r\n\t\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tif (callback != null) { callback(result, null); }\r\n\t\t\treturn Promise.resolve(result);\r\n\t\t}\r\n\t\t// 未发现则发起服务发现并加入等待队列\r\n\t\tif (!serviceDiscoveryWaiters.has(deviceId)) {\r\n\t\t\tserviceDiscoveryWaiters.set(deviceId, []);\r\n\t\t\tgatt.discoverServices();\r\n\t\t}\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\tconst cb = (services : BleService[] | null, error ?: Error) => {\r\n\t\t\t\tif (error != null) reject(error);\r\n\t\t\t\telse resolve(services ?? []);\r\n\t\t\t\tif (callback != null) callback(services, error);\r\n\t\t\t};\r\n\t\t\tconst arr = serviceDiscoveryWaiters.get(deviceId);\r\n\t\t\tif (arr != null) arr.push(cb);\r\n\t\t});\r\n\t}\r\n\tgetCharacteristics(deviceId : string, serviceId : string, callback : (characteristics : BleCharacteristic[] | null, error ?: Error) => void) : void {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\"));\r\n\t\t// 如果服务还没发现,等待服务发现后再查特征\r\n\t\tif (serviceDiscovered.get(deviceId) !== true) {\r\n\t\t\t// 先注册到服务发现等待队列\r\n\t\t\tthis.getServices(deviceId, (services, err) => {\r\n\t\t\t\tif (err != null) {\r\n\t\t\t\t\tcallback(null, err);\r\n\t\t\t\t} else {\r\n\t\t\t\t\tthis.getCharacteristics(deviceId, serviceId, callback);\r\n\t\t\t\t}\r\n\t\t\t});\r\n\t\t\treturn;\r\n\t\t}\r\n\t\t// 服务已发现,正常获取特征\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) return callback(null, new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\"));\r\n\t\tconst chars = service.getCharacteristics();\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:347',chars)\r\n\t\tconst result : BleCharacteristic[] = [];\r\n\t\tif (chars != null) {\r\n\t\t\tconst characteristicsList = chars;\r\n\t\t\tconst size = characteristicsList.size;\r\n\t\t\tconst bleService : BleService = {\r\n\t\t\t\tuuid: serviceId,\r\n\t\t\t\tisPrimary: service.getType() == BluetoothGattService.SERVICE_TYPE_PRIMARY\r\n\t\t\t};\r\n\t\t\tfor (let i = 0 as Int; i < size; i++) {\r\n\t\t\t\tconst char = characteristicsList != null ? characteristicsList.get(i as Int) : characteristicsList[i];\r\n\t\t\t\tif (char != null) {\r\n\t\t\t\t\tconst props = char.getProperties();\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tconst charUuid = char.getUuid() != null ? char.getUuid().toString() : '';\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:362','[ServiceManager] characteristic uuid=', charUuid);\r\n\t\t\t\t\t} catch (e) { __f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:363','[ServiceManager] failed to read char uuid', e); }\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:364',props);\r\n\t\t\t\t\tconst bleCharacteristic : BleCharacteristic = {\r\n\t\t\t\t\t\tuuid: char.getUuid().toString(),\r\n\t\t\t\t\t\tservice: bleService,\r\n\t\t\t\t\t\tproperties: createCharProperties(props)\r\n\t\t\t\t\t};\r\n\t\t\t\t\tresult.push(bleCharacteristic);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t\tcallback(result, null);\r\n\t}\r\n\r\n\tpublic async readCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|read`;\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:385',key)\r\n\t\treturn new Promise((resolve, reject) => {\r\n\t\t\tconst timer = setTimeout(() => {\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\treject(new AkBleErrorImpl(AkBluetoothErrorCode.ConnectionTimeout, \"Connection timeout\", \"\"));\r\n\t\t\t}, 5000);\r\n\t\t\tconst resolveAdapter = (data : any) => { __f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:391','read resolve:', data); resolve(data as ArrayBuffer); };\r\n\t\t\tconst rejectAdapter = (err ?: any) => { reject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Unknown error occurred\", \"\")); };\r\n\t\t\tpendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer));\r\n\t\t\tif (gatt.readCharacteristic(char) == false) {\r\n\t\t\t\tclearTimeout(timer);\r\n\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\treject(new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Unknown error occurred\", \"\"));\r\n\t\t\t}\r\n\t\t\telse {\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:400','read should be succeed', key)\r\n\t\t\t}\r\n\t\t});\r\n\t}\r\n\r\n\tpublic async writeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, data : Uint8Array, options ?: WriteCharacteristicOptions) : Promise {\r\n\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:406','[writeCharacteristic] deviceId:', deviceId, 'serviceId:', serviceId, 'characteristicId:', characteristicId, 'data:', data);\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) {\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:409','[writeCharacteristic] gatt is null');\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\t}\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) {\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:414','[writeCharacteristic] service is null');\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\t}\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) {\r\n\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:419','[writeCharacteristic] characteristic is null');\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\t}\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|write`;\r\n\t\tconst wantsNoResponse = options != null && options.waitForResponse == false;\r\n\t\tlet retryMaxAttempts = 20;\r\n\t\tlet retryDelay = 100;\r\n\t\tlet giveupTimeout = 20000;\r\n\t\tif (options != null) {\r\n\t\t\ttry {\r\n\t\t\t\tif (options.maxAttempts != null) {\r\n\t\t\t\t\tconst parsedAttempts = Math.floor(options.maxAttempts as number);\r\n\t\t\t\t\tif (!isNaN(parsedAttempts) && parsedAttempts > 0) retryMaxAttempts = parsedAttempts;\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t\ttry {\r\n\t\t\t\tif (options.retryDelayMs != null) {\r\n\t\t\t\t\tconst parsedDelay = Math.floor(options.retryDelayMs as number);\r\n\t\t\t\t\tif (!isNaN(parsedDelay) && parsedDelay >= 0) retryDelay = parsedDelay;\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t\ttry {\r\n\t\t\t\tif (options.giveupTimeoutMs != null) {\r\n\t\t\t\t\tconst parsedGiveup = Math.floor(options.giveupTimeoutMs as number);\r\n\t\t\t\t\tif (!isNaN(parsedGiveup) && parsedGiveup > 0) giveupTimeout = parsedGiveup;\r\n\t\t\t\t}\r\n\t\t\t} catch (e) { }\r\n\t\t}\r\n\t\tconst gattInstance = gatt;\r\n\t\tconst executeWrite = () : Promise => {\r\n\r\n\t\t\treturn new Promise((resolve) => {\r\n\t\t\t\tconst initialTimeout = Math.max(giveupTimeout + 5000, 10000);\r\n\t\t\t\tlet timer = setTimeout(() => {\r\n\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:454','[writeCharacteristic] timeout');\r\n\t\t\t\t\tresolve(false);\r\n\t\t\t\t}, initialTimeout);\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:457','[writeCharacteristic] initial timeout set to', initialTimeout, 'ms for', key);\r\n\t\t\t\tconst resolveAdapter = (data : any) => {\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:459','[writeCharacteristic] resolveAdapter called');\r\n\t\t\t\t\tresolve(true);\r\n\t\t\t\t};\r\n\t\t\t\tconst rejectAdapter = (err ?: any) => {\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:463','[writeCharacteristic] rejectAdapter called', err);\r\n\t\t\t\t\tresolve(false);\r\n\t\t\t\t};\r\n\t\t\t\tpendingCallbacks.set(key, new PendingCallbackImpl(resolveAdapter, rejectAdapter, timer));\r\n\t\t\t\tconst byteArray = new ByteArray(data.length as Int);\r\n\t\t\t\tfor (let i = 0 as Int; i < data.length; i++) {\r\n\t\t\t\t\tbyteArray[i] = data[i].toByte();\r\n\t\t\t\t}\r\n\t\t\t\tconst forceWriteTypeNoResponse = options != null && options.forceWriteTypeNoResponse == true;\r\n\t\t\t\tlet usesNoResponse = forceWriteTypeNoResponse || wantsNoResponse;\r\n\t\t\t\ttry {\r\n\t\t\t\t\tconst props = char.getProperties();\r\n\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:475','[writeCharacteristic] characteristic properties mask=', props);\r\n\t\t\t\t\tif (usesNoResponse == false) {\r\n\t\t\t\t\t\tconst supportsWriteWithResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE) !== 0;\r\n\t\t\t\t\t\tconst supportsWriteNoResponse = (props & BluetoothGattCharacteristic.PROPERTY_WRITE_NO_RESPONSE) !== 0;\r\n\t\t\t\t\t\tif (supportsWriteWithResponse == false && supportsWriteNoResponse == true) {\r\n\t\t\t\t\t\t\tusesNoResponse = true;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (usesNoResponse) {\r\n\t\t\t\t\t\ttry { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_NO_RESPONSE); } catch (e) { }\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:485','[writeCharacteristic] using WRITE_TYPE_NO_RESPONSE');\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\ttry { char.setWriteType(BluetoothGattCharacteristic.WRITE_TYPE_DEFAULT); } catch (e) { }\r\n\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:488','[writeCharacteristic] using WRITE_TYPE_DEFAULT');\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:491','[writeCharacteristic] failed to inspect/set write type', e);\r\n\t\t\t\t}\r\n\t\t\t\tconst maxAttempts = retryMaxAttempts;\r\n\t\t\t\tfunction attemptWrite(att : Int) : void {\r\n\t\t\t\t\ttry {\r\n\t\t\t\t\t\tlet setOk = true;\r\n\t\t\t\t\t\ttry {\r\n\t\t\t\t\t\t\tconst setRes = char.setValue(byteArray);\r\n\t\t\t\t\t\t\tif (typeof setRes == 'boolean' && setRes == false) {\r\n\t\t\t\t\t\t\t\tsetOk = false;\r\n\t\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:501','[writeCharacteristic] setValue returned false for', key, 'attempt', att);\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\t\tsetOk = false;\r\n\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:505','[writeCharacteristic] setValue threw for', key, 'attempt', att, e);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (setOk == false) {\r\n\t\t\t\t\t\t\tif (att >= maxAttempts) {\r\n\t\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\tsetTimeout(() => { attemptWrite((att + 1) as Int); }, retryDelay);\r\n\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\ttry {\r\n\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:518','[writeCharacteristic] attempt', att, 'calling gatt.writeCharacteristic');\r\n\t\t\t\t\t\t\tconst r = gattInstance.writeCharacteristic(char);\r\n\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:520','[writeCharacteristic] attempt', att, 'result=', r);\r\n\t\t\t\t\t\t\tif (r == true) {\r\n\t\t\t\t\t\t\t\tif (usesNoResponse) {\r\n\t\t\t\t\t\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:523','[writeCharacteristic] WRITE_TYPE_NO_RESPONSE success for', key);\r\n\t\t\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t\t\tresolve(true);\r\n\t\t\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\t\tconst extra = 20000;\r\n\t\t\t\t\t\t\t\ttimer = setTimeout(() => {\r\n\t\t\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:533','[writeCharacteristic] timeout after write initiated');\r\n\t\t\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t\t\t}, extra);\r\n\t\t\t\t\t\t\t\tconst pendingEntry = pendingCallbacks.get(key);\r\n\t\t\t\t\t\t\t\tif (pendingEntry != null) pendingEntry.timer = timer;\r\n\t\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:541','[writeCharacteristic] attempt', att, 'exception when calling writeCharacteristic', e);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (att < maxAttempts) {\r\n\t\t\t\t\t\t\tconst nextAtt = (att + 1) as Int;\r\n\t\t\t\t\t\t\tsetTimeout(() => { attemptWrite(nextAtt); }, retryDelay);\r\n\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (usesNoResponse) {\r\n\t\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:551','[writeCharacteristic] all attempts failed with WRITE_NO_RESPONSE for', key);\r\n\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t\treturn;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\ttry { clearTimeout(timer); } catch (e) { }\r\n\t\t\t\t\t\tconst giveupTimeoutLocal = giveupTimeout;\r\n\t\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:557','[writeCharacteristic] all attempts failed; waiting for late callback up to', giveupTimeoutLocal, 'ms for', key);\r\n\t\t\t\t\t\tconst giveupTimer = setTimeout(() => {\r\n\t\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:560','[writeCharacteristic] giveup timeout expired for', key);\r\n\t\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t\t}, giveupTimeoutLocal);\r\n\t\t\t\t\t\tconst pendingEntryAfter = pendingCallbacks.get(key);\r\n\t\t\t\t\t\tif (pendingEntryAfter != null) pendingEntryAfter.timer = giveupTimer;\r\n\t\t\t\t\t} catch (e) {\r\n\t\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:568','[writeCharacteristic] Exception in attemptWrite', e);\r\n\t\t\t\t\t\tresolve(false);\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\r\n\t\t\t\ttry {\r\n\t\t\t\t\tattemptWrite(1 as Int);\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\tclearTimeout(timer);\r\n\t\t\t\t\tpendingCallbacks.delete(key);\r\n\t\t\t\t\t__f__('error','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:578','[writeCharacteristic] Exception before attempting write', e);\r\n\t\t\t\t\tresolve(false);\r\n\t\t\t\t}\r\n\t\t\t});\r\n\t\t};\r\n\t\treturn enqueueDeviceWrite(deviceId, executeWrite);\r\n\t}\r\n\r\n\tpublic async subscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string, onData : BleDataReceivedCallback) : Promise {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|notify`;\r\n\t\tnotifyCallbacks.set(key, onData);\r\n\t\tif (gatt.setCharacteristicNotification(char, true) == false) {\r\n\t\t\tnotifyCallbacks.delete(key);\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Failed to unsubscribe characteristic\", \"\");\r\n\t\t} else {\r\n\t\t\t// 写入 CCCD 描述符,启用 notify\r\n\t\t\tconst descriptor = char.getDescriptor(UUID.fromString(\"00002902-0000-1000-8000-00805f9b34fb\"));\r\n\t\t\tif (descriptor != null) {\r\n\t\t\t\t// 设置描述符值\r\n\t\t\t\tconst value =\r\n\t\t\t\t\tBluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE;\r\n\r\n\t\t\t\tdescriptor.setValue(value);\r\n\t\t\t\tconst writedescript = gatt.writeDescriptor(descriptor);\r\n\t\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:608','subscribeCharacteristic: CCCD written for notify', writedescript);\r\n\t\t\t} else {\r\n\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:610','subscribeCharacteristic: CCCD descriptor not found!');\r\n\t\t\t}\r\n\t\t\t__f__('log','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:612','subscribeCharacteristic ok!!');\r\n\t\t}\r\n\t}\r\n\r\n\tpublic async unsubscribeCharacteristic(deviceId : string, serviceId : string, characteristicId : string) : Promise {\r\n\t\tconst gatt = this.deviceManager.getGattInstance(deviceId);\r\n\t\tif (gatt == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.DeviceNotFound, \"Device not found\", \"\");\r\n\t\tconst service = gatt.getService(UUID.fromString(serviceId));\r\n\t\tif (service == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.ServiceNotFound, \"Service not found\", \"\");\r\n\t\tconst char = service.getCharacteristic(UUID.fromString(characteristicId));\r\n\t\tif (char == null) throw new AkBleErrorImpl(AkBluetoothErrorCode.CharacteristicNotFound, \"Characteristic not found\", \"\");\r\n\t\tconst key = `${deviceId}|${serviceId}|${characteristicId}|notify`;\r\n\t\tnotifyCallbacks.delete(key);\r\n\t\tif (gatt.setCharacteristicNotification(char, false) == false) {\r\n\t\t\tthrow new AkBleErrorImpl(AkBluetoothErrorCode.UnknownError, \"Failed to unsubscribe characteristic\", \"\");\r\n\t\t}\r\n\t}\r\n\r\n\r\n\t// 自动发现所有服务和特征\r\n\tpublic async autoDiscoverAll(deviceId : string) : Promise {\r\n\t\tconst services = await this.getServices(deviceId, null) as BleService[];\r\n\t\tconst allCharacteristics : BleCharacteristic[] = [];\r\n\t\tfor (const service of services) {\r\n\t\t\tawait new Promise((resolve, reject) => {\r\n\t\t\t\tthis.getCharacteristics(deviceId, service.uuid, (chars, err) => {\r\n\t\t\t\t\tif (err != null) reject(err);\r\n\t\t\t\t\telse {\r\n\t\t\t\t\t\tif (chars != null) allCharacteristics.push(...chars);\r\n\t\t\t\t\t\tresolve();\r\n\t\t\t\t\t}\r\n\t\t\t\t});\r\n\t\t\t});\r\n\t\t}\r\n\t\treturn { services, characteristics: allCharacteristics };\r\n\t}\r\n\r\n\t// 自动订阅所有支持 notify/indicate 的特征\r\n\tpublic async subscribeAllNotifications(deviceId : string, onData : BleDataReceivedCallback) : Promise {\r\n\t\tconst { services, characteristics } = await this.autoDiscoverAll(deviceId);\r\n\t\tfor (const char of characteristics) {\r\n\t\t\tif (char.properties.notify || char.properties.indicate) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tawait this.subscribeCharacteristic(deviceId, char.service.uuid, char.uuid, onData);\r\n\t\t\t\t} catch (e) {\r\n\t\t\t\t\t// 可以选择忽略单个特征订阅失败\r\n\t\t\t\t\t__f__('warn','at uni_modules/ak-sbsrv/utssdk/app-android/service_manager.uts:658',`订阅特征 ${char.uuid} 失败:`, e);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n}"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts new file mode 100644 index 0000000..f08d8aa --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts @@ -0,0 +1,409 @@ +// 蓝牙相关接口和类型定义 +// 基础设备信息类型 +export type BleDeviceInfo = { + deviceId: string; + name: string; + RSSI?: number; + connected?: boolean; + // 新增 + serviceId?: string; + writeCharId?: string; + notifyCharId?: string; +}; +export type AutoDiscoverAllResult = { + services: BleService[]; + characteristics: BleCharacteristic[]; +}; +// 服务信息类型 +export type BleServiceInfo = { + uuid: string; + isPrimary: boolean; +}; +// 特征值属性类型 +export type BleCharacteristicProperties = { + read: boolean; + write: boolean; + notify: boolean; + indicate: boolean; + writeWithoutResponse?: boolean; + canRead?: boolean; + canWrite?: boolean; + canNotify?: boolean; +}; +// 特征值信息类型 +export type BleCharacteristicInfo = { + uuid: string; + serviceId: string; + properties: BleCharacteristicProperties; +}; +// 错误状态码 +export enum BleErrorCode { + UNKNOWN_ERROR = 0, + BLUETOOTH_UNAVAILABLE = 1, + PERMISSION_DENIED = 2, + DEVICE_NOT_CONNECTED = 3, + SERVICE_NOT_FOUND = 4, + CHARACTERISTIC_NOT_FOUND = 5, + OPERATION_TIMEOUT = 6 +} +// 命令类型 +export enum CommandType { + BATTERY = 1, + DEVICE_INFO = 2, + CUSTOM = 99, + TestBatteryLevel = 0x01 +} +// 错误接口 +export type BleError = { + errCode: number; + errMsg: string; + errSubject?: string; +}; +// 连接选项 +export type BleConnectOptions = { + deviceId: string; + timeout?: number; + success?: (result: any) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// 断开连接选项 +export type BleDisconnectOptions = { + deviceId: string; + success?: (result: any) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// 获取特征值选项 +export type BleCharacteristicOptions = { + deviceId: string; + serviceId: string; + characteristicId: string; + success?: (result: any) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// 写入特征值选项 +export type BleWriteOptions = { + deviceId: string; + serviceId: string; + characteristicId: string; + value: Uint8Array; + writeType?: number; + success?: (result: any) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// Options for writeCharacteristic helper +export type WriteCharacteristicOptions = { + waitForResponse?: boolean; + maxAttempts?: number; + retryDelayMs?: number; + giveupTimeoutMs?: number; + forceWriteTypeNoResponse?: boolean; +}; +// 通知特征值回调函数 +export type BleNotifyCallback = (data: Uint8Array) => void; +// 通知特征值选项 +export type BleNotifyOptions = { + deviceId: string; + serviceId: string; + characteristicId: string; + state?: boolean; // true: 启用通知,false: 禁用通知 + onCharacteristicValueChange: BleNotifyCallback; + success?: (result: any) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// 获取服务选项 +export type BleDeviceServicesOptions = { + deviceId: string; + success?: (result: BleServicesResult) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// 获取特征值选项 +export type BleDeviceCharacteristicsOptions = { + deviceId: string; + serviceId: string; + success?: (result: BleCharacteristicsResult) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// 蓝牙扫描选项 +export type BluetoothScanOptions = { + services?: string[]; + timeout?: number; + onDeviceFound?: (device: BleDeviceInfo) => void; + success?: (result: BleScanResult) => void; + fail?: (error: BleError) => void; + complete?: (result: any) => void; +}; +// 扫描结果 +// 服务结果 +export type BleServicesResult = { + services: BleServiceInfo[]; + errMsg?: string; +}; +// 特征值结果 +export type BleCharacteristicsResult = { + characteristics: BleCharacteristicInfo[]; + errMsg?: string; +}; +// 定义连接状态枚举 +export enum BLE_CONNECTION_STATE { + DISCONNECTED = 0, + CONNECTING = 1, + CONNECTED = 2, + DISCONNECTING = 3 +} +// 电池状态类型定义 +export type BatteryStatus = { + batteryLevel: number; // 电量百分比 + isCharging: boolean; // 充电状态 +}; +// 蓝牙服务接口类型定义 - 转换为type类型 +export type BleService = { + uuid: string; + isPrimary: boolean; +}; +// 蓝牙特征值接口定义 - 转换为type类型 +export type BleCharacteristic = { + uuid: string; + service: BleService; + properties: BleCharacteristicProperties; +}; +// PendingPromise接口定义 +export interface PendingCallback { + resolve: (data: any) => void; + reject: (err?: any) => void; + timer?: number; +} +// 蓝牙相关接口和类型定义 +export type BleDevice = { + deviceId: string; + name: string; + rssi?: number; + lastSeen?: number; // 新增 + // 新增 + serviceId?: string; + writeCharId?: string; + notifyCharId?: string; +}; +// BLE常规选项 +export type BleOptions = { + timeout?: number; + success?: (result: any) => void; + fail?: (error: any) => void; + complete?: () => void; +}; +export type BleConnectionState = number; // 0: DISCONNECTED, 1: CONNECTING, 2: CONNECTED, 3: DISCONNECTING +export type BleConnectOptionsExt = { + timeout?: number; + services?: string[]; + requireResponse?: boolean; + autoReconnect?: boolean; + maxAttempts?: number; + interval?: number; +}; +// 回调函数类型 +export type BleDeviceFoundCallback = (device: BleDevice) => void; +export type BleConnectionStateChangeCallback = (deviceId: string, state: BleConnectionState) => void; +export type BleDataPayload = { + deviceId: string; + serviceId?: string; + characteristicId?: string; + data: string | ArrayBuffer; + format?: number; // 0: JSON, 1: XML, 2: RAW +}; +export type BleDataSentCallback = (payload: BleDataPayload, success: boolean, error?: BleError) => void; +export type BleErrorCallback = (error: BleError) => void; +// 健康数据类型定义 +export enum HealthDataType { + HEART_RATE = 1, + BLOOD_OXYGEN = 2, + TEMPERATURE = 3, + STEP_COUNT = 4, + SLEEP_DATA = 5, + HEALTH_DATA = 6 +} +// Platform-specific services should be imported from per-platform entrypoints +// (e.g. './app-android/index.uts' or './web/index.uts'). +// Avoid re-exporting platform modules at the SDK root to prevent bundlers +// Platform-specific services should be imported from per-platform entrypoints +// (e.g. './app-android/index.uts' or './web/index.uts'). +// Avoid re-exporting platform modules at the SDK root to prevent bundlers +// from pulling android.* symbols into web bundles. +// If a typed ambient reference is required, declare the shape here instead of importing implementation. +// Example lightweight typed placeholder (do not import platform code here): +// export type BluetoothService = any; // platform-specific implementation exported from platform index files +// ====== 新增多协议、统一事件、协议适配、状态管理支持 ====== +export type BleProtocolType = 'standard' | 'custom' | 'health' | 'ibeacon' | 'mesh'; +export type BleEvent = 'deviceFound' | 'scanFinished' | 'connectionStateChanged' | 'dataReceived' | 'dataSent' | 'error' | 'servicesDiscovered' | 'connected' // 新增 + | 'disconnected'; // 新增 +// 事件回调参数 +export type BleEventPayload = { + event: BleEvent; + device?: BleDevice; + protocol?: BleProtocolType; + state?: BleConnectionState; + data?: ArrayBuffer | string | object; + format?: string; + error?: BleError; + extra?: any; +}; +// 事件回调函数 +export type BleEventCallback = (payload: BleEventPayload) => void; +// 多协议设备信息(去除交叉类型,直接展开字段) +export type MultiProtocolDevice = { + deviceId: string; + name: string; + rssi?: number; + protocol: BleProtocolType; +}; +export type ScanDevicesOptions = { + protocols?: BleProtocolType[]; + optionalServices?: string[]; + timeout?: number; + onDeviceFound?: (device: BleDevice) => void; + onScanFinished?: () => void; +}; +// Named payload type used by sendData +export type SendDataPayload = { + deviceId: string; + serviceId?: string; + characteristicId?: string; + data: string | ArrayBuffer; + format?: number; + protocol: BleProtocolType; +}; +// 协议处理器接口(为 protocol-handler 适配器预留) +export type ScanHandler = { + protocol: BleProtocolType; + scanDevices?: (options: ScanDevicesOptions) => Promise; + connect: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; + disconnect: (device: BleDevice) => Promise; + // Optional: send arbitrary data via the protocol's write characteristic + sendData?: (device: BleDevice, payload: SendDataPayload, options?: BleOptions) => Promise; + // Optional: try to connect and discover service/characteristic ids for this device + autoConnect?: (device: BleDevice, options?: BleConnectOptionsExt) => Promise; +}; +// 自动发现服务和特征返回类型 +export type AutoBleInterfaces = { + serviceId: string; + writeCharId: string; + notifyCharId: string; +}; +export type ResponseCallbackEntry = { + cb: (data: Uint8Array) => boolean | void; + multi: boolean; +}; +// Result returned by a DFU control parser. Use a plain string `type` to keep +// the generated Kotlin simple and avoid inline union types which the generator +// does not handle well. +export type ControlParserResult = { + type: string; // e.g. 'progress', 'success', 'error', 'info' + progress?: number; + error?: any; +}; +// DFU types +export type DfuOptions = { + mtu?: number; + useNordic?: boolean; + // If true, the DFU upload will await a write response per-packet. Set false to use + // WRITE_NO_RESPONSE (fire-and-forget) for higher throughput. Default: false. + waitForResponse?: boolean; + // Maximum number of outstanding NO_RESPONSE writes to allow before throttling. + // This implements a simple sliding window. Default: 32. + maxOutstanding?: number; + // Per-chunk sleep (ms) to yield to event loop / Android BLE stack. Default: 2. + writeSleepMs?: number; + // Retry delay (ms) used by the Android write helper when gatt.writeCharacteristic + // returns false. Smaller values can improve throughput on congested stacks. + writeRetryDelayMs?: number; + // Maximum number of immediate write attempts before falling back to the give-up timeout. + writeMaxAttempts?: number; + // Timeout (ms) to wait for a late onCharacteristicWrite callback after all retries fail. + writeGiveupTimeoutMs?: number; + // Packet Receipt Notification (PRN) window size in packets. If set, DFU + // manager will send a Set PRN command to the device and wait for PRN + // notifications after this many packets. Default: 12. + prn?: number; + // Timeout (ms) to wait for a PRN notification once the window is reached. + // Default: 10000 (10s). + prnTimeoutMs?: number; + // When true, disable PRN waits automatically after the first timeout to prevent + // repeated long stalls on devices that do not send PRNs. Default: true. + disablePrnOnTimeout?: boolean; + // Time (ms) to wait for outstanding fire-and-forget writes to drain before issuing + // the activate/validate control command. Default: 3000. + drainOutstandingTimeoutMs?: number; + controlTimeout?: number; + onProgress?: (percent: number) => void; + onLog?: (message: string) => void; + controlParser?: (data: Uint8Array) => ControlParserResult | null; +}; +export type DfuManagerType = { + startDfu: (deviceId: string, firmwareBytes: Uint8Array, options?: DfuOptions) => Promise; +}; +// Lightweight runtime / UTS shims and missing types +// These are conservative placeholders to satisfy typings used across platform files. +// UTSJSONObject: bundler environments used by the build may not support +// TypeScript-style index signatures in this .uts context. Use a conservative +// 'any' alias so generated code doesn't rely on unsupported syntax while +// preserving a usable type at the source level. +export type UTSJSONObject = any; +// ByteArray / Int are used in the Android platform code to interop with Java APIs. +// Define minimal aliases so source can compile. Runtime uses Uint8Array and number. +export type ByteArray = any; // runtime will use Java byte[] via UTS bridge; keep as any here +// Callback types used by service_manager and index wrappers +export type BleDataReceivedCallback = (data: Uint8Array) => void; +export type BleScanResult = { + deviceId: string; + name?: string; + rssi?: number; + advertising?: any; +}; +// Minimal UI / framework placeholders (some files reference these in types only) +export type ComponentPublicInstance = any; +export type UniElement = any; +export type UniPage = any; +// Platform service placeholder (actual implementation exported from platform index files) +// Provide a lightweight, strongly-shaped class skeleton so source-level code +// (and the code generator) can rely on concrete method names and signatures. +// Implementations are platform-specific and exported from per-platform index +// files (e.g. './app-android/index.uts' or './web/index.uts'). This class is +// intentionally thin — it declares method signatures used across pages and +// platform shims so the generator emits resolvable Kotlin symbols. +export class BluetoothService { + // Event emitter style + on(event: BleEvent | string, callback: BleEventCallback): void { } + off(event: BleEvent | string, callback?: BleEventCallback): void { } + // Scanning / discovery + scanDevices(options?: ScanDevicesOptions): Promise { return Promise.resolve(); } + // Connection management + connectDevice(deviceId: string, protocol?: string, options?: BleConnectOptionsExt): Promise { return Promise.resolve(); } + disconnectDevice(deviceId: string, protocol?: string): Promise { return Promise.resolve(); } + getConnectedDevices(): MultiProtocolDevice[] { return []; } + // Services / characteristics + getServices(deviceId: string): Promise { return Promise.resolve([]); } + getCharacteristics(deviceId: string, serviceId: string): Promise { return Promise.resolve([]); } + // Read / write / notify + readCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(new ArrayBuffer(0)); } + writeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, value: Uint8Array | ArrayBuffer, options?: WriteCharacteristicOptions): Promise { return Promise.resolve(true); } + subscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, callback: BleNotifyCallback): Promise { return Promise.resolve(); } + unsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(); } + // Convenience helpers + getAutoBleInterfaces(deviceId: string): Promise { + const res: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' }; + return Promise.resolve(res); + } +} +// Runtime protocol handler base class. Exporting a concrete class ensures the +// generator emits a resolvable runtime type that platform handlers can extend. +// Source-level code can still use the ScanHandler type for typing. +// Runtime ProtocolHandler is implemented in `protocol_handler.uts`. +// Keep the public typing in this file minimal to avoid duplicate runtime +// declarations. Consumers that need the runtime class should import it from +// './protocol_handler.uts'. +//# sourceMappingURL=interface.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts.map new file mode 100644 index 0000000..605c57e --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/interface.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"interface.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/interface.uts"],"names":[],"mappings":"AAAA,cAAc;AAEd,WAAW;AACX,MAAM,MAAM,aAAa,GAAG;IAC3B,QAAQ,EAAG,MAAM,CAAC;IAClB,IAAI,EAAG,MAAM,CAAC;IACd,IAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAU,CAAC,EAAE,OAAO,CAAC;IACrB,KAAK;IACL,SAAU,CAAC,EAAE,MAAM,CAAC;IACpB,WAAY,CAAC,EAAE,MAAM,CAAC;IACtB,YAAa,CAAC,EAAE,MAAM,CAAC;CACvB,CAAA;AACD,MAAM,MAAM,qBAAqB,GAAG;IACnC,QAAQ,EAAG,UAAU,EAAE,CAAC;IACxB,eAAe,EAAG,iBAAiB,EAAE,CAAC;CACtC,CAAA;AAED,SAAS;AACT,MAAM,MAAM,cAAc,GAAG;IAC5B,IAAI,EAAG,MAAM,CAAC;IACd,SAAS,EAAG,OAAO,CAAC;CACpB,CAAA;AAED,UAAU;AACV,MAAM,MAAM,2BAA2B,GAAG;IACzC,IAAI,EAAG,OAAO,CAAC;IACf,KAAK,EAAG,OAAO,CAAC;IAChB,MAAM,EAAG,OAAO,CAAC;IACjB,QAAQ,EAAG,OAAO,CAAC;IACnB,oBAAqB,CAAC,EAAE,OAAO,CAAC;IAChC,OAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,QAAS,CAAC,EAAE,OAAO,CAAC;IACpB,SAAU,CAAC,EAAE,OAAO,CAAC;CACrB,CAAA;AAED,UAAU;AACV,MAAM,MAAM,qBAAqB,GAAG;IACnC,IAAI,EAAG,MAAM,CAAC;IACd,SAAS,EAAG,MAAM,CAAC;IACnB,UAAU,EAAG,2BAA2B,CAAC;CACzC,CAAA;AAED,QAAQ;AACR,MAAM,MAAM,YAAY;IACvB,aAAa,GAAG,CAAC;IACjB,qBAAqB,GAAG,CAAC;IACzB,iBAAiB,GAAG,CAAC;IACrB,oBAAoB,GAAG,CAAC;IACxB,iBAAiB,GAAG,CAAC;IACrB,wBAAwB,GAAG,CAAC;IAC5B,iBAAiB,GAAG,CAAC;CACrB;AAED,OAAO;AACP,MAAM,MAAM,WAAW;IACtB,OAAO,GAAG,CAAC;IACX,WAAW,GAAG,CAAC;IACf,MAAM,GAAG,EAAE;IACX,gBAAgB,GAAG,IAAI;CACvB;AAED,OAAO;AACP,MAAM,MAAM,QAAQ,GAAC;IACpB,OAAO,EAAG,MAAM,CAAC;IACjB,MAAM,EAAG,MAAM,CAAC;IAChB,UAAW,CAAC,EAAE,MAAM,CAAC;CACrB,CAAA;AAGD,OAAO;AACP,MAAM,MAAM,iBAAiB,GAAG;IAC/B,QAAQ,EAAG,MAAM,CAAC;IAClB,OAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;IAClC,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,SAAS;AACT,MAAM,MAAM,oBAAoB,GAAG;IAClC,QAAQ,EAAG,MAAM,CAAC;IAClB,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;IAClC,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,UAAU;AACV,MAAM,MAAM,wBAAwB,GAAG;IACtC,QAAQ,EAAG,MAAM,CAAC;IAClB,SAAS,EAAG,MAAM,CAAC;IACnB,gBAAgB,EAAG,MAAM,CAAC;IAC1B,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;IAClC,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,UAAU;AACV,MAAM,MAAM,eAAe,GAAG;IAC7B,QAAQ,EAAG,MAAM,CAAC;IAClB,SAAS,EAAG,MAAM,CAAC;IACnB,gBAAgB,EAAG,MAAM,CAAC;IAC1B,KAAK,EAAG,UAAU,CAAC;IACnB,SAAU,CAAC,EAAE,MAAM,CAAC;IACpB,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;IAClC,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,yCAAyC;AACzC,MAAM,MAAM,0BAA0B,GAAG;IACxC,eAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B,WAAY,CAAC,EAAE,MAAM,CAAC;IACtB,YAAa,CAAC,EAAE,MAAM,CAAC;IACvB,eAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,wBAAyB,CAAC,EAAE,OAAO,CAAC;CACpC,CAAA;AAED,YAAY;AACZ,MAAM,MAAM,iBAAiB,GAAG,CAAC,IAAI,EAAG,UAAU,KAAK,IAAI,CAAC;AAE5D,UAAU;AACV,MAAM,MAAM,gBAAgB,GAAG;IAC9B,QAAQ,EAAG,MAAM,CAAC;IAClB,SAAS,EAAG,MAAM,CAAC;IACnB,gBAAgB,EAAG,MAAM,CAAC;IAC1B,KAAM,CAAC,EAAE,OAAO,CAAC,CAAE,yBAAyB;IAC5C,2BAA2B,EAAG,iBAAiB,CAAC;IAChD,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;IAClC,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,SAAS;AACT,MAAM,MAAM,wBAAwB,GAAG;IACtC,QAAQ,EAAG,MAAM,CAAC;IAClB,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,iBAAiB,KAAK,IAAI,CAAC;IAChD,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,UAAU;AACV,MAAM,MAAM,+BAA+B,GAAG;IAC7C,QAAQ,EAAG,MAAM,CAAC;IAClB,SAAS,EAAG,MAAM,CAAC;IACnB,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,wBAAwB,KAAK,IAAI,CAAC;IACvD,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,SAAS;AACT,MAAM,MAAM,oBAAoB,GAAG;IAClC,QAAS,CAAC,EAAE,MAAM,EAAE,CAAC;IACrB,OAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,aAAc,CAAC,EAAE,CAAC,MAAM,EAAG,aAAa,KAAK,IAAI,CAAC;IAClD,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,aAAa,KAAK,IAAI,CAAC;IAC5C,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;IACnC,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;CACnC,CAAA;AAED,OAAO;AAEP,OAAO;AACP,MAAM,MAAM,iBAAiB,GAAG;IAC/B,QAAQ,EAAG,cAAc,EAAE,CAAC;IAC5B,MAAO,CAAC,EAAE,MAAM,CAAC;CACjB,CAAA;AAED,QAAQ;AACR,MAAM,MAAM,wBAAwB,GAAG;IACtC,eAAe,EAAG,qBAAqB,EAAE,CAAC;IAC1C,MAAO,CAAC,EAAE,MAAM,CAAC;CACjB,CAAA;AAED,WAAW;AACX,MAAM,MAAM,oBAAoB;IAC/B,YAAY,GAAG,CAAC;IAChB,UAAU,GAAG,CAAC;IACd,SAAS,GAAG,CAAC;IACb,aAAa,GAAG,CAAC;CACjB;AAED,WAAW;AACX,MAAM,MAAM,aAAa,GAAG;IAC3B,YAAY,EAAG,MAAM,CAAC,CAAG,QAAQ;IACjC,UAAU,EAAG,OAAO,CAAC,CAAI,OAAO;CAChC,CAAA;AAED,yBAAyB;AACzB,MAAM,MAAM,UAAU,GAAG;IACxB,IAAI,EAAG,MAAM,CAAC;IACd,SAAS,EAAG,OAAO,CAAC;CACpB,CAAA;AAED,wBAAwB;AACxB,MAAM,MAAM,iBAAiB,GAAG;IAC/B,IAAI,EAAG,MAAM,CAAC;IACd,OAAO,EAAG,UAAU,CAAC;IACrB,UAAU,EAAG,2BAA2B,CAAC;CACzC,CAAA;AAED,qBAAqB;AACrB,MAAM,WAAW,eAAe;IAC/B,OAAO,EAAG,CAAC,IAAI,EAAG,GAAG,KAAK,IAAI,CAAC;IAC/B,MAAM,EAAG,CAAC,GAAI,CAAC,EAAE,GAAG,KAAK,IAAI,CAAC;IAC9B,KAAM,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,cAAc;AACd,MAAM,MAAM,SAAS,GAAG;IACvB,QAAQ,EAAG,MAAM,CAAC;IAClB,IAAI,EAAG,MAAM,CAAC;IACd,IAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAS,CAAC,EAAE,MAAM,CAAC,CAAC,KAAK;IACzB,KAAK;IACL,SAAU,CAAC,EAAE,MAAM,CAAC;IACpB,WAAY,CAAC,EAAE,MAAM,CAAC;IACtB,YAAa,CAAC,EAAE,MAAM,CAAC;CACvB,CAAA;AAED,UAAU;AACV,MAAM,MAAM,UAAU,GAAG;IACxB,OAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAQ,CAAC,EAAE,CAAC,MAAM,EAAG,GAAG,KAAK,IAAI,CAAC;IAClC,IAAK,CAAC,EAAE,CAAC,KAAK,EAAG,GAAG,KAAK,IAAI,CAAC;IAC9B,QAAS,CAAC,EAAE,MAAM,IAAI,CAAC;CACvB,CAAA;AAED,MAAM,MAAM,kBAAkB,GAAG,MAAM,CAAC,CAAC,iEAAiE;AAE1G,MAAM,MAAM,oBAAoB,GAAG;IAClC,OAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,QAAS,CAAC,EAAE,MAAM,EAAE,CAAC;IACrB,eAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B,aAAc,CAAC,EAAE,OAAO,CAAC;IACzB,WAAY,CAAC,EAAE,MAAM,CAAC;IACtB,QAAS,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,SAAS;AACT,MAAM,MAAM,sBAAsB,GAAG,CAAC,MAAM,EAAG,SAAS,KAAK,IAAI,CAAC;AAClE,MAAM,MAAM,gCAAgC,GAAG,CAAC,QAAQ,EAAG,MAAM,EAAE,KAAK,EAAG,kBAAkB,KAAK,IAAI,CAAC;AAEvG,MAAM,MAAM,cAAc,GAAG;IAC5B,QAAQ,EAAG,MAAM,CAAC;IAClB,SAAU,CAAC,EAAE,MAAM,CAAC;IACpB,gBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,IAAI,EAAG,MAAM,GAAG,WAAW,CAAC;IAC5B,MAAO,CAAC,EAAE,MAAM,CAAC,CAAC,0BAA0B;CAC5C,CAAA;AAED,MAAM,MAAM,mBAAmB,GAAG,CAAC,OAAO,EAAG,cAAc,EAAE,OAAO,EAAG,OAAO,EAAE,KAAM,CAAC,EAAE,QAAQ,KAAK,IAAI,CAAC;AAC3G,MAAM,MAAM,gBAAgB,GAAG,CAAC,KAAK,EAAG,QAAQ,KAAK,IAAI,CAAC;AAE1D,WAAW;AACX,MAAM,MAAM,cAAc;IACzB,UAAU,GAAG,CAAC;IACd,YAAY,GAAG,CAAC;IAChB,WAAW,GAAG,CAAC;IACf,UAAU,GAAG,CAAC;IACd,UAAU,GAAG,CAAC;IACd,WAAW,GAAG,CAAC;CACf;AAED,8EAA8E;AAC9E,yDAAyD;AACzD,0EAA0E;AAC1E,8EAA8E;AAC9E,yDAAyD;AACzD,0EAA0E;AAC1E,mDAAmD;AACnD,wGAAwG;AACxG,4EAA4E;AAC5E,6GAA6G;AAI7G,uCAAuC;AACvC,MAAM,MAAM,eAAe,GACxB,UAAU,GACV,QAAQ,GACR,QAAQ,GACR,SAAS,GACT,MAAM,CAAC;AAEV,MAAM,MAAM,QAAQ,GACjB,aAAa,GACb,cAAc,GACd,wBAAwB,GACxB,cAAc,GACd,UAAU,GACV,OAAO,GACP,oBAAoB,GACpB,WAAW,CAAQ,KAAK;GACxB,cAAc,CAAC,CAAI,KAAK;AAE3B,SAAS;AACT,MAAM,MAAM,eAAe,GAAG;IAC7B,KAAK,EAAG,QAAQ,CAAC;IACjB,MAAO,CAAC,EAAE,SAAS,CAAC;IACpB,QAAS,CAAC,EAAE,eAAe,CAAC;IAC5B,KAAM,CAAC,EAAE,kBAAkB,CAAC;IAC5B,IAAK,CAAC,EAAE,WAAW,GAAG,MAAM,GAAG,MAAM,CAAC;IACtC,MAAO,CAAC,EAAE,MAAM,CAAC;IACjB,KAAM,CAAC,EAAE,QAAQ,CAAC;IAClB,KAAM,CAAC,EAAE,GAAG,CAAC;CACb,CAAA;AAED,SAAS;AACT,MAAM,MAAM,gBAAgB,GAAG,CAAC,OAAO,EAAG,eAAe,KAAK,IAAI,CAAC;AAEnE,yBAAyB;AACzB,MAAM,MAAM,mBAAmB,GAAG;IACjC,QAAQ,EAAG,MAAM,CAAC;IAClB,IAAI,EAAG,MAAM,CAAC;IACd,IAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,EAAG,eAAe,CAAC;CAC3B,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG;IAChC,SAAU,CAAC,EAAE,eAAe,EAAE,CAAC;IAC/B,gBAAiB,CAAC,EAAE,MAAM,EAAE,CAAC;IAC7B,OAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,aAAc,CAAC,EAAE,CAAC,MAAM,EAAG,SAAS,KAAK,IAAI,CAAC;IAC9C,cAAe,CAAC,EAAE,MAAM,IAAI,CAAC;CAC7B,CAAC;AACF,sCAAsC;AACtC,MAAM,MAAM,eAAe,GAAG;IAC7B,QAAQ,EAAG,MAAM,CAAC;IAClB,SAAU,CAAC,EAAE,MAAM,CAAC;IACpB,gBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,IAAI,EAAG,MAAM,GAAG,WAAW,CAAC;IAC5B,MAAO,CAAC,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAG,eAAe,CAAC;CAC3B,CAAA;AACD,oCAAoC;AACpC,MAAM,MAAM,WAAW,GAAG;IACzB,QAAQ,EAAG,eAAe,CAAC;IAC3B,WAAY,CAAC,EAAE,CAAC,OAAO,EAAG,kBAAkB,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAC/D,OAAO,EAAG,CAAC,MAAM,EAAG,SAAS,EAAE,OAAQ,CAAC,EAAE,oBAAoB,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACjF,UAAU,EAAG,CAAC,MAAM,EAAG,SAAS,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACnD,wEAAwE;IACxE,QAAS,CAAC,EAAE,CAAC,MAAM,EAAG,SAAS,EAAE,OAAO,EAAG,eAAe,EAAE,OAAQ,CAAC,EAAE,UAAU,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACpG,mFAAmF;IACnF,WAAY,CAAC,EAAE,CAAC,MAAM,EAAG,SAAS,EAAE,OAAQ,CAAC,EAAE,oBAAoB,KAAK,OAAO,CAAC,iBAAiB,CAAC,CAAC;CAEnG,CAAA;AAGD,gBAAgB;AAChB,MAAM,MAAM,iBAAiB,GAAG;IAC/B,SAAS,EAAG,MAAM,CAAC;IACnB,WAAW,EAAG,MAAM,CAAC;IACrB,YAAY,EAAG,MAAM,CAAC;CACtB,CAAA;AACD,MAAM,MAAM,qBAAqB,GAAG;IACnC,EAAE,EAAG,CAAC,IAAI,EAAG,UAAU,KAAK,OAAO,GAAG,IAAI,CAAC;IAC3C,KAAK,EAAG,OAAO,CAAC;CAChB,CAAC;AAEF,6EAA6E;AAC7E,+EAA+E;AAC/E,wBAAwB;AACxB,MAAM,MAAM,mBAAmB,GAAG;IACjC,IAAI,EAAG,MAAM,CAAC,CAAC,8CAA8C;IAC7D,QAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAM,CAAC,EAAE,GAAG,CAAC;CACb,CAAA;AAED,YAAY;AACZ,MAAM,MAAM,UAAU,GAAG;IACxB,GAAI,CAAC,EAAE,MAAM,CAAC;IACd,SAAU,CAAC,EAAE,OAAO,CAAC;IACrB,mFAAmF;IACnF,6EAA6E;IAC7E,eAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B,+EAA+E;IAC/E,wDAAwD;IACxD,cAAe,CAAC,EAAE,MAAM,CAAC;IACzB,+EAA+E;IAC/E,YAAa,CAAC,EAAE,MAAM,CAAC;IACvB,kFAAkF;IAClF,4EAA4E;IAC5E,iBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,yFAAyF;IACzF,gBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,yFAAyF;IACzF,oBAAqB,CAAC,EAAE,MAAM,CAAC;IAC/B,wEAAwE;IACxE,qEAAqE;IACrE,sDAAsD;IACtD,GAAI,CAAC,EAAE,MAAM,CAAC;IACd,0EAA0E;IAC1E,wBAAwB;IACxB,YAAa,CAAC,EAAE,MAAM,CAAC;IACvB,gFAAgF;IAChF,wEAAwE;IACxE,mBAAoB,CAAC,EAAE,OAAO,CAAC;IAC/B,mFAAmF;IACnF,wDAAwD;IACxD,yBAA0B,CAAC,EAAE,MAAM,CAAC;IACpC,cAAe,CAAC,EAAE,MAAM,CAAC;IACzB,UAAW,CAAC,EAAE,CAAC,OAAO,EAAG,MAAM,KAAK,IAAI,CAAC;IACzC,KAAM,CAAC,EAAE,CAAC,OAAO,EAAG,MAAM,KAAK,IAAI,CAAC;IACpC,aAAc,CAAC,EAAE,CAAC,IAAI,EAAG,UAAU,KAAK,mBAAmB,GAAG,IAAI,CAAC;CACnE,CAAA;AAED,MAAM,MAAM,cAAc,GAAG;IAC5B,QAAQ,EAAG,CAAC,QAAQ,EAAG,MAAM,EAAE,aAAa,EAAG,UAAU,EAAE,OAAQ,CAAC,EAAE,UAAU,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;CACnG,CAAA;AAED,oDAAoD;AACpD,qFAAqF;AACrF,wEAAwE;AACxE,6EAA6E;AAC7E,yEAAyE;AACzE,gDAAgD;AAChD,MAAM,MAAM,aAAa,GAAG,GAAG,CAAC;AAEhC,mFAAmF;AACnF,oFAAoF;AACpF,MAAM,MAAM,SAAS,GAAG,GAAG,CAAC,CAAC,gEAAgE;AAE7F,4DAA4D;AAC5D,MAAM,MAAM,uBAAuB,GAAG,CAAC,IAAI,EAAE,UAAU,KAAK,IAAI,CAAC;AACjE,MAAM,MAAM,aAAa,GAAG;IAC3B,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,GAAG,CAAC;CAClB,CAAC;AAEF,iFAAiF;AACjF,MAAM,MAAM,uBAAuB,GAAG,GAAG,CAAC;AAC1C,MAAM,MAAM,UAAU,GAAG,GAAG,CAAC;AAC7B,MAAM,MAAM,OAAO,GAAG,GAAG,CAAC;AAE1B,0FAA0F;AAC1F,6EAA6E;AAC7E,6EAA6E;AAC7E,6EAA6E;AAC7E,6EAA6E;AAC7E,2EAA2E;AAC3E,mEAAmE;AACnE,MAAM,OAAO,gBAAgB;IAC5B,sBAAsB;IACtB,EAAE,CAAC,KAAK,EAAE,QAAQ,GAAG,MAAM,EAAE,QAAQ,EAAE,gBAAgB,GAAG,IAAI,GAAE,CAAC;IACjE,GAAG,CAAC,KAAK,EAAE,QAAQ,GAAG,MAAM,EAAE,QAAQ,CAAC,EAAE,gBAAgB,GAAG,IAAI,GAAE,CAAC;IAEnE,uBAAuB;IACvB,WAAW,CAAC,OAAO,CAAC,EAAE,kBAAkB,GAAG,OAAO,CAAC,IAAI,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAEtF,wBAAwB;IACxB,aAAa,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,oBAAoB,GAAG,OAAO,CAAC,IAAI,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAC/H,gBAAgB,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAClG,mBAAmB,IAAI,mBAAmB,EAAE,GAAG,OAAO,EAAE,CAAC,CAAC,CAAC;IAE3D,6BAA6B;IAC7B,WAAW,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,EAAE,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;IACpF,kBAAkB,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,EAAE,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;IAErH,wBAAwB;IACxB,kBAAkB,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,GAAG,OAAO,CAAC,WAAW,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,CAAC,IAAI,WAAW,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACvJ,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,KAAK,0BAA0B,EAAE,OAAO,CAAC,EAAE,0BAA0B,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAC7M,uBAAuB,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,EAAE,QAAQ,EAAE,iBAAiB,GAAG,OAAO,CAAC,IAAI,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAChK,yBAAyB,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,gBAAgB,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,GAAG,OAAO,OAAO,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAEpI,sBAAsB;IACtB,oBAAoB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC;QACjE,MAAM,GAAG,EAAE,iBAAiB,GAAG,EAAE,SAAS,EAAE,EAAE,EAAE,WAAW,EAAE,EAAE,EAAE,YAAY,EAAE,EAAE,EAAE,CAAC;QACpF,OAAO,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IAC7B,CAAC;CACF;AAED,8EAA8E;AAC9E,+EAA+E;AAC/E,mEAAmE;AACnE,oEAAoE;AACpE,yEAAyE;AACzE,4EAA4E;AAC5E,4BAA4B","sourcesContent":["// 蓝牙相关接口和类型定义\r\n\r\n// 基础设备信息类型\r\nexport type BleDeviceInfo = {\r\n\tdeviceId : string;\r\n\tname : string;\r\n\tRSSI ?: number;\r\n\tconnected ?: boolean;\r\n\t// 新增\r\n\tserviceId ?: string;\r\n\twriteCharId ?: string;\r\n\tnotifyCharId ?: string;\r\n}\r\nexport type AutoDiscoverAllResult = {\r\n\tservices : BleService[];\r\n\tcharacteristics : BleCharacteristic[];\r\n}\r\n\r\n// 服务信息类型\r\nexport type BleServiceInfo = {\r\n\tuuid : string;\r\n\tisPrimary : boolean;\r\n}\r\n\r\n// 特征值属性类型\r\nexport type BleCharacteristicProperties = {\r\n\tread : boolean;\r\n\twrite : boolean;\r\n\tnotify : boolean;\r\n\tindicate : boolean;\r\n\twriteWithoutResponse ?: boolean;\r\n\tcanRead ?: boolean;\r\n\tcanWrite ?: boolean;\r\n\tcanNotify ?: boolean;\r\n}\r\n\r\n// 特征值信息类型\r\nexport type BleCharacteristicInfo = {\r\n\tuuid : string;\r\n\tserviceId : string;\r\n\tproperties : BleCharacteristicProperties;\r\n}\r\n\r\n// 错误状态码\r\nexport enum BleErrorCode {\r\n\tUNKNOWN_ERROR = 0,\r\n\tBLUETOOTH_UNAVAILABLE = 1,\r\n\tPERMISSION_DENIED = 2,\r\n\tDEVICE_NOT_CONNECTED = 3,\r\n\tSERVICE_NOT_FOUND = 4,\r\n\tCHARACTERISTIC_NOT_FOUND = 5,\r\n\tOPERATION_TIMEOUT = 6\r\n}\r\n\r\n// 命令类型\r\nexport enum CommandType {\r\n\tBATTERY = 1,\r\n\tDEVICE_INFO = 2,\r\n\tCUSTOM = 99,\r\n\tTestBatteryLevel = 0x01\r\n}\r\n\r\n// 错误接口\r\nexport type BleError {\r\n\terrCode : number;\r\n\terrMsg : string;\r\n\terrSubject ?: string;\r\n}\r\n\r\n\r\n// 连接选项\r\nexport type BleConnectOptions = {\r\n\tdeviceId : string;\r\n\ttimeout ?: number;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 断开连接选项\r\nexport type BleDisconnectOptions = {\r\n\tdeviceId : string;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 获取特征值选项\r\nexport type BleCharacteristicOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tcharacteristicId : string;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 写入特征值选项\r\nexport type BleWriteOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tcharacteristicId : string;\r\n\tvalue : Uint8Array;\r\n\twriteType ?: number;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// Options for writeCharacteristic helper\r\nexport type WriteCharacteristicOptions = {\r\n\twaitForResponse ?: boolean;\r\n\tmaxAttempts ?: number;\r\n\tretryDelayMs ?: number;\r\n\tgiveupTimeoutMs ?: number;\r\n\tforceWriteTypeNoResponse ?: boolean;\r\n}\r\n\r\n// 通知特征值回调函数\r\nexport type BleNotifyCallback = (data : Uint8Array) => void;\r\n\r\n// 通知特征值选项\r\nexport type BleNotifyOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tcharacteristicId : string;\r\n\tstate ?: boolean; // true: 启用通知,false: 禁用通知\r\n\tonCharacteristicValueChange : BleNotifyCallback;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 获取服务选项\r\nexport type BleDeviceServicesOptions = {\r\n\tdeviceId : string;\r\n\tsuccess ?: (result : BleServicesResult) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 获取特征值选项\r\nexport type BleDeviceCharacteristicsOptions = {\r\n\tdeviceId : string;\r\n\tserviceId : string;\r\n\tsuccess ?: (result : BleCharacteristicsResult) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 蓝牙扫描选项\r\nexport type BluetoothScanOptions = {\r\n\tservices ?: string[];\r\n\ttimeout ?: number;\r\n\tonDeviceFound ?: (device : BleDeviceInfo) => void;\r\n\tsuccess ?: (result : BleScanResult) => void;\r\n\tfail ?: (error : BleError) => void;\r\n\tcomplete ?: (result : any) => void;\r\n}\r\n\r\n// 扫描结果\r\n\r\n// 服务结果\r\nexport type BleServicesResult = {\r\n\tservices : BleServiceInfo[];\r\n\terrMsg ?: string;\r\n}\r\n\r\n// 特征值结果\r\nexport type BleCharacteristicsResult = {\r\n\tcharacteristics : BleCharacteristicInfo[];\r\n\terrMsg ?: string;\r\n}\r\n\r\n// 定义连接状态枚举\r\nexport enum BLE_CONNECTION_STATE {\r\n\tDISCONNECTED = 0,\r\n\tCONNECTING = 1,\r\n\tCONNECTED = 2,\r\n\tDISCONNECTING = 3\r\n}\r\n\r\n// 电池状态类型定义\r\nexport type BatteryStatus = {\r\n\tbatteryLevel : number; // 电量百分比\r\n\tisCharging : boolean; // 充电状态\r\n}\r\n\r\n// 蓝牙服务接口类型定义 - 转换为type类型\r\nexport type BleService = {\r\n\tuuid : string;\r\n\tisPrimary : boolean;\r\n}\r\n\r\n// 蓝牙特征值接口定义 - 转换为type类型\r\nexport type BleCharacteristic = {\r\n\tuuid : string;\r\n\tservice : BleService;\r\n\tproperties : BleCharacteristicProperties;\r\n}\r\n\r\n// PendingPromise接口定义\r\nexport interface PendingCallback {\r\n\tresolve : (data : any) => void;\r\n\treject : (err ?: any) => void;\r\n\ttimer ?: number;\r\n}\r\n\r\n// 蓝牙相关接口和类型定义\r\nexport type BleDevice = {\r\n\tdeviceId : string;\r\n\tname : string;\r\n\trssi ?: number;\r\n\tlastSeen ?: number; // 新增\r\n\t// 新增\r\n\tserviceId ?: string;\r\n\twriteCharId ?: string;\r\n\tnotifyCharId ?: string;\r\n}\r\n\r\n// BLE常规选项\r\nexport type BleOptions = {\r\n\ttimeout ?: number;\r\n\tsuccess ?: (result : any) => void;\r\n\tfail ?: (error : any) => void;\r\n\tcomplete ?: () => void;\r\n}\r\n\r\nexport type BleConnectionState = number; // 0: DISCONNECTED, 1: CONNECTING, 2: CONNECTED, 3: DISCONNECTING\r\n\r\nexport type BleConnectOptionsExt = {\r\n\ttimeout ?: number;\r\n\tservices ?: string[];\r\n\trequireResponse ?: boolean;\r\n\tautoReconnect ?: boolean;\r\n\tmaxAttempts ?: number;\r\n\tinterval ?: number;\r\n};\r\n\r\n// 回调函数类型\r\nexport type BleDeviceFoundCallback = (device : BleDevice) => void;\r\nexport type BleConnectionStateChangeCallback = (deviceId : string, state : BleConnectionState) => void;\r\n\r\nexport type BleDataPayload = {\r\n\tdeviceId : string;\r\n\tserviceId ?: string;\r\n\tcharacteristicId ?: string;\r\n\tdata : string | ArrayBuffer;\r\n\tformat ?: number; // 0: JSON, 1: XML, 2: RAW\r\n}\r\n\r\nexport type BleDataSentCallback = (payload : BleDataPayload, success : boolean, error ?: BleError) => void;\r\nexport type BleErrorCallback = (error : BleError) => void;\r\n\r\n// 健康数据类型定义\r\nexport enum HealthDataType {\r\n\tHEART_RATE = 1,\r\n\tBLOOD_OXYGEN = 2,\r\n\tTEMPERATURE = 3,\r\n\tSTEP_COUNT = 4,\r\n\tSLEEP_DATA = 5,\r\n\tHEALTH_DATA = 6\r\n}\r\n\r\n// Platform-specific services should be imported from per-platform entrypoints\r\n// (e.g. './app-android/index.uts' or './web/index.uts').\r\n// Avoid re-exporting platform modules at the SDK root to prevent bundlers\r\n// Platform-specific services should be imported from per-platform entrypoints\r\n// (e.g. './app-android/index.uts' or './web/index.uts').\r\n// Avoid re-exporting platform modules at the SDK root to prevent bundlers\r\n// from pulling android.* symbols into web bundles.\r\n// If a typed ambient reference is required, declare the shape here instead of importing implementation.\r\n// Example lightweight typed placeholder (do not import platform code here):\r\n// export type BluetoothService = any; // platform-specific implementation exported from platform index files\r\n\r\n\r\n\r\n// ====== 新增多协议、统一事件、协议适配、状态管理支持 ======\r\nexport type BleProtocolType =\r\n\t| 'standard'\r\n\t| 'custom'\r\n\t| 'health'\r\n\t| 'ibeacon'\r\n\t| 'mesh';\r\n\r\nexport type BleEvent =\r\n\t| 'deviceFound'\r\n\t| 'scanFinished'\r\n\t| 'connectionStateChanged'\r\n\t| 'dataReceived'\r\n\t| 'dataSent'\r\n\t| 'error'\r\n\t| 'servicesDiscovered'\r\n\t| 'connected' // 新增\r\n\t| 'disconnected'; // 新增\r\n\r\n// 事件回调参数\r\nexport type BleEventPayload = {\r\n\tevent : BleEvent;\r\n\tdevice ?: BleDevice;\r\n\tprotocol ?: BleProtocolType;\r\n\tstate ?: BleConnectionState;\r\n\tdata ?: ArrayBuffer | string | object;\r\n\tformat ?: string;\r\n\terror ?: BleError;\r\n\textra ?: any;\r\n}\r\n\r\n// 事件回调函数\r\nexport type BleEventCallback = (payload : BleEventPayload) => void;\r\n\r\n// 多协议设备信息(去除交叉类型,直接展开字段)\r\nexport type MultiProtocolDevice = {\r\n\tdeviceId : string;\r\n\tname : string;\r\n\trssi ?: number;\r\n\tprotocol : BleProtocolType;\r\n};\r\n\r\nexport type ScanDevicesOptions = {\r\n\tprotocols ?: BleProtocolType[];\r\n\toptionalServices ?: string[];\r\n\ttimeout ?: number;\r\n\tonDeviceFound ?: (device : BleDevice) => void;\r\n\tonScanFinished ?: () => void;\r\n};\r\n// Named payload type used by sendData\r\nexport type SendDataPayload = {\r\n\tdeviceId : string;\r\n\tserviceId ?: string;\r\n\tcharacteristicId ?: string;\r\n\tdata : string | ArrayBuffer;\r\n\tformat ?: number;\r\n\tprotocol : BleProtocolType;\r\n}\r\n// 协议处理器接口(为 protocol-handler 适配器预留)\r\nexport type ScanHandler = {\r\n\tprotocol : BleProtocolType;\r\n\tscanDevices ?: (options : ScanDevicesOptions) => Promise;\r\n\tconnect : (device : BleDevice, options ?: BleConnectOptionsExt) => Promise;\r\n\tdisconnect : (device : BleDevice) => Promise;\r\n\t// Optional: send arbitrary data via the protocol's write characteristic\r\n\tsendData ?: (device : BleDevice, payload : SendDataPayload, options ?: BleOptions) => Promise;\r\n\t// Optional: try to connect and discover service/characteristic ids for this device\r\n\tautoConnect ?: (device : BleDevice, options ?: BleConnectOptionsExt) => Promise;\r\n\r\n}\r\n\r\n\r\n// 自动发现服务和特征返回类型\r\nexport type AutoBleInterfaces = {\r\n\tserviceId : string;\r\n\twriteCharId : string;\r\n\tnotifyCharId : string;\r\n}\r\nexport type ResponseCallbackEntry = {\r\n\tcb : (data : Uint8Array) => boolean | void;\r\n\tmulti : boolean;\r\n};\r\n\r\n// Result returned by a DFU control parser. Use a plain string `type` to keep\r\n// the generated Kotlin simple and avoid inline union types which the generator\r\n// does not handle well.\r\nexport type ControlParserResult = {\r\n\ttype : string; // e.g. 'progress', 'success', 'error', 'info'\r\n\tprogress ?: number;\r\n\terror ?: any;\r\n}\r\n\r\n// DFU types\r\nexport type DfuOptions = {\r\n\tmtu ?: number;\r\n\tuseNordic ?: boolean;\r\n\t// If true, the DFU upload will await a write response per-packet. Set false to use\r\n\t// WRITE_NO_RESPONSE (fire-and-forget) for higher throughput. Default: false.\r\n\twaitForResponse ?: boolean;\r\n\t// Maximum number of outstanding NO_RESPONSE writes to allow before throttling.\r\n\t// This implements a simple sliding window. Default: 32.\r\n\tmaxOutstanding ?: number;\r\n\t// Per-chunk sleep (ms) to yield to event loop / Android BLE stack. Default: 2.\r\n\twriteSleepMs ?: number;\r\n\t// Retry delay (ms) used by the Android write helper when gatt.writeCharacteristic\r\n\t// returns false. Smaller values can improve throughput on congested stacks.\r\n\twriteRetryDelayMs ?: number;\r\n\t// Maximum number of immediate write attempts before falling back to the give-up timeout.\r\n\twriteMaxAttempts ?: number;\r\n\t// Timeout (ms) to wait for a late onCharacteristicWrite callback after all retries fail.\r\n\twriteGiveupTimeoutMs ?: number;\r\n\t// Packet Receipt Notification (PRN) window size in packets. If set, DFU\r\n\t// manager will send a Set PRN command to the device and wait for PRN\r\n\t// notifications after this many packets. Default: 12.\r\n\tprn ?: number;\r\n\t// Timeout (ms) to wait for a PRN notification once the window is reached.\r\n\t// Default: 10000 (10s).\r\n\tprnTimeoutMs ?: number;\r\n\t// When true, disable PRN waits automatically after the first timeout to prevent\r\n\t// repeated long stalls on devices that do not send PRNs. Default: true.\r\n\tdisablePrnOnTimeout ?: boolean;\r\n\t// Time (ms) to wait for outstanding fire-and-forget writes to drain before issuing\r\n\t// the activate/validate control command. Default: 3000.\r\n\tdrainOutstandingTimeoutMs ?: number;\r\n\tcontrolTimeout ?: number;\r\n\tonProgress ?: (percent : number) => void;\r\n\tonLog ?: (message : string) => void;\r\n\tcontrolParser ?: (data : Uint8Array) => ControlParserResult | null;\r\n}\r\n\r\nexport type DfuManagerType = {\r\n\tstartDfu : (deviceId : string, firmwareBytes : Uint8Array, options ?: DfuOptions) => Promise;\r\n}\r\n\r\n// Lightweight runtime / UTS shims and missing types\r\n// These are conservative placeholders to satisfy typings used across platform files.\r\n// UTSJSONObject: bundler environments used by the build may not support\r\n// TypeScript-style index signatures in this .uts context. Use a conservative\r\n// 'any' alias so generated code doesn't rely on unsupported syntax while\r\n// preserving a usable type at the source level.\r\nexport type UTSJSONObject = any;\r\n\r\n// ByteArray / Int are used in the Android platform code to interop with Java APIs.\r\n// Define minimal aliases so source can compile. Runtime uses Uint8Array and number.\r\nexport type ByteArray = any; // runtime will use Java byte[] via UTS bridge; keep as any here\r\n\r\n// Callback types used by service_manager and index wrappers\r\nexport type BleDataReceivedCallback = (data: Uint8Array) => void;\r\nexport type BleScanResult = {\r\n\tdeviceId: string;\r\n\tname?: string;\r\n\trssi?: number;\r\n\tadvertising?: any;\r\n};\r\n\r\n// Minimal UI / framework placeholders (some files reference these in types only)\r\nexport type ComponentPublicInstance = any;\r\nexport type UniElement = any;\r\nexport type UniPage = any;\r\n\r\n// Platform service placeholder (actual implementation exported from platform index files)\r\n// Provide a lightweight, strongly-shaped class skeleton so source-level code\r\n// (and the code generator) can rely on concrete method names and signatures.\r\n// Implementations are platform-specific and exported from per-platform index\r\n// files (e.g. './app-android/index.uts' or './web/index.uts'). This class is\r\n// intentionally thin — it declares method signatures used across pages and\r\n// platform shims so the generator emits resolvable Kotlin symbols.\r\nexport class BluetoothService {\r\n\t// Event emitter style\r\n\ton(event: BleEvent | string, callback: BleEventCallback): void {}\r\n\toff(event: BleEvent | string, callback?: BleEventCallback): void {}\r\n\r\n\t// Scanning / discovery\r\n\tscanDevices(options?: ScanDevicesOptions): Promise { return Promise.resolve(); }\r\n\r\n\t// Connection management\r\n\tconnectDevice(deviceId: string, protocol?: string, options?: BleConnectOptionsExt): Promise { return Promise.resolve(); }\r\n\tdisconnectDevice(deviceId: string, protocol?: string): Promise { return Promise.resolve(); }\r\n\tgetConnectedDevices(): MultiProtocolDevice[] { return []; }\r\n\r\n\t// Services / characteristics\r\n\tgetServices(deviceId: string): Promise { return Promise.resolve([]); }\r\n\tgetCharacteristics(deviceId: string, serviceId: string): Promise { return Promise.resolve([]); }\r\n\r\n\t// Read / write / notify\r\n\treadCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(new ArrayBuffer(0)); }\r\n\twriteCharacteristic(deviceId: string, serviceId: string, characteristicId: string, value: Uint8Array | ArrayBuffer, options?: WriteCharacteristicOptions): Promise { return Promise.resolve(true); }\r\n\tsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string, callback: BleNotifyCallback): Promise { return Promise.resolve(); }\r\n\tunsubscribeCharacteristic(deviceId: string, serviceId: string, characteristicId: string): Promise { return Promise.resolve(); }\r\n\r\n\t\t// Convenience helpers\r\n\t\tgetAutoBleInterfaces(deviceId: string): Promise {\r\n\t\t\tconst res: AutoBleInterfaces = { serviceId: '', writeCharId: '', notifyCharId: '' };\r\n\t\t\treturn Promise.resolve(res);\r\n\t\t}\r\n}\r\n\r\n// Runtime protocol handler base class. Exporting a concrete class ensures the\r\n// generator emits a resolvable runtime type that platform handlers can extend.\r\n// Source-level code can still use the ScanHandler type for typing.\r\n// Runtime ProtocolHandler is implemented in `protocol_handler.uts`.\r\n// Keep the public typing in this file minimal to avoid duplicate runtime\r\n// declarations. Consumers that need the runtime class should import it from\r\n// './protocol_handler.uts'."]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts new file mode 100644 index 0000000..7b7f75a --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts @@ -0,0 +1,127 @@ +// Minimal ProtocolHandler runtime class used by pages and components. +// This class adapts the platform `BluetoothService` to a small protocol API +// expected by pages: setConnectionParameters, initialize, testBatteryLevel, +// testVersionInfo. Implemented conservatively to avoid heavy dependencies. +import type { BluetoothService, AutoBleInterfaces, AutoDiscoverAllResult, BleService, BleCharacteristic, BleProtocolType, BleDevice, ScanDevicesOptions, BleConnectOptionsExt, SendDataPayload, BleOptions } from './interface.uts'; +export class ProtocolHandler { + // bluetoothService may be omitted for lightweight wrappers; allow null + bluetoothService: BluetoothService | null = null; + protocol: BleProtocolType = 'standard'; + deviceId: string | null = null; + serviceId: string | null = null; + writeCharId: string | null = null; + notifyCharId: string | null = null; + initialized: boolean = false; + // Accept an optional BluetoothService so wrapper subclasses can call + // `super()` without forcing a runtime instance. + constructor(bluetoothService?: BluetoothService) { + if (bluetoothService != null) + this.bluetoothService = bluetoothService; + } + setConnectionParameters(deviceId: string, serviceId: string, writeCharId: string, notifyCharId: string) { + this.deviceId = deviceId; + this.serviceId = serviceId; + this.writeCharId = writeCharId; + this.notifyCharId = notifyCharId; + } + // initialize: optional setup, returns a Promise that resolves when ready + async initialize(): Promise { + // Simple async initializer — keep implementation minimal and generator-friendly. + try { + // If bluetoothService exposes any protocol-specific setup, call it here. + this.initialized = true; + return; + } + catch (e: any) { + throw e; + } + } + // Protocol lifecycle / operations — default no-ops so generated code has + // concrete member references and platform-specific handlers can override. + async scanDevices(options?: ScanDevicesOptions): Promise { return; } + async connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return; } + async disconnect(device: BleDevice): Promise { return; } + async sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { return; } + async autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return { serviceId: '', writeCharId: '', notifyCharId: '' } as AutoBleInterfaces; } + // Example: testBatteryLevel will attempt to read the battery characteristic + // if write/notify-based protocol is not available. Returns number percentage. + async testBatteryLevel(): Promise { + if (this.deviceId == null) + throw new Error('deviceId not set'); + // copy to local so Kotlin generator can smart-cast the value across awaits + const deviceId = this.deviceId!; + // try reading standard Battery characteristic (180F -> 2A19) + if (this.bluetoothService == null) + throw new Error('bluetoothService not set'); + const services = await this.bluetoothService!.getServices(deviceId); + let found: BleService | null = null; + for (let i = 0; i < services.length; i++) { + const s = services[i]; + const uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null); + const uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : ''; + if (uuid.indexOf('180f') !== -1) { + found = s; + break; + } + } + if (found == null) { + // fallback: if writeCharId exists and notify available use protocol (not implemented) + return 0; + } + const foundUuid = found!.uuid; + const charsRaw = await this.bluetoothService!.getCharacteristics(deviceId, foundUuid); + const chars: BleCharacteristic[] = charsRaw; + const batChar = chars.find((c: BleCharacteristic): boolean => ((c.properties != null && c.properties.read) || (c.uuid != null && ('' + c.uuid).toLowerCase().includes('2a19')))); + if (batChar == null) + return 0; + const buf = await this.bluetoothService!.readCharacteristic(deviceId, foundUuid, batChar.uuid); + const arr = new Uint8Array(buf); + if (arr.length > 0) { + return arr[0]; + } + return 0; + } + // testVersionInfo: try to read Device Information characteristics or return empty + async testVersionInfo(hw: boolean): Promise { + // copy to local so Kotlin generator can smart-cast the value across awaits + const deviceId = this.deviceId; + if (deviceId == null) + return ''; + // Device Information service 180A, characteristics: 2A26 (SW), 2A27 (HW) sometimes + if (this.bluetoothService == null) + return ''; + const _services = await this.bluetoothService!.getServices(deviceId); + const services2: BleService[] = _services; + let found2: BleService | null = null; + for (let i = 0; i < services2.length; i++) { + const s = services2[i]; + const uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null); + const uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : ''; + if (uuid.indexOf('180a') !== -1) { + found2 = s; + break; + } + } + if (found2 == null) + return ''; + const _found2 = found2; + const found2Uuid = _found2!.uuid; + const chars = await this.bluetoothService!.getCharacteristics(deviceId, found2Uuid); + const target = chars.find((c): boolean => { + const id = ('' + c.uuid).toLowerCase(); + if (hw) + return id.includes('2a27') || id.includes('hardware'); + return id.includes('2a26') || id.includes('software'); + }); + if (target == null) + return ''; + const buf = await this.bluetoothService!.readCharacteristic(deviceId, found2Uuid, target.uuid); + try { + return new TextDecoder().decode(new Uint8Array(buf)); + } + catch (e: any) { + return ''; + } + } +} +//# sourceMappingURL=protocol_handler.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts.map new file mode 100644 index 0000000..212eea6 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/protocol_handler.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"protocol_handler.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/protocol_handler.uts"],"names":[],"mappings":"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","sourcesContent":["// Minimal ProtocolHandler runtime class used by pages and components.\r\n// This class adapts the platform `BluetoothService` to a small protocol API\r\n// expected by pages: setConnectionParameters, initialize, testBatteryLevel,\r\n// testVersionInfo. Implemented conservatively to avoid heavy dependencies.\r\n\r\nimport type { BluetoothService, AutoBleInterfaces, AutoDiscoverAllResult, BleService, BleCharacteristic, BleProtocolType, BleDevice, ScanDevicesOptions, BleConnectOptionsExt, SendDataPayload, BleOptions } from './interface.uts'\r\n\r\nexport class ProtocolHandler {\r\n\t// bluetoothService may be omitted for lightweight wrappers; allow null\r\n\tbluetoothService: BluetoothService | null = null\r\n\tprotocol: BleProtocolType = 'standard'\r\n\tdeviceId: string | null = null\r\n\tserviceId: string | null = null\r\n\twriteCharId: string | null = null\r\n\tnotifyCharId: string | null = null\r\n\tinitialized: boolean = false\r\n\r\n\t// Accept an optional BluetoothService so wrapper subclasses can call\r\n\t// `super()` without forcing a runtime instance.\r\n\tconstructor(bluetoothService?: BluetoothService) {\r\n\t\tif (bluetoothService != null) this.bluetoothService = bluetoothService\r\n\t}\r\n\r\n\tsetConnectionParameters(deviceId: string, serviceId: string, writeCharId: string, notifyCharId: string) {\r\n\t\tthis.deviceId = deviceId\r\n\t\tthis.serviceId = serviceId\r\n\t\tthis.writeCharId = writeCharId\r\n\t\tthis.notifyCharId = notifyCharId\r\n\t}\r\n\r\n\t// initialize: optional setup, returns a Promise that resolves when ready\r\n\tasync initialize(): Promise {\r\n\t\t// Simple async initializer — keep implementation minimal and generator-friendly.\r\n\t\ttry {\r\n\t\t\t// If bluetoothService exposes any protocol-specific setup, call it here.\r\n\t\t\tthis.initialized = true\r\n\t\t\treturn\r\n\t\t} catch (e) {\r\n\t\t\tthrow e\r\n\t\t}\r\n\t}\r\n\r\n\t// Protocol lifecycle / operations — default no-ops so generated code has\r\n\t// concrete member references and platform-specific handlers can override.\r\n\tasync scanDevices(options?: ScanDevicesOptions): Promise { return; }\r\n\tasync connect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return; }\r\n\tasync disconnect(device: BleDevice): Promise { return; }\r\n\tasync sendData(device: BleDevice, payload?: SendDataPayload, options?: BleOptions): Promise { return; }\r\n\tasync autoConnect(device: BleDevice, options?: BleConnectOptionsExt): Promise { return { serviceId: '', writeCharId: '', notifyCharId: '' }; }\r\n\r\n\t// Example: testBatteryLevel will attempt to read the battery characteristic\r\n\t// if write/notify-based protocol is not available. Returns number percentage.\r\n\tasync testBatteryLevel(): Promise {\r\n\t\tif (this.deviceId == null) throw new Error('deviceId not set')\r\n\t\t// copy to local so Kotlin generator can smart-cast the value across awaits\r\n\t\tconst deviceId = this.deviceId\r\n\t\t// try reading standard Battery characteristic (180F -> 2A19)\r\n\t\tif (this.bluetoothService == null) throw new Error('bluetoothService not set')\r\n\t\tconst services = await this.bluetoothService.getServices(deviceId)\r\n\r\n\t\r\n\tlet found: BleService | null = null\r\n\t\tfor (let i = 0; i < services.length; i++) {\r\n\t\t\tconst s = services[i]\r\n\t\t\tconst uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null)\r\n\t\t\tconst uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : ''\r\n\t\t\tif (uuid.indexOf('180f') !== -1) { found = s; break }\r\n\t\t}\r\n\t\tif (found == null) {\r\n\t\t\t// fallback: if writeCharId exists and notify available use protocol (not implemented)\r\n\t\t\treturn 0\r\n\t\t}\r\n\tconst foundUuid = found!.uuid\r\n\tconst charsRaw = await this.bluetoothService.getCharacteristics(deviceId, foundUuid)\r\n\tconst chars: BleCharacteristic[] = charsRaw\r\n\tconst batChar = chars.find((c: BleCharacteristic) => ((c.properties != null && c.properties.read) || (c.uuid != null && ('' + c.uuid).toLowerCase().includes('2a19'))))\r\n\t\tif (batChar == null) return 0\r\n\tconst buf = await this.bluetoothService.readCharacteristic(deviceId, foundUuid, batChar.uuid)\r\n\t\tconst arr = new Uint8Array(buf)\r\n\t\tif (arr.length > 0) {\r\n\t\t\treturn arr[0]\r\n\t\t}\r\n\t\treturn 0\r\n\t}\r\n\r\n\t// testVersionInfo: try to read Device Information characteristics or return empty\r\n\tasync testVersionInfo(hw: boolean): Promise {\r\n\t\t// copy to local so Kotlin generator can smart-cast the value across awaits\r\n\t\tconst deviceId = this.deviceId\r\n\t\tif (deviceId == null) return ''\r\n\t\t// Device Information service 180A, characteristics: 2A26 (SW), 2A27 (HW) sometimes\r\n\t\tif (this.bluetoothService == null) return ''\r\n\t\tconst _services = await this.bluetoothService.getServices(deviceId)\r\n\t\tconst services2: BleService[] = _services \r\n\t\tlet found2: BleService | null = null\r\n\t\tfor (let i = 0; i < services2.length; i++) {\r\n\t\t\tconst s = services2[i]\r\n\t\t\tconst uuidCandidate: string | null = (s != null && s.uuid != null ? s.uuid : null)\r\n\t\t\tconst uuid = uuidCandidate != null ? ('' + uuidCandidate).toLowerCase() : ''\r\n\t\t\tif (uuid.indexOf('180a') !== -1) { found2 = s; break }\r\n\t\t}\r\n\t\tif (found2 == null) return ''\r\n\t\tconst _found2 = found2\r\n\t\tconst found2Uuid = _found2!.uuid\r\n\t\tconst chars = await this.bluetoothService.getCharacteristics(deviceId, found2Uuid)\r\n\t\tconst target = chars.find((c) => {\r\n\t\t\tconst id = ('' + c.uuid).toLowerCase()\r\n\t\t\tif (hw) return id.includes('2a27') || id.includes('hardware')\r\n\t\t\treturn id.includes('2a26') || id.includes('software')\r\n\t\t})\r\n\t\tif (target == null) return ''\r\n\tconst buf = await this.bluetoothService.readCharacteristic(deviceId, found2Uuid, target.uuid)\r\n\ttry { return new TextDecoder().decode(new Uint8Array(buf)) } catch (e) { return '' }\r\n\t}\r\n}\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts new file mode 100644 index 0000000..01d47bf --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts @@ -0,0 +1,33 @@ +// Minimal error definitions used across the BLE module. +// Keep this file small and avoid runtime dependencies; it's mainly for typing and +// simple runtime error construction used by native platform code. +export enum AkBluetoothErrorCode { + UnknownError = 0, + DeviceNotFound = 1, + ServiceNotFound = 2, + CharacteristicNotFound = 3, + ConnectionTimeout = 4, + Unspecified = 99 +} +export class AkBleErrorImpl extends Error { + public code: AkBluetoothErrorCode; + public detail: any | null; + constructor(code: AkBluetoothErrorCode, message?: string, detail: any | null = null) { + super(message ?? AkBleErrorImpl.defaultMessage(code)); + this.name = 'AkBleError'; + this.code = code; + this.detail = detail; + } + static defaultMessage(code: AkBluetoothErrorCode): string { + switch (code) { + case AkBluetoothErrorCode.DeviceNotFound: return 'Device not found'; + case AkBluetoothErrorCode.ServiceNotFound: return 'Service not found'; + case AkBluetoothErrorCode.CharacteristicNotFound: return 'Characteristic not found'; + case AkBluetoothErrorCode.ConnectionTimeout: return 'Connection timed out'; + case AkBluetoothErrorCode.UnknownError: + default: return 'Unknown Bluetooth error'; + } + } +} +export default AkBleErrorImpl; +//# sourceMappingURL=unierror.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts.map new file mode 100644 index 0000000..ec767ec --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/ak-sbsrv/utssdk/unierror.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"unierror.uts","sourceRoot":"","sources":["uni_modules/ak-sbsrv/utssdk/unierror.uts"],"names":[],"mappings":"AAAA,wDAAwD;AACxD,kFAAkF;AAClF,kEAAkE;AAElE,MAAM,MAAM,oBAAoB;IAC/B,YAAY,GAAG,CAAC;IAChB,cAAc,GAAG,CAAC;IAClB,eAAe,GAAG,CAAC;IACnB,sBAAsB,GAAG,CAAC;IAC1B,iBAAiB,GAAG,CAAC;IACrB,WAAW,GAAG,EAAE;CAChB;AAED,MAAM,OAAO,cAAe,SAAQ,KAAK;IACxC,MAAM,CAAC,IAAI,EAAE,oBAAoB,CAAC;IAClC,MAAM,CAAC,MAAM,EAAE,GAAG,GAAC,IAAI,CAAC;IACxB,YAAY,IAAI,EAAE,oBAAoB,EAAE,OAAO,CAAC,EAAE,MAAM,EAAE,MAAM,EAAE,GAAG,GAAC,IAAI,GAAG,IAAI;QAChF,KAAK,CAAC,OAAO,IAAI,cAAc,CAAC,cAAc,CAAC,IAAI,CAAC,CAAC,CAAC;QACtD,IAAI,CAAC,IAAI,GAAG,YAAY,CAAC;QACzB,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC;QACjB,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;IACtB,CAAC;IACD,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,oBAAoB;QAC/C,QAAQ,IAAI,EAAE;YACb,KAAK,oBAAoB,CAAC,cAAc,CAAC,CAAC,OAAO,kBAAkB,CAAC;YACpE,KAAK,oBAAoB,CAAC,eAAe,CAAC,CAAC,OAAO,mBAAmB,CAAC;YACtE,KAAK,oBAAoB,CAAC,sBAAsB,CAAC,CAAC,OAAO,0BAA0B,CAAC;YACpF,KAAK,oBAAoB,CAAC,iBAAiB,CAAC,CAAC,OAAO,sBAAsB,CAAC;YAC3E,KAAK,oBAAoB,CAAC,YAAY,CAAC;YAAC,OAAO,CAAC,CAAC,OAAO,yBAAyB,CAAC;SAClF;IACF,CAAC;CACD;AAED,eAAe,cAAc,CAAC","sourcesContent":["// Minimal error definitions used across the BLE module.\r\n// Keep this file small and avoid runtime dependencies; it's mainly for typing and\r\n// simple runtime error construction used by native platform code.\r\n\r\nexport enum AkBluetoothErrorCode {\r\n\tUnknownError = 0,\r\n\tDeviceNotFound = 1,\r\n\tServiceNotFound = 2,\r\n\tCharacteristicNotFound = 3,\r\n\tConnectionTimeout = 4,\r\n\tUnspecified = 99\r\n}\r\n\r\nexport class AkBleErrorImpl extends Error {\r\n\tpublic code: AkBluetoothErrorCode;\r\n\tpublic detail: any|null;\n\tconstructor(code: AkBluetoothErrorCode, message?: string, detail: any|null = null) {\r\n\t\tsuper(message ?? AkBleErrorImpl.defaultMessage(code));\r\n\t\tthis.name = 'AkBleError';\r\n\t\tthis.code = code;\r\n\t\tthis.detail = detail;\r\n\t}\r\n\tstatic defaultMessage(code: AkBluetoothErrorCode) {\r\n\t\tswitch (code) {\r\n\t\t\tcase AkBluetoothErrorCode.DeviceNotFound: return 'Device not found';\r\n\t\t\tcase AkBluetoothErrorCode.ServiceNotFound: return 'Service not found';\r\n\t\t\tcase AkBluetoothErrorCode.CharacteristicNotFound: return 'Characteristic not found';\r\n\t\t\tcase AkBluetoothErrorCode.ConnectionTimeout: return 'Connection timed out';\r\n\t\t\tcase AkBluetoothErrorCode.UnknownError: default: return 'Unknown Bluetooth error';\r\n\t\t}\r\n\t}\r\n}\r\n\r\nexport default AkBleErrorImpl;\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts new file mode 100644 index 0000000..2e56a91 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts @@ -0,0 +1,62 @@ +import Context from "android.content.Context"; +import BatteryManager from "android.os.BatteryManager"; +import { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts'; +import IntentFilter from 'android.content.IntentFilter'; +import Intent from 'android.content.Intent'; +import { GetBatteryInfoFailImpl } from '../unierror'; +/** + * 异步获取电量 + */ +export const getBatteryInfo: GetBatteryInfo = function (options: GetBatteryInfoOptions) { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const manager = context.getSystemService(Context.BATTERY_SERVICE) as BatteryManager; + const level = manager.getIntProperty(BatteryManager.BATTERY_PROPERTY_CAPACITY); + let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED); + let batteryStatus = context.registerReceiver(null, ifilter); + let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1); + let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL; + const res: GetBatteryInfoSuccess = { + errMsg: 'getBatteryInfo:ok', + level, + isCharging: isCharging + }; + options.success?.(res); + options.complete?.(res); + } + else { + let res = new GetBatteryInfoFailImpl(1001); + options.fail?.(res); + options.complete?.(res); + } +}; +/** + * 同步获取电量 + */ +export const getBatteryInfoSync: GetBatteryInfoSync = function (): GetBatteryInfoResult { + const context = UTSAndroid.getAppContext(); + if (context != null) { + const manager = context.getSystemService(Context.BATTERY_SERVICE) as BatteryManager; + const level = manager.getIntProperty(BatteryManager.BATTERY_PROPERTY_CAPACITY); + let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED); + let batteryStatus = context.registerReceiver(null, ifilter); + let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1); + let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL; + const res: GetBatteryInfoResult = { + level: level, + isCharging: isCharging + }; + return res; + } + else { + /** + * 无有效上下文 + */ + const res: GetBatteryInfoResult = { + level: -1, + isCharging: false + }; + return res; + } +}; +//# sourceMappingURL=index.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts.map new file mode 100644 index 0000000..9b23eb1 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"index.uts","sourceRoot":"","sources":["uni_modules/uni-getbatteryinfo/utssdk/app-android/index.uts"],"names":[],"mappings":"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","sourcesContent":["import Context from \"android.content.Context\";\r\nimport BatteryManager from \"android.os.BatteryManager\";\r\n\r\nimport { GetBatteryInfo, GetBatteryInfoOptions, GetBatteryInfoSuccess, GetBatteryInfoResult, GetBatteryInfoSync } from '../interface.uts'\r\nimport IntentFilter from 'android.content.IntentFilter';\r\nimport Intent from 'android.content.Intent';\r\n\r\nimport { GetBatteryInfoFailImpl } from '../unierror';\r\n\r\n/**\r\n * 异步获取电量\r\n */\r\nexport const getBatteryInfo : GetBatteryInfo = function (options : GetBatteryInfoOptions) {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoSuccess = {\r\n errMsg: 'getBatteryInfo:ok',\r\n level,\r\n isCharging: isCharging\r\n }\r\n options.success?.(res)\r\n options.complete?.(res)\r\n } else {\r\n let res = new GetBatteryInfoFailImpl(1001);\r\n options.fail?.(res)\r\n options.complete?.(res)\r\n }\r\n}\r\n\r\n/**\r\n * 同步获取电量\r\n */\r\nexport const getBatteryInfoSync : GetBatteryInfoSync = function () : GetBatteryInfoResult {\r\n const context = UTSAndroid.getAppContext();\r\n if (context != null) {\r\n const manager = context.getSystemService(\r\n Context.BATTERY_SERVICE\r\n ) as BatteryManager;\r\n const level = manager.getIntProperty(\r\n BatteryManager.BATTERY_PROPERTY_CAPACITY\r\n );\r\n\r\n let ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);\r\n let batteryStatus = context.registerReceiver(null, ifilter);\r\n let status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1);\r\n let isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL;\r\n\r\n const res : GetBatteryInfoResult = {\r\n level: level,\r\n isCharging: isCharging\r\n };\r\n return res;\r\n }\r\n else {\r\n /**\r\n * 无有效上下文\r\n */\r\n const res : GetBatteryInfoResult = {\r\n level: -1,\r\n isCharging: false\r\n };\r\n return res;\r\n }\r\n}\r\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts new file mode 100644 index 0000000..12a3059 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts @@ -0,0 +1,131 @@ +export type GetBatteryInfoSuccess = { + errMsg: string; + /** + * 设备电量,范围1 - 100 + */ + level: number; + /** + * 是否正在充电中 + */ + isCharging: boolean; +}; +export type GetBatteryInfoOptions = { + /** + * 接口调用结束的回调函数(调用成功、失败都会执行) + */ + success?: (res: GetBatteryInfoSuccess) => void; + /** + * 接口调用失败的回调函数 + */ + fail?: (res: UniError) => void; + /** + * 接口调用成功的回调 + */ + complete?: (res: any) => void; +}; +export type GetBatteryInfoResult = { + /** + * 设备电量,范围1 - 100 + */ + level: number; + /** + * 是否正在充电中 + */ + isCharging: boolean; +}; +/** + * 错误码 + * - 1001 getAppContext is null + */ +export type GetBatteryInfoErrorCode = 1001; +/** + * GetBatteryInfo 的错误回调参数 + */ +export interface GetBatteryInfoFail extends IUniError { + errCode: GetBatteryInfoErrorCode; +} +; +/** +* 获取电量信息 +* @param {GetBatteryInfoOptions} options +* +* +* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html +* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22 +* @since 3.6.11 +* +* @assert () => success({errCode: 0, errSubject: "uni-getBatteryInfo", errMsg: "getBatteryInfo:ok", level: 60, isCharging: false }) +* @assert () => fail({errCode: 1001, errSubject: "uni-getBatteryInfo", errMsg: "getBatteryInfo:fail getAppContext is null" }) +*/ +export type GetBatteryInfo = (options: GetBatteryInfoOptions) => void; +export type GetBatteryInfoSync = () => GetBatteryInfoResult; +interface Uni { + /** + * 获取电池电量信息 + * @description 获取电池电量信息 + * @param {GetBatteryInfoOptions} options + * @example + * ```typescript + * uni.getBatteryInfo({ + * success(res) { + * __f__('log','at uni_modules/uni-getbatteryinfo/utssdk/interface.uts:78',res); + * } + * }) + * ``` + * @remark + * - 该接口需要同步调用 + * @uniPlatform { + * "app": { + * "android": { + * "osVer": "4.4.4", + * "uniVer": "3.6.11", + * "unixVer": "3.9.0" + * }, + * "ios": { + * "osVer": "12.0", + * "uniVer": "3.6.11", + * "unixVer": "4.11" + * } + * }, + * "web": { + * "uniVer": "3.6.11", + * "unixVer": "4.0" + * } + * } + * @uniVueVersion 2,3 //支持的vue版本 + * + */ + getBatteryInfo(options: GetBatteryInfoOptions): void; + /** + * 同步获取电池电量信息 + * @description 获取电池电量信息 + * @example + * ```typescript + * uni.getBatteryInfo() + * ``` + * @remark + * - 该接口需要同步调用 + * @uniPlatform { + * "app": { + * "android": { + * "osVer": "4.4.4", + * "uniVer": "3.6.11", + * "unixVer": "3.9.0" + * }, + * "ios": { + * "osVer": "12.0", + * "uniVer": "3.6.11", + * "unixVer": "4.11" + * } + * }, + * "web": { + * "uniVer": "3.6.11", + * "unixVer": "4.0" + * } + * } + * @uniVueVersion 2,3 //支持的vue版本 + * + */ + getBatteryInfoSync(): GetBatteryInfoResult; +} +//# sourceMappingURL=interface.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts.map new file mode 100644 index 0000000..516ceee --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/interface.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"interface.uts","sourceRoot":"","sources":["uni_modules/uni-getbatteryinfo/utssdk/interface.uts"],"names":[],"mappings":"AAAA,MAAM,MAAM,qBAAqB,GAAG;IACnC,MAAM,EAAG,MAAM,CAAC;IAChB;;MAEE;IACF,KAAK,EAAG,MAAM,CAAC;IACf;;MAEE;IACF,UAAU,EAAG,OAAO,CAAA;CACpB,CAAA;AAED,MAAM,MAAM,qBAAqB,GAAG;IACnC;;UAEG;IACH,OAAQ,CAAC,EAAE,CAAC,GAAG,EAAG,qBAAqB,KAAK,IAAI,CAAA;IAChD;;UAEG;IACH,IAAK,CAAC,EAAE,CAAC,GAAG,EAAG,QAAQ,KAAK,IAAI,CAAA;IAChC;;UAEG;IACH,QAAS,CAAC,EAAE,CAAC,GAAG,EAAG,GAAG,KAAK,IAAI,CAAA;CAC/B,CAAA;AAED,MAAM,MAAM,oBAAoB,GAAG;IAClC;;MAEE;IACF,KAAK,EAAG,MAAM,CAAC;IACf;;MAEE;IACF,UAAU,EAAG,OAAO,CAAA;CACpB,CAAA;AAED;;;GAGG;AACH,MAAM,MAAM,uBAAuB,GAAG,IAAI,CAAE;AAC5C;;GAEG;AACH,MAAM,WAAW,kBAAmB,SAAQ,SAAS;IACnD,OAAO,EAAG,uBAAuB,CAAA;CAClC;AAAA,CAAC;AAEF;;;;;;;;;;;EAWE;AACF,MAAM,MAAM,cAAc,GAAG,CAAC,OAAO,EAAG,qBAAqB,KAAK,IAAI,CAAA;AAGtE,MAAM,MAAM,kBAAkB,GAAG,MAAM,oBAAoB,CAAA;AAE3D,UAAU,GAAG;IAEZ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OAkCG;IACH,cAAc,CAAE,OAAO,EAAG,qBAAqB,GAAI,IAAI,CAAC;IACxD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OA6BG;IACH,kBAAkB,IAAG,oBAAoB,CAAA;CAEzC","sourcesContent":["export type GetBatteryInfoSuccess = {\n\terrMsg : string,\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\nexport type GetBatteryInfoOptions = {\n\t/**\n\t\t* 接口调用结束的回调函数(调用成功、失败都会执行)\n\t\t*/\n\tsuccess ?: (res : GetBatteryInfoSuccess) => void\n\t/**\n\t\t* 接口调用失败的回调函数\n\t\t*/\n\tfail ?: (res : UniError) => void\n\t/**\n\t\t* 接口调用成功的回调\n\t\t*/\n\tcomplete ?: (res : any) => void\n}\n\nexport type GetBatteryInfoResult = {\n\t/**\n\t* 设备电量,范围1 - 100\n\t*/\n\tlevel : number,\n\t/**\n\t* 是否正在充电中\n\t*/\n\tisCharging : boolean\n}\n\n/**\n * 错误码\n * - 1001 getAppContext is null\n */\nexport type GetBatteryInfoErrorCode = 1001 ;\n/**\n * GetBatteryInfo 的错误回调参数\n */\nexport interface GetBatteryInfoFail extends IUniError {\n errCode : GetBatteryInfoErrorCode\n};\n\n/**\n* 获取电量信息\n* @param {GetBatteryInfoOptions} options\n*\n*\n* @tutorial https://uniapp.dcloud.net.cn/api/system/batteryInfo.html\n* @platforms APP-IOS = ^9.0,APP-ANDROID = ^22\n* @since 3.6.11\n*\n* @assert () => success({errCode: 0, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:ok\", level: 60, isCharging: false })\n* @assert () => fail({errCode: 1001, errSubject: \"uni-getBatteryInfo\", errMsg: \"getBatteryInfo:fail getAppContext is null\" })\n*/\nexport type GetBatteryInfo = (options : GetBatteryInfoOptions) => void\n\n\nexport type GetBatteryInfoSync = () => GetBatteryInfoResult\n\ninterface Uni {\n\n\t/**\n\t * 获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @param {GetBatteryInfoOptions} options\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo({\n\t *\t\tsuccess(res) {\n\t *\t\t\t__f__('log','at uni_modules/uni-getbatteryinfo/utssdk/interface.uts:78',res);\n\t *\t\t}\n\t * })\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfo (options : GetBatteryInfoOptions) : void,\n\t/**\n\t * 同步获取电池电量信息\n\t * @description 获取电池电量信息\n\t * @example\n\t * ```typescript\n\t * uni.getBatteryInfo()\n\t * ```\n\t * @remark\n\t * - 该接口需要同步调用\n\t * @uniPlatform {\n\t * \"app\": {\n\t * \"android\": {\n\t * \"osVer\": \"4.4.4\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"3.9.0\"\n\t * },\n\t * \"ios\": {\n\t * \"osVer\": \"12.0\",\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.11\"\n\t * }\n\t * },\n\t * \"web\": {\n\t * \"uniVer\": \"3.6.11\",\n\t * \"unixVer\": \"4.0\"\n\t * }\n\t * }\n\t * @uniVueVersion 2,3 //支持的vue版本\n\t *\n\t */\n\tgetBatteryInfoSync():GetBatteryInfoResult\n\n}\n"]} \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts new file mode 100644 index 0000000..b8a1000 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts @@ -0,0 +1,30 @@ +import { GetBatteryInfoErrorCode, GetBatteryInfoFail } from "./interface.uts"; +/** + * 错误主题 + */ +export const UniErrorSubject = 'uni-getBatteryInfo'; +/** + * 错误信息 + * @UniError + */ +export const UniErrors: Map = new Map([ + /** + * 错误码及对应的错误信息 + */ + [1001, 'getBatteryInfo:fail getAppContext is null'], +]); +/** + * 错误对象实现 + */ +export class GetBatteryInfoFailImpl extends UniError implements GetBatteryInfoFail { + /** + * 错误对象构造函数 + */ + constructor(errCode: GetBatteryInfoErrorCode) { + super(); + this.errSubject = UniErrorSubject; + this.errCode = errCode; + this.errMsg = UniErrors[errCode] ?? ""; + } +} +//# sourceMappingURL=unierror.uts.map \ No newline at end of file diff --git a/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts.map b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts.map new file mode 100644 index 0000000..8dd5e50 --- /dev/null +++ b/unpackage/dist/dev/.uvue/app-android/uni_modules/uni-getbatteryinfo/utssdk/unierror.uts.map @@ -0,0 +1 @@ +{"version":3,"file":"unierror.uts","sourceRoot":"","sources":["uni_modules/uni-getbatteryinfo/utssdk/unierror.uts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAA;AAC7E;;GAEG;AACH,MAAM,CAAC,MAAM,eAAe,GAAG,oBAAoB,CAAC;AAGpD;;;GAGG;AACH,MAAM,CAAC,MAAM,SAAS,EAAG,GAAG,CAAC,uBAAuB,EAAE,MAAM,CAAC,GAAG,IAAI,GAAG,CAAC;IACtE;;OAEG;IACH,CAAC,IAAI,EAAE,2CAA2C,CAAC;CACpD,CAAC,CAAC;AAGH;;GAEG;AACH,MAAM,OAAO,sBAAuB,SAAQ,QAAS,YAAW,kBAAkB;IAEhF;;OAEG;IACH,YAAY,OAAO,EAAG,uBAAuB;QAC3C,KAAK,EAAE,CAAC;QACR,IAAI,CAAC,UAAU,GAAG,eAAe,CAAC;QAClC,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACvB,IAAI,CAAC,MAAM,GAAG,SAAS,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC;IACzC,CAAC;CACF","sourcesContent":["import { GetBatteryInfoErrorCode, GetBatteryInfoFail } from \"./interface.uts\"\r\n/**\r\n * 错误主题\r\n */\r\nexport const UniErrorSubject = 'uni-getBatteryInfo';\r\n\r\n\r\n/**\r\n * 错误信息\r\n * @UniError\r\n */\r\nexport const UniErrors : Map = new Map([\r\n /**\r\n * 错误码及对应的错误信息\r\n */\r\n [1001, 'getBatteryInfo:fail getAppContext is null'],\r\n]);\r\n\r\n\r\n/**\r\n * 错误对象实现\r\n */\r\nexport class GetBatteryInfoFailImpl extends UniError implements GetBatteryInfoFail {\r\n\r\n /**\r\n * 错误对象构造函数\r\n */\r\n constructor(errCode : GetBatteryInfoErrorCode) {\r\n super();\r\n this.errSubject = UniErrorSubject;\r\n this.errCode = errCode;\r\n this.errMsg = UniErrors[errCode] ?? \"\";\r\n }\r\n}"]} \ No newline at end of file diff --git a/unpackage/dist/dev/app-android/index/classes.dex b/unpackage/dist/dev/app-android/index/classes.dex new file mode 100644 index 0000000..2469776 Binary files /dev/null and b/unpackage/dist/dev/app-android/index/classes.dex differ diff --git a/unpackage/dist/dev/app-android/manifest.json b/unpackage/dist/dev/app-android/manifest.json new file mode 100644 index 0000000..177657b --- /dev/null +++ b/unpackage/dist/dev/app-android/manifest.json @@ -0,0 +1,28 @@ +{ + "id": "__UNI__95B2570", + "name": "akbleserver", + "description": "", + "version": { + "name": "1.0.1", + "code": "101" + }, + "uni-app-x": { + "compilerVersion": "4.76" + }, + "app-android": { + "distribute": { + "modules": { + "FileSystem": {} + }, + "icons": { + "hdpi": "unpackage/res/icons/72x72.png", + "xhdpi": "unpackage/res/icons/96x96.png", + "xxhdpi": "unpackage/res/icons/144x144.png", + "xxxhdpi": "unpackage/res/icons/192x192.png" + }, + "splashScreens": { + "default": {} + } + } + } +} \ No newline at end of file diff --git a/unpackage/dist/dev/app-android/pages/akbletest/classes.dex b/unpackage/dist/dev/app-android/pages/akbletest/classes.dex new file mode 100644 index 0000000..0c2da51 Binary files /dev/null and b/unpackage/dist/dev/app-android/pages/akbletest/classes.dex differ diff --git a/unpackage/dist/dev/app-android/static/OmFw2509140009.zip b/unpackage/dist/dev/app-android/static/OmFw2509140009.zip new file mode 100644 index 0000000..5b7b661 Binary files /dev/null and b/unpackage/dist/dev/app-android/static/OmFw2509140009.zip differ diff --git a/unpackage/dist/dev/app-android/static/OmFw2510150943.zip b/unpackage/dist/dev/app-android/static/OmFw2510150943.zip new file mode 100644 index 0000000..dacb75e Binary files /dev/null and b/unpackage/dist/dev/app-android/static/OmFw2510150943.zip differ diff --git a/unpackage/dist/dev/app-android/static/logo.png b/unpackage/dist/dev/app-android/static/logo.png new file mode 100644 index 0000000..b5771e2 Binary files /dev/null and b/unpackage/dist/dev/app-android/static/logo.png differ diff --git a/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/classes.dex b/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/classes.dex new file mode 100644 index 0000000..55d93fb Binary files /dev/null and b/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/classes.dex differ diff --git a/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/config.json b/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/config.json new file mode 100644 index 0000000..bf95925 --- /dev/null +++ b/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/config.json @@ -0,0 +1,3 @@ +{ + "minSdkVersion": "21" +} \ No newline at end of file diff --git a/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.kt b/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.kt new file mode 100644 index 0000000..4323a4f --- /dev/null +++ b/unpackage/dist/dev/app-android/uni_modules/uni-getbatteryinfo/utssdk/app-android/index.kt @@ -0,0 +1,109 @@ +@file:Suppress("UNCHECKED_CAST", "USELESS_CAST", "INAPPLICABLE_JVM_NAME", "UNUSED_ANONYMOUS_PARAMETER", "NAME_SHADOWING", "UNNECESSARY_NOT_NULL_ASSERTION") +package uts.sdk.modules.uniGetbatteryinfo +import android.content.Context +import android.content.Intent +import android.content.IntentFilter +import android.os.BatteryManager +import io.dcloud.uniapp.* +import io.dcloud.uniapp.extapi.* +import io.dcloud.uniapp.framework.* +import io.dcloud.uniapp.runtime.* +import io.dcloud.uniapp.vue.* +import io.dcloud.uniapp.vue.shared.* +import io.dcloud.unicloud.* +import io.dcloud.uts.* +import io.dcloud.uts.Map +import io.dcloud.uts.Set +import io.dcloud.uts.UTSAndroid +import kotlinx.coroutines.CoroutineScope +import kotlinx.coroutines.Deferred +import kotlinx.coroutines.Dispatchers +import kotlinx.coroutines.async +open class GetBatteryInfoSuccess ( + @JsonNotNull + open var errMsg: String, + @JsonNotNull + open var level: Number, + @JsonNotNull + open var isCharging: Boolean = false, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoSuccess", "uni_modules/uni-getbatteryinfo/utssdk/interface.uts", 1, 13) + } +} +open class GetBatteryInfoOptions ( + open var success: ((res: GetBatteryInfoSuccess) -> Unit)? = null, + open var fail: ((res: UniError) -> Unit)? = null, + open var complete: ((res: Any) -> Unit)? = null, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoOptions", "uni_modules/uni-getbatteryinfo/utssdk/interface.uts", 12, 13) + } +} +open class GetBatteryInfoResult ( + @JsonNotNull + open var level: Number, + @JsonNotNull + open var isCharging: Boolean = false, +) : UTSObject(), IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoResult", "uni_modules/uni-getbatteryinfo/utssdk/interface.uts", 26, 13) + } +} +typealias GetBatteryInfoErrorCode = Number +interface GetBatteryInfoFail : IUniError { + override var errCode: GetBatteryInfoErrorCode +} +typealias GetBatteryInfo = (options: GetBatteryInfoOptions) -> Unit +typealias GetBatteryInfoSync = () -> GetBatteryInfoResult +val UniErrorSubject = "uni-getBatteryInfo" +val UniErrors: Map = Map(_uA( + _uA( + 1001, + "getBatteryInfo:fail getAppContext is null" + ) +)) +open class GetBatteryInfoFailImpl : UniError, GetBatteryInfoFail, IUTSSourceMap { + override fun `__$getOriginalPosition`(): UTSSourceMapPosition? { + return UTSSourceMapPosition("GetBatteryInfoFailImpl", "uni_modules/uni-getbatteryinfo/utssdk/unierror.uts", 19, 14) + } + constructor(errCode: GetBatteryInfoErrorCode) : super() { + this.errSubject = UniErrorSubject + this.errCode = errCode + this.errMsg = UniErrors[errCode] ?: "" + } +} +val getBatteryInfo: GetBatteryInfo = fun(options: GetBatteryInfoOptions) { + val context = UTSAndroid.getAppContext() + if (context != null) { + val manager = context.getSystemService(Context.BATTERY_SERVICE) as BatteryManager + val level = manager.getIntProperty(BatteryManager.BATTERY_PROPERTY_CAPACITY) + var ifilter = IntentFilter(Intent.ACTION_BATTERY_CHANGED) + var batteryStatus = context.registerReceiver(null, ifilter) + var status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1) + var isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL + val res = GetBatteryInfoSuccess(errMsg = "getBatteryInfo:ok", level = level, isCharging = isCharging) + options.success?.invoke(res) + options.complete?.invoke(res) + } else { + var res = GetBatteryInfoFailImpl(1001) + options.fail?.invoke(res) + options.complete?.invoke(res) + } +} +val getBatteryInfoSync: GetBatteryInfoSync = fun(): GetBatteryInfoResult { + val context = UTSAndroid.getAppContext() + if (context != null) { + val manager = context.getSystemService(Context.BATTERY_SERVICE) as BatteryManager + val level = manager.getIntProperty(BatteryManager.BATTERY_PROPERTY_CAPACITY) + var ifilter = IntentFilter(Intent.ACTION_BATTERY_CHANGED) + var batteryStatus = context.registerReceiver(null, ifilter) + var status = batteryStatus?.getIntExtra(BatteryManager.EXTRA_STATUS, -1) + var isCharging = status == BatteryManager.BATTERY_STATUS_CHARGING || status == BatteryManager.BATTERY_STATUS_FULL + val res = GetBatteryInfoResult(level = level, isCharging = isCharging) + return res + } else { + val res = GetBatteryInfoResult(level = -1, isCharging = false) + return res + } +} diff --git a/unpackage/res/icons/1024x1024.png b/unpackage/res/icons/1024x1024.png new file mode 100644 index 0000000..5e2ed32 Binary files /dev/null and b/unpackage/res/icons/1024x1024.png differ diff --git a/unpackage/res/icons/144x144.png b/unpackage/res/icons/144x144.png new file mode 100644 index 0000000..21f090e Binary files /dev/null and b/unpackage/res/icons/144x144.png differ diff --git a/unpackage/res/icons/192x192.png b/unpackage/res/icons/192x192.png new file mode 100644 index 0000000..adf2440 Binary files /dev/null and b/unpackage/res/icons/192x192.png differ diff --git a/unpackage/res/icons/72x72.png b/unpackage/res/icons/72x72.png new file mode 100644 index 0000000..ecbf0f2 Binary files /dev/null and b/unpackage/res/icons/72x72.png differ diff --git a/unpackage/res/icons/96x96.png b/unpackage/res/icons/96x96.png new file mode 100644 index 0000000..7ac1f38 Binary files /dev/null and b/unpackage/res/icons/96x96.png differ