@thelacanians/vue-native-runtime 0.1.0 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +108 -0
- package/dist/index.cjs +1686 -59
- package/dist/index.d.cts +1942 -131
- package/dist/index.d.ts +1942 -131
- package/dist/index.js +1644 -49
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -43,7 +43,7 @@ function createTextNode(text) {
|
|
|
43
43
|
};
|
|
44
44
|
return markRaw(node);
|
|
45
45
|
}
|
|
46
|
-
function createCommentNode(
|
|
46
|
+
function createCommentNode(_text) {
|
|
47
47
|
const node = {
|
|
48
48
|
id: getNextNodeId(),
|
|
49
49
|
type: "__COMMENT__",
|
|
@@ -332,9 +332,9 @@ var NativeBridgeImpl = class {
|
|
|
332
332
|
}
|
|
333
333
|
const handlers = this.globalEventHandlers.get(eventName);
|
|
334
334
|
if (handlers) {
|
|
335
|
-
handlers.forEach((
|
|
335
|
+
handlers.forEach((h28) => {
|
|
336
336
|
try {
|
|
337
|
-
|
|
337
|
+
h28(payload);
|
|
338
338
|
} catch (err) {
|
|
339
339
|
console.error(`[VueNative] Error in global event handler "${eventName}":`, err);
|
|
340
340
|
}
|
|
@@ -545,7 +545,10 @@ var VView = defineComponent({
|
|
|
545
545
|
props: {
|
|
546
546
|
style: Object,
|
|
547
547
|
testID: String,
|
|
548
|
-
accessibilityLabel: String
|
|
548
|
+
accessibilityLabel: String,
|
|
549
|
+
accessibilityRole: String,
|
|
550
|
+
accessibilityHint: String,
|
|
551
|
+
accessibilityState: Object
|
|
549
552
|
},
|
|
550
553
|
setup(props, { slots }) {
|
|
551
554
|
return () => h("VView", { ...props }, slots.default?.());
|
|
@@ -563,7 +566,10 @@ var VText = defineComponent2({
|
|
|
563
566
|
type: Boolean,
|
|
564
567
|
default: false
|
|
565
568
|
},
|
|
566
|
-
|
|
569
|
+
accessibilityLabel: String,
|
|
570
|
+
accessibilityRole: String,
|
|
571
|
+
accessibilityHint: String,
|
|
572
|
+
accessibilityState: Object
|
|
567
573
|
},
|
|
568
574
|
setup(props, { slots }) {
|
|
569
575
|
return () => h2("VText", { ...props }, slots.default?.());
|
|
@@ -585,7 +591,11 @@ var VButton = defineComponent3({
|
|
|
585
591
|
default: 0.7
|
|
586
592
|
},
|
|
587
593
|
onPress: Function,
|
|
588
|
-
onLongPress: Function
|
|
594
|
+
onLongPress: Function,
|
|
595
|
+
accessibilityLabel: String,
|
|
596
|
+
accessibilityRole: String,
|
|
597
|
+
accessibilityHint: String,
|
|
598
|
+
accessibilityState: Object
|
|
589
599
|
},
|
|
590
600
|
setup(props, { slots }) {
|
|
591
601
|
return () => h3(
|
|
@@ -635,7 +645,11 @@ var VInput = defineComponent4({
|
|
|
635
645
|
type: Boolean,
|
|
636
646
|
default: false
|
|
637
647
|
},
|
|
638
|
-
style: Object
|
|
648
|
+
style: Object,
|
|
649
|
+
accessibilityLabel: String,
|
|
650
|
+
accessibilityRole: String,
|
|
651
|
+
accessibilityHint: String,
|
|
652
|
+
accessibilityState: Object
|
|
639
653
|
},
|
|
640
654
|
emits: ["update:modelValue", "focus", "blur", "submit"],
|
|
641
655
|
setup(props, { emit }) {
|
|
@@ -663,6 +677,10 @@ var VInput = defineComponent4({
|
|
|
663
677
|
maxLength: props.maxLength,
|
|
664
678
|
multiline: props.multiline,
|
|
665
679
|
style: props.style,
|
|
680
|
+
accessibilityLabel: props.accessibilityLabel,
|
|
681
|
+
accessibilityRole: props.accessibilityRole,
|
|
682
|
+
accessibilityHint: props.accessibilityHint,
|
|
683
|
+
accessibilityState: props.accessibilityState,
|
|
666
684
|
onChangetext,
|
|
667
685
|
onFocus,
|
|
668
686
|
onBlur,
|
|
@@ -686,7 +704,11 @@ var VSwitch = defineComponent5({
|
|
|
686
704
|
},
|
|
687
705
|
onTintColor: String,
|
|
688
706
|
thumbTintColor: String,
|
|
689
|
-
style: Object
|
|
707
|
+
style: Object,
|
|
708
|
+
accessibilityLabel: String,
|
|
709
|
+
accessibilityRole: String,
|
|
710
|
+
accessibilityHint: String,
|
|
711
|
+
accessibilityState: Object
|
|
690
712
|
},
|
|
691
713
|
emits: ["update:modelValue", "change"],
|
|
692
714
|
setup(props, { emit }) {
|
|
@@ -701,6 +723,10 @@ var VSwitch = defineComponent5({
|
|
|
701
723
|
onTintColor: props.onTintColor,
|
|
702
724
|
thumbTintColor: props.thumbTintColor,
|
|
703
725
|
style: props.style,
|
|
726
|
+
accessibilityLabel: props.accessibilityLabel,
|
|
727
|
+
accessibilityRole: props.accessibilityRole,
|
|
728
|
+
accessibilityHint: props.accessibilityHint,
|
|
729
|
+
accessibilityState: props.accessibilityState,
|
|
704
730
|
onChange
|
|
705
731
|
});
|
|
706
732
|
}
|
|
@@ -773,7 +799,11 @@ var VScrollView = defineComponent7({
|
|
|
773
799
|
type: Boolean,
|
|
774
800
|
default: false
|
|
775
801
|
},
|
|
776
|
-
style: Object
|
|
802
|
+
style: Object,
|
|
803
|
+
accessibilityLabel: String,
|
|
804
|
+
accessibilityRole: String,
|
|
805
|
+
accessibilityHint: String,
|
|
806
|
+
accessibilityState: Object
|
|
777
807
|
},
|
|
778
808
|
emits: ["scroll", "refresh"],
|
|
779
809
|
setup(props, { slots, emit }) {
|
|
@@ -795,6 +825,10 @@ var VScrollView = defineComponent7({
|
|
|
795
825
|
contentContainerStyle: props.contentContainerStyle,
|
|
796
826
|
refreshing: props.refreshing,
|
|
797
827
|
style: props.style,
|
|
828
|
+
accessibilityLabel: props.accessibilityLabel,
|
|
829
|
+
accessibilityRole: props.accessibilityRole,
|
|
830
|
+
accessibilityHint: props.accessibilityHint,
|
|
831
|
+
accessibilityState: props.accessibilityState,
|
|
798
832
|
onScroll,
|
|
799
833
|
onRefresh
|
|
800
834
|
},
|
|
@@ -815,7 +849,10 @@ var VImage = defineComponent8({
|
|
|
815
849
|
},
|
|
816
850
|
style: Object,
|
|
817
851
|
testID: String,
|
|
818
|
-
accessibilityLabel: String
|
|
852
|
+
accessibilityLabel: String,
|
|
853
|
+
accessibilityRole: String,
|
|
854
|
+
accessibilityHint: String,
|
|
855
|
+
accessibilityState: Object
|
|
819
856
|
},
|
|
820
857
|
emits: ["load", "error"],
|
|
821
858
|
setup(props, { emit }) {
|
|
@@ -863,7 +900,11 @@ var VSlider = defineComponent11({
|
|
|
863
900
|
modelValue: { type: Number, default: 0 },
|
|
864
901
|
min: { type: Number, default: 0 },
|
|
865
902
|
max: { type: Number, default: 1 },
|
|
866
|
-
style: { type: Object, default: () => ({}) }
|
|
903
|
+
style: { type: Object, default: () => ({}) },
|
|
904
|
+
accessibilityLabel: String,
|
|
905
|
+
accessibilityRole: String,
|
|
906
|
+
accessibilityHint: String,
|
|
907
|
+
accessibilityState: Object
|
|
867
908
|
},
|
|
868
909
|
emits: ["update:modelValue", "change"],
|
|
869
910
|
setup(props, { emit }) {
|
|
@@ -872,6 +913,10 @@ var VSlider = defineComponent11({
|
|
|
872
913
|
value: props.modelValue,
|
|
873
914
|
minimumValue: props.min,
|
|
874
915
|
maximumValue: props.max,
|
|
916
|
+
accessibilityLabel: props.accessibilityLabel,
|
|
917
|
+
accessibilityRole: props.accessibilityRole,
|
|
918
|
+
accessibilityHint: props.accessibilityHint,
|
|
919
|
+
accessibilityState: props.accessibilityState,
|
|
875
920
|
onChange: (val) => {
|
|
876
921
|
emit("update:modelValue", val);
|
|
877
922
|
emit("change", val);
|
|
@@ -1158,6 +1203,352 @@ var VActionSheet = defineComponent20({
|
|
|
1158
1203
|
}
|
|
1159
1204
|
});
|
|
1160
1205
|
|
|
1206
|
+
// src/components/VRefreshControl.ts
|
|
1207
|
+
import { defineComponent as defineComponent21, h as h21 } from "@vue/runtime-core";
|
|
1208
|
+
var VRefreshControl = defineComponent21({
|
|
1209
|
+
name: "VRefreshControl",
|
|
1210
|
+
props: {
|
|
1211
|
+
refreshing: {
|
|
1212
|
+
type: Boolean,
|
|
1213
|
+
default: false
|
|
1214
|
+
},
|
|
1215
|
+
onRefresh: Function,
|
|
1216
|
+
tintColor: String,
|
|
1217
|
+
title: String,
|
|
1218
|
+
style: Object
|
|
1219
|
+
},
|
|
1220
|
+
setup(props) {
|
|
1221
|
+
return () => h21("VRefreshControl", {
|
|
1222
|
+
refreshing: props.refreshing,
|
|
1223
|
+
onRefresh: props.onRefresh,
|
|
1224
|
+
tintColor: props.tintColor,
|
|
1225
|
+
title: props.title
|
|
1226
|
+
});
|
|
1227
|
+
}
|
|
1228
|
+
});
|
|
1229
|
+
|
|
1230
|
+
// src/components/VPressable.ts
|
|
1231
|
+
import { defineComponent as defineComponent22, h as h22 } from "@vue/runtime-core";
|
|
1232
|
+
var VPressable = defineComponent22({
|
|
1233
|
+
name: "VPressable",
|
|
1234
|
+
props: {
|
|
1235
|
+
style: Object,
|
|
1236
|
+
disabled: {
|
|
1237
|
+
type: Boolean,
|
|
1238
|
+
default: false
|
|
1239
|
+
},
|
|
1240
|
+
activeOpacity: {
|
|
1241
|
+
type: Number,
|
|
1242
|
+
default: 0.7
|
|
1243
|
+
},
|
|
1244
|
+
onPress: Function,
|
|
1245
|
+
onPressIn: Function,
|
|
1246
|
+
onPressOut: Function,
|
|
1247
|
+
onLongPress: Function,
|
|
1248
|
+
accessibilityLabel: String,
|
|
1249
|
+
accessibilityRole: String,
|
|
1250
|
+
accessibilityHint: String,
|
|
1251
|
+
accessibilityState: Object
|
|
1252
|
+
},
|
|
1253
|
+
setup(props, { slots }) {
|
|
1254
|
+
return () => h22(
|
|
1255
|
+
"VPressable",
|
|
1256
|
+
{
|
|
1257
|
+
...props,
|
|
1258
|
+
onPress: props.disabled ? void 0 : props.onPress,
|
|
1259
|
+
onPressIn: props.disabled ? void 0 : props.onPressIn,
|
|
1260
|
+
onPressOut: props.disabled ? void 0 : props.onPressOut,
|
|
1261
|
+
onLongPress: props.disabled ? void 0 : props.onLongPress
|
|
1262
|
+
},
|
|
1263
|
+
slots.default?.()
|
|
1264
|
+
);
|
|
1265
|
+
}
|
|
1266
|
+
});
|
|
1267
|
+
|
|
1268
|
+
// src/components/VSectionList.ts
|
|
1269
|
+
import { defineComponent as defineComponent23, h as h23 } from "@vue/runtime-core";
|
|
1270
|
+
var VSectionList = defineComponent23({
|
|
1271
|
+
name: "VSectionList",
|
|
1272
|
+
props: {
|
|
1273
|
+
/** Array of section objects, each with a title and data array */
|
|
1274
|
+
sections: {
|
|
1275
|
+
type: Array,
|
|
1276
|
+
required: true
|
|
1277
|
+
},
|
|
1278
|
+
/** Extract a unique key from each item. Defaults to index as string. */
|
|
1279
|
+
keyExtractor: {
|
|
1280
|
+
type: Function,
|
|
1281
|
+
default: (_item, index) => String(index)
|
|
1282
|
+
},
|
|
1283
|
+
/** Estimated height per row in points. Default: 44 */
|
|
1284
|
+
estimatedItemHeight: {
|
|
1285
|
+
type: Number,
|
|
1286
|
+
default: 44
|
|
1287
|
+
},
|
|
1288
|
+
/** Whether section headers stick to the top when scrolling. Default: true */
|
|
1289
|
+
stickySectionHeaders: {
|
|
1290
|
+
type: Boolean,
|
|
1291
|
+
default: true
|
|
1292
|
+
},
|
|
1293
|
+
/** Show vertical scroll indicator. Default: true */
|
|
1294
|
+
showsScrollIndicator: {
|
|
1295
|
+
type: Boolean,
|
|
1296
|
+
default: true
|
|
1297
|
+
},
|
|
1298
|
+
/** Enable bounce at scroll boundaries. Default: true */
|
|
1299
|
+
bounces: {
|
|
1300
|
+
type: Boolean,
|
|
1301
|
+
default: true
|
|
1302
|
+
},
|
|
1303
|
+
style: {
|
|
1304
|
+
type: Object,
|
|
1305
|
+
default: () => ({})
|
|
1306
|
+
}
|
|
1307
|
+
},
|
|
1308
|
+
emits: ["scroll", "endReached"],
|
|
1309
|
+
setup(props, { slots, emit }) {
|
|
1310
|
+
return () => {
|
|
1311
|
+
const sections = props.sections ?? [];
|
|
1312
|
+
const children = [];
|
|
1313
|
+
if (slots.header) {
|
|
1314
|
+
children.push(
|
|
1315
|
+
h23("VView", { key: "__header__", style: { flexShrink: 0 } }, slots.header())
|
|
1316
|
+
);
|
|
1317
|
+
}
|
|
1318
|
+
const totalItems = sections.reduce((sum, s) => sum + (s.data?.length ?? 0), 0);
|
|
1319
|
+
if (totalItems === 0 && slots.empty) {
|
|
1320
|
+
children.push(
|
|
1321
|
+
h23("VView", { key: "__empty__", style: { flexShrink: 0 } }, slots.empty())
|
|
1322
|
+
);
|
|
1323
|
+
}
|
|
1324
|
+
for (let sectionIndex = 0; sectionIndex < sections.length; sectionIndex++) {
|
|
1325
|
+
const section = sections[sectionIndex];
|
|
1326
|
+
if (slots.sectionHeader) {
|
|
1327
|
+
children.push(
|
|
1328
|
+
h23(
|
|
1329
|
+
"VView",
|
|
1330
|
+
{
|
|
1331
|
+
key: `__section_header_${sectionIndex}__`,
|
|
1332
|
+
__sectionHeader: true,
|
|
1333
|
+
style: { flexShrink: 0 }
|
|
1334
|
+
},
|
|
1335
|
+
slots.sectionHeader({ section, index: sectionIndex })
|
|
1336
|
+
)
|
|
1337
|
+
);
|
|
1338
|
+
}
|
|
1339
|
+
const items = section.data ?? [];
|
|
1340
|
+
for (let itemIndex = 0; itemIndex < items.length; itemIndex++) {
|
|
1341
|
+
const item = items[itemIndex];
|
|
1342
|
+
children.push(
|
|
1343
|
+
h23(
|
|
1344
|
+
"VView",
|
|
1345
|
+
{
|
|
1346
|
+
key: `${sectionIndex}_${props.keyExtractor(item, itemIndex)}`,
|
|
1347
|
+
style: { flexShrink: 0 }
|
|
1348
|
+
},
|
|
1349
|
+
slots.item?.({ item, index: itemIndex, section }) ?? []
|
|
1350
|
+
)
|
|
1351
|
+
);
|
|
1352
|
+
}
|
|
1353
|
+
if (slots.sectionFooter) {
|
|
1354
|
+
children.push(
|
|
1355
|
+
h23(
|
|
1356
|
+
"VView",
|
|
1357
|
+
{
|
|
1358
|
+
key: `__section_footer_${sectionIndex}__`,
|
|
1359
|
+
style: { flexShrink: 0 }
|
|
1360
|
+
},
|
|
1361
|
+
slots.sectionFooter({ section, index: sectionIndex })
|
|
1362
|
+
)
|
|
1363
|
+
);
|
|
1364
|
+
}
|
|
1365
|
+
}
|
|
1366
|
+
if (slots.footer) {
|
|
1367
|
+
children.push(
|
|
1368
|
+
h23("VView", { key: "__footer__", style: { flexShrink: 0 } }, slots.footer())
|
|
1369
|
+
);
|
|
1370
|
+
}
|
|
1371
|
+
return h23(
|
|
1372
|
+
"VSectionList",
|
|
1373
|
+
{
|
|
1374
|
+
style: props.style,
|
|
1375
|
+
estimatedItemHeight: props.estimatedItemHeight,
|
|
1376
|
+
stickySectionHeaders: props.stickySectionHeaders,
|
|
1377
|
+
showsScrollIndicator: props.showsScrollIndicator,
|
|
1378
|
+
bounces: props.bounces,
|
|
1379
|
+
onScroll: (e) => emit("scroll", e),
|
|
1380
|
+
onEndReached: () => emit("endReached")
|
|
1381
|
+
},
|
|
1382
|
+
children
|
|
1383
|
+
);
|
|
1384
|
+
};
|
|
1385
|
+
}
|
|
1386
|
+
});
|
|
1387
|
+
|
|
1388
|
+
// src/components/VCheckbox.ts
|
|
1389
|
+
import { defineComponent as defineComponent24, h as h24 } from "@vue/runtime-core";
|
|
1390
|
+
var VCheckbox = defineComponent24({
|
|
1391
|
+
name: "VCheckbox",
|
|
1392
|
+
props: {
|
|
1393
|
+
modelValue: {
|
|
1394
|
+
type: Boolean,
|
|
1395
|
+
default: false
|
|
1396
|
+
},
|
|
1397
|
+
disabled: {
|
|
1398
|
+
type: Boolean,
|
|
1399
|
+
default: false
|
|
1400
|
+
},
|
|
1401
|
+
label: {
|
|
1402
|
+
type: String,
|
|
1403
|
+
default: void 0
|
|
1404
|
+
},
|
|
1405
|
+
checkColor: String,
|
|
1406
|
+
tintColor: String,
|
|
1407
|
+
style: Object,
|
|
1408
|
+
accessibilityLabel: String,
|
|
1409
|
+
accessibilityHint: String
|
|
1410
|
+
},
|
|
1411
|
+
emits: ["update:modelValue", "change"],
|
|
1412
|
+
setup(props, { emit }) {
|
|
1413
|
+
const onChange = (payload) => {
|
|
1414
|
+
const value = typeof payload === "boolean" ? payload : !!(payload?.value ?? payload);
|
|
1415
|
+
emit("update:modelValue", value);
|
|
1416
|
+
emit("change", value);
|
|
1417
|
+
};
|
|
1418
|
+
return () => h24("VCheckbox", {
|
|
1419
|
+
value: props.modelValue,
|
|
1420
|
+
disabled: props.disabled,
|
|
1421
|
+
label: props.label,
|
|
1422
|
+
checkColor: props.checkColor,
|
|
1423
|
+
tintColor: props.tintColor,
|
|
1424
|
+
style: props.style,
|
|
1425
|
+
accessibilityLabel: props.accessibilityLabel,
|
|
1426
|
+
accessibilityHint: props.accessibilityHint,
|
|
1427
|
+
onChange
|
|
1428
|
+
});
|
|
1429
|
+
}
|
|
1430
|
+
});
|
|
1431
|
+
|
|
1432
|
+
// src/components/VRadio.ts
|
|
1433
|
+
import { defineComponent as defineComponent25, h as h25 } from "@vue/runtime-core";
|
|
1434
|
+
var VRadio = defineComponent25({
|
|
1435
|
+
name: "VRadio",
|
|
1436
|
+
props: {
|
|
1437
|
+
modelValue: {
|
|
1438
|
+
type: String,
|
|
1439
|
+
default: void 0
|
|
1440
|
+
},
|
|
1441
|
+
options: {
|
|
1442
|
+
type: Array,
|
|
1443
|
+
required: true
|
|
1444
|
+
},
|
|
1445
|
+
disabled: {
|
|
1446
|
+
type: Boolean,
|
|
1447
|
+
default: false
|
|
1448
|
+
},
|
|
1449
|
+
tintColor: String,
|
|
1450
|
+
style: Object,
|
|
1451
|
+
accessibilityLabel: String
|
|
1452
|
+
},
|
|
1453
|
+
emits: ["update:modelValue", "change"],
|
|
1454
|
+
setup(props, { emit }) {
|
|
1455
|
+
const onChange = (payload) => {
|
|
1456
|
+
const value = payload?.value ?? payload;
|
|
1457
|
+
emit("update:modelValue", value);
|
|
1458
|
+
emit("change", value);
|
|
1459
|
+
};
|
|
1460
|
+
return () => h25("VRadio", {
|
|
1461
|
+
selectedValue: props.modelValue,
|
|
1462
|
+
options: props.options,
|
|
1463
|
+
disabled: props.disabled,
|
|
1464
|
+
tintColor: props.tintColor,
|
|
1465
|
+
style: props.style,
|
|
1466
|
+
accessibilityLabel: props.accessibilityLabel,
|
|
1467
|
+
onChange
|
|
1468
|
+
});
|
|
1469
|
+
}
|
|
1470
|
+
});
|
|
1471
|
+
|
|
1472
|
+
// src/components/VDropdown.ts
|
|
1473
|
+
import { defineComponent as defineComponent26, h as h26 } from "@vue/runtime-core";
|
|
1474
|
+
var VDropdown = defineComponent26({
|
|
1475
|
+
name: "VDropdown",
|
|
1476
|
+
props: {
|
|
1477
|
+
modelValue: {
|
|
1478
|
+
type: String,
|
|
1479
|
+
default: void 0
|
|
1480
|
+
},
|
|
1481
|
+
options: {
|
|
1482
|
+
type: Array,
|
|
1483
|
+
required: true
|
|
1484
|
+
},
|
|
1485
|
+
placeholder: {
|
|
1486
|
+
type: String,
|
|
1487
|
+
default: "Select..."
|
|
1488
|
+
},
|
|
1489
|
+
disabled: {
|
|
1490
|
+
type: Boolean,
|
|
1491
|
+
default: false
|
|
1492
|
+
},
|
|
1493
|
+
tintColor: String,
|
|
1494
|
+
style: Object,
|
|
1495
|
+
accessibilityLabel: String
|
|
1496
|
+
},
|
|
1497
|
+
emits: ["update:modelValue", "change"],
|
|
1498
|
+
setup(props, { emit }) {
|
|
1499
|
+
const onChange = (payload) => {
|
|
1500
|
+
const value = payload?.value ?? payload;
|
|
1501
|
+
emit("update:modelValue", value);
|
|
1502
|
+
emit("change", value);
|
|
1503
|
+
};
|
|
1504
|
+
return () => h26("VDropdown", {
|
|
1505
|
+
selectedValue: props.modelValue,
|
|
1506
|
+
options: props.options,
|
|
1507
|
+
placeholder: props.placeholder,
|
|
1508
|
+
disabled: props.disabled,
|
|
1509
|
+
tintColor: props.tintColor,
|
|
1510
|
+
style: props.style,
|
|
1511
|
+
accessibilityLabel: props.accessibilityLabel,
|
|
1512
|
+
onChange
|
|
1513
|
+
});
|
|
1514
|
+
}
|
|
1515
|
+
});
|
|
1516
|
+
|
|
1517
|
+
// src/components/VVideo.ts
|
|
1518
|
+
import { defineComponent as defineComponent27, h as h27 } from "@vue/runtime-core";
|
|
1519
|
+
var VVideo = defineComponent27({
|
|
1520
|
+
name: "VVideo",
|
|
1521
|
+
props: {
|
|
1522
|
+
source: Object,
|
|
1523
|
+
autoplay: { type: Boolean, default: false },
|
|
1524
|
+
loop: { type: Boolean, default: false },
|
|
1525
|
+
muted: { type: Boolean, default: false },
|
|
1526
|
+
paused: { type: Boolean, default: false },
|
|
1527
|
+
controls: { type: Boolean, default: true },
|
|
1528
|
+
volume: { type: Number, default: 1 },
|
|
1529
|
+
resizeMode: {
|
|
1530
|
+
type: String,
|
|
1531
|
+
default: "cover"
|
|
1532
|
+
},
|
|
1533
|
+
poster: String,
|
|
1534
|
+
style: Object,
|
|
1535
|
+
testID: String,
|
|
1536
|
+
accessibilityLabel: String
|
|
1537
|
+
},
|
|
1538
|
+
emits: ["ready", "play", "pause", "end", "error", "progress"],
|
|
1539
|
+
setup(props, { emit }) {
|
|
1540
|
+
return () => h27("VVideo", {
|
|
1541
|
+
...props,
|
|
1542
|
+
onReady: (e) => emit("ready", e),
|
|
1543
|
+
onPlay: () => emit("play"),
|
|
1544
|
+
onPause: () => emit("pause"),
|
|
1545
|
+
onEnd: () => emit("end"),
|
|
1546
|
+
onError: (e) => emit("error", e),
|
|
1547
|
+
onProgress: (e) => emit("progress", e)
|
|
1548
|
+
});
|
|
1549
|
+
}
|
|
1550
|
+
});
|
|
1551
|
+
|
|
1161
1552
|
// src/directives/vShow.ts
|
|
1162
1553
|
var vShow = {
|
|
1163
1554
|
beforeMount(el, { value }) {
|
|
@@ -1169,6 +1560,51 @@ var vShow = {
|
|
|
1169
1560
|
}
|
|
1170
1561
|
};
|
|
1171
1562
|
|
|
1563
|
+
// src/errorBoundary.ts
|
|
1564
|
+
import { defineComponent as defineComponent28, ref, watch, onErrorCaptured } from "@vue/runtime-core";
|
|
1565
|
+
var ErrorBoundary = defineComponent28({
|
|
1566
|
+
name: "ErrorBoundary",
|
|
1567
|
+
props: {
|
|
1568
|
+
onError: Function,
|
|
1569
|
+
resetKeys: {
|
|
1570
|
+
type: Array,
|
|
1571
|
+
default: () => []
|
|
1572
|
+
}
|
|
1573
|
+
},
|
|
1574
|
+
setup(props, { slots }) {
|
|
1575
|
+
const error = ref(null);
|
|
1576
|
+
const errorInfo = ref("");
|
|
1577
|
+
onErrorCaptured((err, _instance, info) => {
|
|
1578
|
+
const normalizedError = err instanceof Error ? err : new Error(String(err));
|
|
1579
|
+
error.value = normalizedError;
|
|
1580
|
+
errorInfo.value = info;
|
|
1581
|
+
if (props.onError) {
|
|
1582
|
+
props.onError(normalizedError, info);
|
|
1583
|
+
}
|
|
1584
|
+
return false;
|
|
1585
|
+
});
|
|
1586
|
+
function reset() {
|
|
1587
|
+
error.value = null;
|
|
1588
|
+
errorInfo.value = "";
|
|
1589
|
+
}
|
|
1590
|
+
watch(
|
|
1591
|
+
() => props.resetKeys,
|
|
1592
|
+
() => {
|
|
1593
|
+
if (error.value) {
|
|
1594
|
+
reset();
|
|
1595
|
+
}
|
|
1596
|
+
},
|
|
1597
|
+
{ deep: true }
|
|
1598
|
+
);
|
|
1599
|
+
return () => {
|
|
1600
|
+
if (error.value && slots.fallback) {
|
|
1601
|
+
return slots.fallback({ error: error.value, errorInfo: errorInfo.value, reset });
|
|
1602
|
+
}
|
|
1603
|
+
return slots.default?.();
|
|
1604
|
+
};
|
|
1605
|
+
}
|
|
1606
|
+
});
|
|
1607
|
+
|
|
1172
1608
|
// src/index.ts
|
|
1173
1609
|
export * from "@vue/runtime-core";
|
|
1174
1610
|
|
|
@@ -1213,6 +1649,7 @@ var validStyleProperties = /* @__PURE__ */ new Set([
|
|
|
1213
1649
|
"gap",
|
|
1214
1650
|
"rowGap",
|
|
1215
1651
|
"columnGap",
|
|
1652
|
+
"direction",
|
|
1216
1653
|
"display",
|
|
1217
1654
|
"overflow",
|
|
1218
1655
|
"zIndex",
|
|
@@ -1260,7 +1697,15 @@ var validStyleProperties = /* @__PURE__ */ new Set([
|
|
|
1260
1697
|
"resizeMode",
|
|
1261
1698
|
"tintColor",
|
|
1262
1699
|
// Transform
|
|
1263
|
-
"transform"
|
|
1700
|
+
"transform",
|
|
1701
|
+
// Accessibility
|
|
1702
|
+
"accessibilityLabel",
|
|
1703
|
+
"accessibilityRole",
|
|
1704
|
+
"accessibilityHint",
|
|
1705
|
+
"accessibilityState",
|
|
1706
|
+
"accessibilityValue",
|
|
1707
|
+
"accessible",
|
|
1708
|
+
"importantForAccessibility"
|
|
1264
1709
|
]);
|
|
1265
1710
|
function createStyleSheet(styles) {
|
|
1266
1711
|
const isDev = typeof __DEV__ !== "undefined" ? __DEV__ : true;
|
|
@@ -1318,9 +1763,9 @@ function useAsyncStorage() {
|
|
|
1318
1763
|
}
|
|
1319
1764
|
|
|
1320
1765
|
// src/composables/useClipboard.ts
|
|
1321
|
-
import { ref } from "@vue/runtime-core";
|
|
1766
|
+
import { ref as ref2 } from "@vue/runtime-core";
|
|
1322
1767
|
function useClipboard() {
|
|
1323
|
-
const content =
|
|
1768
|
+
const content = ref2("");
|
|
1324
1769
|
function copy(text) {
|
|
1325
1770
|
return NativeBridge.invokeNativeModule("Clipboard", "copy", [text]).then(() => void 0);
|
|
1326
1771
|
}
|
|
@@ -1334,16 +1779,16 @@ function useClipboard() {
|
|
|
1334
1779
|
}
|
|
1335
1780
|
|
|
1336
1781
|
// src/composables/useDeviceInfo.ts
|
|
1337
|
-
import { ref as
|
|
1782
|
+
import { ref as ref3, onMounted } from "@vue/runtime-core";
|
|
1338
1783
|
function useDeviceInfo() {
|
|
1339
|
-
const model =
|
|
1340
|
-
const systemVersion =
|
|
1341
|
-
const systemName =
|
|
1342
|
-
const name =
|
|
1343
|
-
const screenWidth =
|
|
1344
|
-
const screenHeight =
|
|
1345
|
-
const scale =
|
|
1346
|
-
const isLoaded =
|
|
1784
|
+
const model = ref3("");
|
|
1785
|
+
const systemVersion = ref3("");
|
|
1786
|
+
const systemName = ref3("");
|
|
1787
|
+
const name = ref3("");
|
|
1788
|
+
const screenWidth = ref3(0);
|
|
1789
|
+
const screenHeight = ref3(0);
|
|
1790
|
+
const scale = ref3(1);
|
|
1791
|
+
const isLoaded = ref3(false);
|
|
1347
1792
|
async function fetchInfo() {
|
|
1348
1793
|
const info = await NativeBridge.invokeNativeModule("DeviceInfo", "getInfo", []);
|
|
1349
1794
|
model.value = info.model ?? "";
|
|
@@ -1372,10 +1817,10 @@ function useDeviceInfo() {
|
|
|
1372
1817
|
}
|
|
1373
1818
|
|
|
1374
1819
|
// src/composables/useKeyboard.ts
|
|
1375
|
-
import { ref as
|
|
1820
|
+
import { ref as ref4 } from "@vue/runtime-core";
|
|
1376
1821
|
function useKeyboard() {
|
|
1377
|
-
const isVisible =
|
|
1378
|
-
const height =
|
|
1822
|
+
const isVisible = ref4(false);
|
|
1823
|
+
const height = ref4(0);
|
|
1379
1824
|
function dismiss() {
|
|
1380
1825
|
return NativeBridge.invokeNativeModule("Keyboard", "dismiss", []).then(() => void 0);
|
|
1381
1826
|
}
|
|
@@ -1439,10 +1884,10 @@ function useAnimation() {
|
|
|
1439
1884
|
}
|
|
1440
1885
|
|
|
1441
1886
|
// src/composables/useNetwork.ts
|
|
1442
|
-
import { ref as
|
|
1887
|
+
import { ref as ref5, onUnmounted } from "@vue/runtime-core";
|
|
1443
1888
|
function useNetwork() {
|
|
1444
|
-
const isConnected =
|
|
1445
|
-
const connectionType =
|
|
1889
|
+
const isConnected = ref5(true);
|
|
1890
|
+
const connectionType = ref5("unknown");
|
|
1446
1891
|
NativeBridge.invokeNativeModule("Network", "getStatus").then((status) => {
|
|
1447
1892
|
isConnected.value = status.isConnected;
|
|
1448
1893
|
connectionType.value = status.connectionType;
|
|
@@ -1457,9 +1902,9 @@ function useNetwork() {
|
|
|
1457
1902
|
}
|
|
1458
1903
|
|
|
1459
1904
|
// src/composables/useAppState.ts
|
|
1460
|
-
import { ref as
|
|
1905
|
+
import { ref as ref6, onUnmounted as onUnmounted2 } from "@vue/runtime-core";
|
|
1461
1906
|
function useAppState() {
|
|
1462
|
-
const state =
|
|
1907
|
+
const state = ref6("active");
|
|
1463
1908
|
NativeBridge.invokeNativeModule("AppState", "getState").then((s) => {
|
|
1464
1909
|
state.value = s;
|
|
1465
1910
|
}).catch(() => {
|
|
@@ -1502,10 +1947,10 @@ function usePermissions() {
|
|
|
1502
1947
|
}
|
|
1503
1948
|
|
|
1504
1949
|
// src/composables/useGeolocation.ts
|
|
1505
|
-
import { ref as
|
|
1950
|
+
import { ref as ref7, onUnmounted as onUnmounted3 } from "@vue/runtime-core";
|
|
1506
1951
|
function useGeolocation() {
|
|
1507
|
-
const coords =
|
|
1508
|
-
const error =
|
|
1952
|
+
const coords = ref7(null);
|
|
1953
|
+
const error = ref7(null);
|
|
1509
1954
|
let watchId = null;
|
|
1510
1955
|
async function getCurrentPosition() {
|
|
1511
1956
|
const result = await NativeBridge.invokeNativeModule("Geolocation", "getCurrentPosition");
|
|
@@ -1532,20 +1977,43 @@ function useGeolocation() {
|
|
|
1532
1977
|
}
|
|
1533
1978
|
|
|
1534
1979
|
// src/composables/useCamera.ts
|
|
1980
|
+
import { onUnmounted as onUnmounted4 } from "@vue/runtime-core";
|
|
1535
1981
|
function useCamera() {
|
|
1982
|
+
const qrCleanups = [];
|
|
1536
1983
|
async function launchCamera(options = {}) {
|
|
1537
1984
|
return NativeBridge.invokeNativeModule("Camera", "launchCamera", [options]);
|
|
1538
1985
|
}
|
|
1539
1986
|
async function launchImageLibrary(options = {}) {
|
|
1540
1987
|
return NativeBridge.invokeNativeModule("Camera", "launchImageLibrary", [options]);
|
|
1541
1988
|
}
|
|
1542
|
-
|
|
1989
|
+
async function captureVideo(options = {}) {
|
|
1990
|
+
return NativeBridge.invokeNativeModule("Camera", "captureVideo", [options]);
|
|
1991
|
+
}
|
|
1992
|
+
async function scanQRCode() {
|
|
1993
|
+
return NativeBridge.invokeNativeModule("Camera", "scanQRCode");
|
|
1994
|
+
}
|
|
1995
|
+
async function stopQRScan() {
|
|
1996
|
+
return NativeBridge.invokeNativeModule("Camera", "stopQRScan");
|
|
1997
|
+
}
|
|
1998
|
+
function onQRCodeDetected(callback) {
|
|
1999
|
+
const unsubscribe = NativeBridge.onGlobalEvent("camera:qrDetected", callback);
|
|
2000
|
+
qrCleanups.push(unsubscribe);
|
|
2001
|
+
return unsubscribe;
|
|
2002
|
+
}
|
|
2003
|
+
onUnmounted4(() => {
|
|
2004
|
+
NativeBridge.invokeNativeModule("Camera", "stopQRScan").catch(() => {
|
|
2005
|
+
});
|
|
2006
|
+
qrCleanups.forEach((fn) => fn());
|
|
2007
|
+
qrCleanups.length = 0;
|
|
2008
|
+
});
|
|
2009
|
+
return { launchCamera, launchImageLibrary, captureVideo, scanQRCode, stopQRScan, onQRCodeDetected };
|
|
1543
2010
|
}
|
|
1544
2011
|
|
|
1545
2012
|
// src/composables/useNotifications.ts
|
|
1546
|
-
import { ref as
|
|
2013
|
+
import { ref as ref8, onUnmounted as onUnmounted5 } from "@vue/runtime-core";
|
|
1547
2014
|
function useNotifications() {
|
|
1548
|
-
const isGranted =
|
|
2015
|
+
const isGranted = ref8(false);
|
|
2016
|
+
const pushToken = ref8(null);
|
|
1549
2017
|
async function requestPermission() {
|
|
1550
2018
|
const granted = await NativeBridge.invokeNativeModule("Notifications", "requestPermission");
|
|
1551
2019
|
isGranted.value = granted;
|
|
@@ -1565,10 +2033,44 @@ function useNotifications() {
|
|
|
1565
2033
|
}
|
|
1566
2034
|
function onNotification(handler) {
|
|
1567
2035
|
const unsubscribe = NativeBridge.onGlobalEvent("notification:received", handler);
|
|
1568
|
-
|
|
2036
|
+
onUnmounted5(unsubscribe);
|
|
2037
|
+
return unsubscribe;
|
|
2038
|
+
}
|
|
2039
|
+
async function registerForPush() {
|
|
2040
|
+
await NativeBridge.invokeNativeModule("Notifications", "registerForPush");
|
|
2041
|
+
}
|
|
2042
|
+
async function getToken() {
|
|
2043
|
+
return NativeBridge.invokeNativeModule("Notifications", "getToken");
|
|
2044
|
+
}
|
|
2045
|
+
function onPushToken(handler) {
|
|
2046
|
+
const unsubscribe = NativeBridge.onGlobalEvent("push:token", (payload) => {
|
|
2047
|
+
pushToken.value = payload.token;
|
|
2048
|
+
handler(payload.token);
|
|
2049
|
+
});
|
|
2050
|
+
onUnmounted5(unsubscribe);
|
|
2051
|
+
return unsubscribe;
|
|
2052
|
+
}
|
|
2053
|
+
function onPushReceived(handler) {
|
|
2054
|
+
const unsubscribe = NativeBridge.onGlobalEvent("push:received", handler);
|
|
2055
|
+
onUnmounted5(unsubscribe);
|
|
1569
2056
|
return unsubscribe;
|
|
1570
2057
|
}
|
|
1571
|
-
return {
|
|
2058
|
+
return {
|
|
2059
|
+
// Local
|
|
2060
|
+
isGranted,
|
|
2061
|
+
requestPermission,
|
|
2062
|
+
getPermissionStatus,
|
|
2063
|
+
scheduleLocal,
|
|
2064
|
+
cancel,
|
|
2065
|
+
cancelAll,
|
|
2066
|
+
onNotification,
|
|
2067
|
+
// Push
|
|
2068
|
+
pushToken,
|
|
2069
|
+
registerForPush,
|
|
2070
|
+
getToken,
|
|
2071
|
+
onPushToken,
|
|
2072
|
+
onPushReceived
|
|
2073
|
+
};
|
|
1572
2074
|
}
|
|
1573
2075
|
|
|
1574
2076
|
// src/composables/useBiometry.ts
|
|
@@ -1586,10 +2088,18 @@ function useBiometry() {
|
|
|
1586
2088
|
}
|
|
1587
2089
|
|
|
1588
2090
|
// src/composables/useHttp.ts
|
|
1589
|
-
import { ref as
|
|
2091
|
+
import { ref as ref9 } from "@vue/runtime-core";
|
|
1590
2092
|
function useHttp(config = {}) {
|
|
1591
|
-
|
|
1592
|
-
|
|
2093
|
+
if (config.pins && Object.keys(config.pins).length > 0) {
|
|
2094
|
+
const configurePins = globalThis.__VN_configurePins;
|
|
2095
|
+
if (typeof configurePins === "function") {
|
|
2096
|
+
configurePins(JSON.stringify(config.pins));
|
|
2097
|
+
} else {
|
|
2098
|
+
NativeBridge.invokeNativeModule("Http", "configurePins", [config.pins]);
|
|
2099
|
+
}
|
|
2100
|
+
}
|
|
2101
|
+
const loading = ref9(false);
|
|
2102
|
+
const error = ref9(null);
|
|
1593
2103
|
async function request(method, url, options = {}) {
|
|
1594
2104
|
const fullUrl = config.baseURL ? `${config.baseURL}${url}` : url;
|
|
1595
2105
|
loading.value = true;
|
|
@@ -1635,10 +2145,10 @@ function useHttp(config = {}) {
|
|
|
1635
2145
|
}
|
|
1636
2146
|
|
|
1637
2147
|
// src/composables/useColorScheme.ts
|
|
1638
|
-
import { ref as
|
|
2148
|
+
import { ref as ref10, onUnmounted as onUnmounted6 } from "@vue/runtime-core";
|
|
1639
2149
|
function useColorScheme() {
|
|
1640
|
-
const colorScheme =
|
|
1641
|
-
const isDark =
|
|
2150
|
+
const colorScheme = ref10("light");
|
|
2151
|
+
const isDark = ref10(false);
|
|
1642
2152
|
const unsubscribe = NativeBridge.onGlobalEvent(
|
|
1643
2153
|
"colorScheme:change",
|
|
1644
2154
|
(payload) => {
|
|
@@ -1646,12 +2156,12 @@ function useColorScheme() {
|
|
|
1646
2156
|
isDark.value = payload.colorScheme === "dark";
|
|
1647
2157
|
}
|
|
1648
2158
|
);
|
|
1649
|
-
|
|
2159
|
+
onUnmounted6(unsubscribe);
|
|
1650
2160
|
return { colorScheme, isDark };
|
|
1651
2161
|
}
|
|
1652
2162
|
|
|
1653
2163
|
// src/composables/useBackHandler.ts
|
|
1654
|
-
import { onMounted as onMounted2, onUnmounted as
|
|
2164
|
+
import { onMounted as onMounted2, onUnmounted as onUnmounted7 } from "@vue/runtime-core";
|
|
1655
2165
|
function useBackHandler(handler) {
|
|
1656
2166
|
let unsubscribe = null;
|
|
1657
2167
|
onMounted2(() => {
|
|
@@ -1659,12 +2169,1056 @@ function useBackHandler(handler) {
|
|
|
1659
2169
|
handler();
|
|
1660
2170
|
});
|
|
1661
2171
|
});
|
|
1662
|
-
|
|
2172
|
+
onUnmounted7(() => {
|
|
1663
2173
|
unsubscribe?.();
|
|
1664
2174
|
unsubscribe = null;
|
|
1665
2175
|
});
|
|
1666
2176
|
}
|
|
1667
2177
|
|
|
2178
|
+
// src/composables/useSecureStorage.ts
|
|
2179
|
+
function useSecureStorage() {
|
|
2180
|
+
function getItem(key) {
|
|
2181
|
+
return NativeBridge.invokeNativeModule("SecureStorage", "get", [key]);
|
|
2182
|
+
}
|
|
2183
|
+
function setItem(key, value) {
|
|
2184
|
+
return NativeBridge.invokeNativeModule("SecureStorage", "set", [key, value]).then(() => void 0);
|
|
2185
|
+
}
|
|
2186
|
+
function removeItem(key) {
|
|
2187
|
+
return NativeBridge.invokeNativeModule("SecureStorage", "remove", [key]).then(() => void 0);
|
|
2188
|
+
}
|
|
2189
|
+
function clear() {
|
|
2190
|
+
return NativeBridge.invokeNativeModule("SecureStorage", "clear", []).then(() => void 0);
|
|
2191
|
+
}
|
|
2192
|
+
return { getItem, setItem, removeItem, clear };
|
|
2193
|
+
}
|
|
2194
|
+
|
|
2195
|
+
// src/composables/useI18n.ts
|
|
2196
|
+
import { ref as ref11, onMounted as onMounted3 } from "@vue/runtime-core";
|
|
2197
|
+
function useI18n() {
|
|
2198
|
+
const isRTL = ref11(false);
|
|
2199
|
+
const locale = ref11("en");
|
|
2200
|
+
onMounted3(async () => {
|
|
2201
|
+
try {
|
|
2202
|
+
const info = await NativeBridge.invokeNativeModule("DeviceInfo", "getDeviceInfo", []);
|
|
2203
|
+
locale.value = info?.locale || "en";
|
|
2204
|
+
isRTL.value = ["ar", "he", "fa", "ur"].some((l) => locale.value.startsWith(l));
|
|
2205
|
+
} catch {
|
|
2206
|
+
}
|
|
2207
|
+
});
|
|
2208
|
+
return { isRTL, locale };
|
|
2209
|
+
}
|
|
2210
|
+
|
|
2211
|
+
// src/composables/usePlatform.ts
|
|
2212
|
+
function usePlatform() {
|
|
2213
|
+
const platform = typeof __PLATFORM__ !== "undefined" ? __PLATFORM__ : "ios";
|
|
2214
|
+
const isIOS = platform === "ios";
|
|
2215
|
+
const isAndroid = platform === "android";
|
|
2216
|
+
return { platform, isIOS, isAndroid };
|
|
2217
|
+
}
|
|
2218
|
+
|
|
2219
|
+
// src/composables/useDimensions.ts
|
|
2220
|
+
import { ref as ref12, onMounted as onMounted4, onUnmounted as onUnmounted8 } from "@vue/runtime-core";
|
|
2221
|
+
function useDimensions() {
|
|
2222
|
+
const width = ref12(0);
|
|
2223
|
+
const height = ref12(0);
|
|
2224
|
+
const scale = ref12(1);
|
|
2225
|
+
onMounted4(async () => {
|
|
2226
|
+
try {
|
|
2227
|
+
const info = await NativeBridge.invokeNativeModule("DeviceInfo", "getInfo", []);
|
|
2228
|
+
width.value = info?.screenWidth || 0;
|
|
2229
|
+
height.value = info?.screenHeight || 0;
|
|
2230
|
+
scale.value = info?.scale || 1;
|
|
2231
|
+
} catch {
|
|
2232
|
+
}
|
|
2233
|
+
});
|
|
2234
|
+
const cleanup = NativeBridge.onGlobalEvent("dimensionsChange", (payload) => {
|
|
2235
|
+
if (payload.width != null) width.value = payload.width;
|
|
2236
|
+
if (payload.height != null) height.value = payload.height;
|
|
2237
|
+
if (payload.scale != null) scale.value = payload.scale;
|
|
2238
|
+
});
|
|
2239
|
+
onUnmounted8(cleanup);
|
|
2240
|
+
return { width, height, scale };
|
|
2241
|
+
}
|
|
2242
|
+
|
|
2243
|
+
// src/composables/useWebSocket.ts
|
|
2244
|
+
import { ref as ref13, onUnmounted as onUnmounted9 } from "@vue/runtime-core";
|
|
2245
|
+
var connectionCounter = 0;
|
|
2246
|
+
function useWebSocket(url, options = {}) {
|
|
2247
|
+
const {
|
|
2248
|
+
autoConnect = true,
|
|
2249
|
+
autoReconnect = false,
|
|
2250
|
+
maxReconnectAttempts = 3,
|
|
2251
|
+
reconnectInterval = 1e3
|
|
2252
|
+
} = options;
|
|
2253
|
+
const connectionId = `ws_${++connectionCounter}_${Date.now()}`;
|
|
2254
|
+
const status = ref13("CLOSED");
|
|
2255
|
+
const lastMessage = ref13(null);
|
|
2256
|
+
const error = ref13(null);
|
|
2257
|
+
let reconnectAttempts = 0;
|
|
2258
|
+
let reconnectTimer = null;
|
|
2259
|
+
const unsubscribers = [];
|
|
2260
|
+
unsubscribers.push(
|
|
2261
|
+
NativeBridge.onGlobalEvent("websocket:open", (payload) => {
|
|
2262
|
+
if (payload.connectionId !== connectionId) return;
|
|
2263
|
+
status.value = "OPEN";
|
|
2264
|
+
error.value = null;
|
|
2265
|
+
reconnectAttempts = 0;
|
|
2266
|
+
})
|
|
2267
|
+
);
|
|
2268
|
+
unsubscribers.push(
|
|
2269
|
+
NativeBridge.onGlobalEvent("websocket:message", (payload) => {
|
|
2270
|
+
if (payload.connectionId !== connectionId) return;
|
|
2271
|
+
lastMessage.value = payload.data;
|
|
2272
|
+
})
|
|
2273
|
+
);
|
|
2274
|
+
unsubscribers.push(
|
|
2275
|
+
NativeBridge.onGlobalEvent("websocket:close", (payload) => {
|
|
2276
|
+
if (payload.connectionId !== connectionId) return;
|
|
2277
|
+
status.value = "CLOSED";
|
|
2278
|
+
if (autoReconnect && reconnectAttempts < maxReconnectAttempts && payload.code !== 1e3) {
|
|
2279
|
+
reconnectAttempts++;
|
|
2280
|
+
reconnectTimer = setTimeout(() => {
|
|
2281
|
+
open();
|
|
2282
|
+
}, reconnectInterval);
|
|
2283
|
+
}
|
|
2284
|
+
})
|
|
2285
|
+
);
|
|
2286
|
+
unsubscribers.push(
|
|
2287
|
+
NativeBridge.onGlobalEvent("websocket:error", (payload) => {
|
|
2288
|
+
if (payload.connectionId !== connectionId) return;
|
|
2289
|
+
error.value = payload.message;
|
|
2290
|
+
})
|
|
2291
|
+
);
|
|
2292
|
+
function open() {
|
|
2293
|
+
if (status.value === "OPEN" || status.value === "CONNECTING") return;
|
|
2294
|
+
status.value = "CONNECTING";
|
|
2295
|
+
error.value = null;
|
|
2296
|
+
NativeBridge.invokeNativeModule("WebSocket", "connect", [url, connectionId]).catch((err) => {
|
|
2297
|
+
status.value = "CLOSED";
|
|
2298
|
+
error.value = err.message;
|
|
2299
|
+
});
|
|
2300
|
+
}
|
|
2301
|
+
function send(data) {
|
|
2302
|
+
if (status.value !== "OPEN") return;
|
|
2303
|
+
const message = typeof data === "string" ? data : JSON.stringify(data);
|
|
2304
|
+
NativeBridge.invokeNativeModule("WebSocket", "send", [connectionId, message]).catch((err) => {
|
|
2305
|
+
error.value = err.message;
|
|
2306
|
+
});
|
|
2307
|
+
}
|
|
2308
|
+
function close(code, reason) {
|
|
2309
|
+
if (status.value === "CLOSED" || status.value === "CLOSING") return;
|
|
2310
|
+
status.value = "CLOSING";
|
|
2311
|
+
if (reconnectTimer) {
|
|
2312
|
+
clearTimeout(reconnectTimer);
|
|
2313
|
+
reconnectTimer = null;
|
|
2314
|
+
}
|
|
2315
|
+
reconnectAttempts = maxReconnectAttempts;
|
|
2316
|
+
NativeBridge.invokeNativeModule("WebSocket", "close", [connectionId, code ?? 1e3, reason ?? ""]).catch(() => {
|
|
2317
|
+
status.value = "CLOSED";
|
|
2318
|
+
});
|
|
2319
|
+
}
|
|
2320
|
+
if (autoConnect) {
|
|
2321
|
+
open();
|
|
2322
|
+
}
|
|
2323
|
+
onUnmounted9(() => {
|
|
2324
|
+
if (reconnectTimer) {
|
|
2325
|
+
clearTimeout(reconnectTimer);
|
|
2326
|
+
}
|
|
2327
|
+
if (status.value === "OPEN" || status.value === "CONNECTING") {
|
|
2328
|
+
reconnectAttempts = maxReconnectAttempts;
|
|
2329
|
+
NativeBridge.invokeNativeModule("WebSocket", "close", [connectionId, 1e3, ""]).catch(() => {
|
|
2330
|
+
});
|
|
2331
|
+
}
|
|
2332
|
+
unsubscribers.forEach((unsub) => unsub());
|
|
2333
|
+
});
|
|
2334
|
+
return { status, lastMessage, error, send, close, open };
|
|
2335
|
+
}
|
|
2336
|
+
|
|
2337
|
+
// src/composables/useFileSystem.ts
|
|
2338
|
+
function useFileSystem() {
|
|
2339
|
+
function readFile(path, encoding) {
|
|
2340
|
+
return NativeBridge.invokeNativeModule("FileSystem", "readFile", [path, encoding ?? "utf8"]);
|
|
2341
|
+
}
|
|
2342
|
+
function writeFile(path, content, encoding) {
|
|
2343
|
+
return NativeBridge.invokeNativeModule("FileSystem", "writeFile", [path, content, encoding ?? "utf8"]).then(() => void 0);
|
|
2344
|
+
}
|
|
2345
|
+
function deleteFile(path) {
|
|
2346
|
+
return NativeBridge.invokeNativeModule("FileSystem", "deleteFile", [path]).then(() => void 0);
|
|
2347
|
+
}
|
|
2348
|
+
function exists(path) {
|
|
2349
|
+
return NativeBridge.invokeNativeModule("FileSystem", "exists", [path]);
|
|
2350
|
+
}
|
|
2351
|
+
function listDirectory(path) {
|
|
2352
|
+
return NativeBridge.invokeNativeModule("FileSystem", "listDirectory", [path]);
|
|
2353
|
+
}
|
|
2354
|
+
function downloadFile(url, destPath) {
|
|
2355
|
+
return NativeBridge.invokeNativeModule("FileSystem", "downloadFile", [url, destPath]);
|
|
2356
|
+
}
|
|
2357
|
+
function getDocumentsPath() {
|
|
2358
|
+
return NativeBridge.invokeNativeModule("FileSystem", "getDocumentsPath", []);
|
|
2359
|
+
}
|
|
2360
|
+
function getCachesPath() {
|
|
2361
|
+
return NativeBridge.invokeNativeModule("FileSystem", "getCachesPath", []);
|
|
2362
|
+
}
|
|
2363
|
+
function stat(path) {
|
|
2364
|
+
return NativeBridge.invokeNativeModule("FileSystem", "stat", [path]);
|
|
2365
|
+
}
|
|
2366
|
+
function mkdir(path) {
|
|
2367
|
+
return NativeBridge.invokeNativeModule("FileSystem", "mkdir", [path]).then(() => void 0);
|
|
2368
|
+
}
|
|
2369
|
+
function copyFile(srcPath, destPath) {
|
|
2370
|
+
return NativeBridge.invokeNativeModule("FileSystem", "copyFile", [srcPath, destPath]).then(() => void 0);
|
|
2371
|
+
}
|
|
2372
|
+
function moveFile(srcPath, destPath) {
|
|
2373
|
+
return NativeBridge.invokeNativeModule("FileSystem", "moveFile", [srcPath, destPath]).then(() => void 0);
|
|
2374
|
+
}
|
|
2375
|
+
return {
|
|
2376
|
+
readFile,
|
|
2377
|
+
writeFile,
|
|
2378
|
+
deleteFile,
|
|
2379
|
+
exists,
|
|
2380
|
+
listDirectory,
|
|
2381
|
+
downloadFile,
|
|
2382
|
+
getDocumentsPath,
|
|
2383
|
+
getCachesPath,
|
|
2384
|
+
stat,
|
|
2385
|
+
mkdir,
|
|
2386
|
+
copyFile,
|
|
2387
|
+
moveFile
|
|
2388
|
+
};
|
|
2389
|
+
}
|
|
2390
|
+
|
|
2391
|
+
// src/composables/useSensors.ts
|
|
2392
|
+
import { ref as ref14, onUnmounted as onUnmounted10 } from "@vue/runtime-core";
|
|
2393
|
+
function useAccelerometer(options = {}) {
|
|
2394
|
+
const x = ref14(0);
|
|
2395
|
+
const y = ref14(0);
|
|
2396
|
+
const z = ref14(0);
|
|
2397
|
+
const isAvailable = ref14(false);
|
|
2398
|
+
let running = false;
|
|
2399
|
+
let unsubscribe = null;
|
|
2400
|
+
NativeBridge.invokeNativeModule("Sensors", "isAvailable", ["accelerometer"]).then((result) => {
|
|
2401
|
+
isAvailable.value = result.available;
|
|
2402
|
+
}).catch(() => {
|
|
2403
|
+
});
|
|
2404
|
+
function start() {
|
|
2405
|
+
if (running) return;
|
|
2406
|
+
running = true;
|
|
2407
|
+
unsubscribe = NativeBridge.onGlobalEvent("sensor:accelerometer", (payload) => {
|
|
2408
|
+
x.value = payload.x;
|
|
2409
|
+
y.value = payload.y;
|
|
2410
|
+
z.value = payload.z;
|
|
2411
|
+
});
|
|
2412
|
+
NativeBridge.invokeNativeModule("Sensors", "startAccelerometer", [
|
|
2413
|
+
options.interval ?? 100
|
|
2414
|
+
]).catch(() => {
|
|
2415
|
+
});
|
|
2416
|
+
}
|
|
2417
|
+
function stop() {
|
|
2418
|
+
if (!running) return;
|
|
2419
|
+
running = false;
|
|
2420
|
+
unsubscribe?.();
|
|
2421
|
+
unsubscribe = null;
|
|
2422
|
+
NativeBridge.invokeNativeModule("Sensors", "stopAccelerometer").catch(() => {
|
|
2423
|
+
});
|
|
2424
|
+
}
|
|
2425
|
+
onUnmounted10(() => {
|
|
2426
|
+
stop();
|
|
2427
|
+
});
|
|
2428
|
+
return { x, y, z, isAvailable, start, stop };
|
|
2429
|
+
}
|
|
2430
|
+
function useGyroscope(options = {}) {
|
|
2431
|
+
const x = ref14(0);
|
|
2432
|
+
const y = ref14(0);
|
|
2433
|
+
const z = ref14(0);
|
|
2434
|
+
const isAvailable = ref14(false);
|
|
2435
|
+
let running = false;
|
|
2436
|
+
let unsubscribe = null;
|
|
2437
|
+
NativeBridge.invokeNativeModule("Sensors", "isAvailable", ["gyroscope"]).then((result) => {
|
|
2438
|
+
isAvailable.value = result.available;
|
|
2439
|
+
}).catch(() => {
|
|
2440
|
+
});
|
|
2441
|
+
function start() {
|
|
2442
|
+
if (running) return;
|
|
2443
|
+
running = true;
|
|
2444
|
+
unsubscribe = NativeBridge.onGlobalEvent("sensor:gyroscope", (payload) => {
|
|
2445
|
+
x.value = payload.x;
|
|
2446
|
+
y.value = payload.y;
|
|
2447
|
+
z.value = payload.z;
|
|
2448
|
+
});
|
|
2449
|
+
NativeBridge.invokeNativeModule("Sensors", "startGyroscope", [
|
|
2450
|
+
options.interval ?? 100
|
|
2451
|
+
]).catch(() => {
|
|
2452
|
+
});
|
|
2453
|
+
}
|
|
2454
|
+
function stop() {
|
|
2455
|
+
if (!running) return;
|
|
2456
|
+
running = false;
|
|
2457
|
+
unsubscribe?.();
|
|
2458
|
+
unsubscribe = null;
|
|
2459
|
+
NativeBridge.invokeNativeModule("Sensors", "stopGyroscope").catch(() => {
|
|
2460
|
+
});
|
|
2461
|
+
}
|
|
2462
|
+
onUnmounted10(() => {
|
|
2463
|
+
stop();
|
|
2464
|
+
});
|
|
2465
|
+
return { x, y, z, isAvailable, start, stop };
|
|
2466
|
+
}
|
|
2467
|
+
|
|
2468
|
+
// src/composables/useAudio.ts
|
|
2469
|
+
import { ref as ref15, onUnmounted as onUnmounted11 } from "@vue/runtime-core";
|
|
2470
|
+
function useAudio() {
|
|
2471
|
+
const duration = ref15(0);
|
|
2472
|
+
const position = ref15(0);
|
|
2473
|
+
const isPlaying = ref15(false);
|
|
2474
|
+
const isRecording = ref15(false);
|
|
2475
|
+
const error = ref15(null);
|
|
2476
|
+
const unsubProgress = NativeBridge.onGlobalEvent("audio:progress", (payload) => {
|
|
2477
|
+
position.value = payload.currentTime ?? 0;
|
|
2478
|
+
duration.value = payload.duration ?? 0;
|
|
2479
|
+
});
|
|
2480
|
+
const unsubComplete = NativeBridge.onGlobalEvent("audio:complete", () => {
|
|
2481
|
+
isPlaying.value = false;
|
|
2482
|
+
position.value = 0;
|
|
2483
|
+
});
|
|
2484
|
+
const unsubError = NativeBridge.onGlobalEvent("audio:error", (payload) => {
|
|
2485
|
+
error.value = payload.message ?? "Unknown audio error";
|
|
2486
|
+
isPlaying.value = false;
|
|
2487
|
+
});
|
|
2488
|
+
onUnmounted11(() => {
|
|
2489
|
+
unsubProgress();
|
|
2490
|
+
unsubComplete();
|
|
2491
|
+
unsubError();
|
|
2492
|
+
NativeBridge.invokeNativeModule("Audio", "stop", []).catch(() => {
|
|
2493
|
+
});
|
|
2494
|
+
if (isRecording.value) {
|
|
2495
|
+
NativeBridge.invokeNativeModule("Audio", "stopRecording", []).catch(() => {
|
|
2496
|
+
});
|
|
2497
|
+
}
|
|
2498
|
+
});
|
|
2499
|
+
async function play(uri, options = {}) {
|
|
2500
|
+
error.value = null;
|
|
2501
|
+
const result = await NativeBridge.invokeNativeModule("Audio", "play", [uri, options]);
|
|
2502
|
+
if (result?.duration != null) {
|
|
2503
|
+
duration.value = result.duration;
|
|
2504
|
+
}
|
|
2505
|
+
isPlaying.value = true;
|
|
2506
|
+
}
|
|
2507
|
+
async function pause() {
|
|
2508
|
+
await NativeBridge.invokeNativeModule("Audio", "pause", []);
|
|
2509
|
+
isPlaying.value = false;
|
|
2510
|
+
}
|
|
2511
|
+
async function resume() {
|
|
2512
|
+
await NativeBridge.invokeNativeModule("Audio", "resume", []);
|
|
2513
|
+
isPlaying.value = true;
|
|
2514
|
+
}
|
|
2515
|
+
async function stop() {
|
|
2516
|
+
await NativeBridge.invokeNativeModule("Audio", "stop", []);
|
|
2517
|
+
isPlaying.value = false;
|
|
2518
|
+
position.value = 0;
|
|
2519
|
+
duration.value = 0;
|
|
2520
|
+
}
|
|
2521
|
+
async function seek(positionSec) {
|
|
2522
|
+
await NativeBridge.invokeNativeModule("Audio", "seek", [positionSec]);
|
|
2523
|
+
}
|
|
2524
|
+
async function setVolume(volume) {
|
|
2525
|
+
await NativeBridge.invokeNativeModule("Audio", "setVolume", [volume]);
|
|
2526
|
+
}
|
|
2527
|
+
async function startRecording(options = {}) {
|
|
2528
|
+
error.value = null;
|
|
2529
|
+
const result = await NativeBridge.invokeNativeModule("Audio", "startRecording", [options]);
|
|
2530
|
+
isRecording.value = true;
|
|
2531
|
+
return result?.uri ?? "";
|
|
2532
|
+
}
|
|
2533
|
+
async function stopRecording() {
|
|
2534
|
+
const result = await NativeBridge.invokeNativeModule("Audio", "stopRecording", []);
|
|
2535
|
+
isRecording.value = false;
|
|
2536
|
+
return { uri: result?.uri ?? "", duration: result?.duration ?? 0 };
|
|
2537
|
+
}
|
|
2538
|
+
async function pauseRecording() {
|
|
2539
|
+
await NativeBridge.invokeNativeModule("Audio", "pauseRecording", []);
|
|
2540
|
+
}
|
|
2541
|
+
async function resumeRecording() {
|
|
2542
|
+
await NativeBridge.invokeNativeModule("Audio", "resumeRecording", []);
|
|
2543
|
+
}
|
|
2544
|
+
return {
|
|
2545
|
+
// Playback
|
|
2546
|
+
play,
|
|
2547
|
+
pause,
|
|
2548
|
+
resume,
|
|
2549
|
+
stop,
|
|
2550
|
+
seek,
|
|
2551
|
+
setVolume,
|
|
2552
|
+
// Recording
|
|
2553
|
+
startRecording,
|
|
2554
|
+
stopRecording,
|
|
2555
|
+
pauseRecording,
|
|
2556
|
+
resumeRecording,
|
|
2557
|
+
// Reactive state
|
|
2558
|
+
duration,
|
|
2559
|
+
position,
|
|
2560
|
+
isPlaying,
|
|
2561
|
+
isRecording,
|
|
2562
|
+
error
|
|
2563
|
+
};
|
|
2564
|
+
}
|
|
2565
|
+
|
|
2566
|
+
// src/composables/useDatabase.ts
|
|
2567
|
+
import { ref as ref16, onUnmounted as onUnmounted12 } from "@vue/runtime-core";
|
|
2568
|
+
function useDatabase(name = "default") {
|
|
2569
|
+
const isOpen = ref16(false);
|
|
2570
|
+
let opened = false;
|
|
2571
|
+
async function ensureOpen() {
|
|
2572
|
+
if (opened) return;
|
|
2573
|
+
await NativeBridge.invokeNativeModule("Database", "open", [name]);
|
|
2574
|
+
opened = true;
|
|
2575
|
+
isOpen.value = true;
|
|
2576
|
+
}
|
|
2577
|
+
async function execute(sql, params) {
|
|
2578
|
+
await ensureOpen();
|
|
2579
|
+
return NativeBridge.invokeNativeModule("Database", "execute", [name, sql, params ?? []]);
|
|
2580
|
+
}
|
|
2581
|
+
async function query(sql, params) {
|
|
2582
|
+
await ensureOpen();
|
|
2583
|
+
return NativeBridge.invokeNativeModule("Database", "query", [name, sql, params ?? []]);
|
|
2584
|
+
}
|
|
2585
|
+
async function transaction(callback) {
|
|
2586
|
+
await ensureOpen();
|
|
2587
|
+
const statements = [];
|
|
2588
|
+
const ctx = {
|
|
2589
|
+
execute: async (sql, params) => {
|
|
2590
|
+
statements.push({ sql, params: params ?? [] });
|
|
2591
|
+
return { rowsAffected: 0 };
|
|
2592
|
+
},
|
|
2593
|
+
query: async (sql, params) => {
|
|
2594
|
+
if (statements.length > 0) {
|
|
2595
|
+
await NativeBridge.invokeNativeModule("Database", "executeTransaction", [name, statements.splice(0)]);
|
|
2596
|
+
}
|
|
2597
|
+
return NativeBridge.invokeNativeModule("Database", "query", [name, sql, params ?? []]);
|
|
2598
|
+
}
|
|
2599
|
+
};
|
|
2600
|
+
await callback(ctx);
|
|
2601
|
+
if (statements.length > 0) {
|
|
2602
|
+
await NativeBridge.invokeNativeModule("Database", "executeTransaction", [name, statements]);
|
|
2603
|
+
}
|
|
2604
|
+
}
|
|
2605
|
+
async function close() {
|
|
2606
|
+
if (!opened) return;
|
|
2607
|
+
await NativeBridge.invokeNativeModule("Database", "close", [name]);
|
|
2608
|
+
opened = false;
|
|
2609
|
+
isOpen.value = false;
|
|
2610
|
+
}
|
|
2611
|
+
onUnmounted12(() => {
|
|
2612
|
+
if (opened) {
|
|
2613
|
+
NativeBridge.invokeNativeModule("Database", "close", [name]).catch(() => {
|
|
2614
|
+
});
|
|
2615
|
+
opened = false;
|
|
2616
|
+
isOpen.value = false;
|
|
2617
|
+
}
|
|
2618
|
+
});
|
|
2619
|
+
return { execute, query, transaction, close, isOpen };
|
|
2620
|
+
}
|
|
2621
|
+
|
|
2622
|
+
// src/composables/usePerformance.ts
|
|
2623
|
+
import { ref as ref17, onUnmounted as onUnmounted13 } from "@vue/runtime-core";
|
|
2624
|
+
function usePerformance() {
|
|
2625
|
+
const isProfiling = ref17(false);
|
|
2626
|
+
const fps = ref17(0);
|
|
2627
|
+
const memoryMB = ref17(0);
|
|
2628
|
+
const bridgeOps = ref17(0);
|
|
2629
|
+
let unsubscribe = null;
|
|
2630
|
+
function handleMetrics(payload) {
|
|
2631
|
+
fps.value = payload.fps ?? 0;
|
|
2632
|
+
memoryMB.value = payload.memoryMB ?? 0;
|
|
2633
|
+
bridgeOps.value = payload.bridgeOps ?? 0;
|
|
2634
|
+
}
|
|
2635
|
+
async function startProfiling() {
|
|
2636
|
+
if (isProfiling.value) return;
|
|
2637
|
+
unsubscribe = NativeBridge.onGlobalEvent("perf:metrics", handleMetrics);
|
|
2638
|
+
await NativeBridge.invokeNativeModule("Performance", "startProfiling", []);
|
|
2639
|
+
isProfiling.value = true;
|
|
2640
|
+
}
|
|
2641
|
+
async function stopProfiling() {
|
|
2642
|
+
if (!isProfiling.value) return;
|
|
2643
|
+
await NativeBridge.invokeNativeModule("Performance", "stopProfiling", []);
|
|
2644
|
+
isProfiling.value = false;
|
|
2645
|
+
if (unsubscribe) {
|
|
2646
|
+
unsubscribe();
|
|
2647
|
+
unsubscribe = null;
|
|
2648
|
+
}
|
|
2649
|
+
}
|
|
2650
|
+
async function getMetrics() {
|
|
2651
|
+
return NativeBridge.invokeNativeModule("Performance", "getMetrics", []);
|
|
2652
|
+
}
|
|
2653
|
+
onUnmounted13(() => {
|
|
2654
|
+
if (isProfiling.value) {
|
|
2655
|
+
NativeBridge.invokeNativeModule("Performance", "stopProfiling", []).catch(() => {
|
|
2656
|
+
});
|
|
2657
|
+
isProfiling.value = false;
|
|
2658
|
+
}
|
|
2659
|
+
if (unsubscribe) {
|
|
2660
|
+
unsubscribe();
|
|
2661
|
+
unsubscribe = null;
|
|
2662
|
+
}
|
|
2663
|
+
});
|
|
2664
|
+
return {
|
|
2665
|
+
startProfiling,
|
|
2666
|
+
stopProfiling,
|
|
2667
|
+
getMetrics,
|
|
2668
|
+
isProfiling,
|
|
2669
|
+
fps,
|
|
2670
|
+
memoryMB,
|
|
2671
|
+
bridgeOps
|
|
2672
|
+
};
|
|
2673
|
+
}
|
|
2674
|
+
|
|
2675
|
+
// src/composables/useSharedElementTransition.ts
|
|
2676
|
+
import { ref as ref18, onUnmounted as onUnmounted14 } from "@vue/runtime-core";
|
|
2677
|
+
var sharedElementRegistry = /* @__PURE__ */ new Map();
|
|
2678
|
+
function useSharedElementTransition(elementId) {
|
|
2679
|
+
const viewId = ref18(null);
|
|
2680
|
+
function register(nativeViewId) {
|
|
2681
|
+
viewId.value = nativeViewId;
|
|
2682
|
+
sharedElementRegistry.set(elementId, nativeViewId);
|
|
2683
|
+
}
|
|
2684
|
+
function unregister() {
|
|
2685
|
+
viewId.value = null;
|
|
2686
|
+
sharedElementRegistry.delete(elementId);
|
|
2687
|
+
}
|
|
2688
|
+
onUnmounted14(() => {
|
|
2689
|
+
unregister();
|
|
2690
|
+
});
|
|
2691
|
+
return {
|
|
2692
|
+
id: elementId,
|
|
2693
|
+
viewId,
|
|
2694
|
+
register,
|
|
2695
|
+
unregister
|
|
2696
|
+
};
|
|
2697
|
+
}
|
|
2698
|
+
async function measureViewFrame(nativeViewId) {
|
|
2699
|
+
return NativeBridge.invokeNativeModule("Animation", "measureView", [nativeViewId]);
|
|
2700
|
+
}
|
|
2701
|
+
function getSharedElementViewId(elementId) {
|
|
2702
|
+
return sharedElementRegistry.get(elementId);
|
|
2703
|
+
}
|
|
2704
|
+
function getRegisteredSharedElements() {
|
|
2705
|
+
return Array.from(sharedElementRegistry.keys());
|
|
2706
|
+
}
|
|
2707
|
+
function clearSharedElementRegistry() {
|
|
2708
|
+
sharedElementRegistry.clear();
|
|
2709
|
+
}
|
|
2710
|
+
|
|
2711
|
+
// src/composables/useIAP.ts
|
|
2712
|
+
import { ref as ref19, onUnmounted as onUnmounted15 } from "@vue/runtime-core";
|
|
2713
|
+
function useIAP() {
|
|
2714
|
+
const products = ref19([]);
|
|
2715
|
+
const isReady = ref19(false);
|
|
2716
|
+
const error = ref19(null);
|
|
2717
|
+
const cleanups = [];
|
|
2718
|
+
const unsubscribe = NativeBridge.onGlobalEvent("iap:transactionUpdate", (payload) => {
|
|
2719
|
+
if (payload.state === "failed" && payload.error) {
|
|
2720
|
+
error.value = payload.error;
|
|
2721
|
+
}
|
|
2722
|
+
});
|
|
2723
|
+
cleanups.push(unsubscribe);
|
|
2724
|
+
NativeBridge.invokeNativeModule("IAP", "initialize").then(() => {
|
|
2725
|
+
isReady.value = true;
|
|
2726
|
+
}).catch((err) => {
|
|
2727
|
+
error.value = String(err);
|
|
2728
|
+
});
|
|
2729
|
+
async function getProducts(skus) {
|
|
2730
|
+
error.value = null;
|
|
2731
|
+
try {
|
|
2732
|
+
const result = await NativeBridge.invokeNativeModule("IAP", "getProducts", [skus]);
|
|
2733
|
+
const productList = result;
|
|
2734
|
+
products.value = productList;
|
|
2735
|
+
return productList;
|
|
2736
|
+
} catch (err) {
|
|
2737
|
+
error.value = String(err);
|
|
2738
|
+
return [];
|
|
2739
|
+
}
|
|
2740
|
+
}
|
|
2741
|
+
async function purchase(sku) {
|
|
2742
|
+
error.value = null;
|
|
2743
|
+
try {
|
|
2744
|
+
return await NativeBridge.invokeNativeModule("IAP", "purchase", [sku]);
|
|
2745
|
+
} catch (err) {
|
|
2746
|
+
error.value = String(err);
|
|
2747
|
+
return null;
|
|
2748
|
+
}
|
|
2749
|
+
}
|
|
2750
|
+
async function restorePurchases() {
|
|
2751
|
+
error.value = null;
|
|
2752
|
+
try {
|
|
2753
|
+
return await NativeBridge.invokeNativeModule("IAP", "restorePurchases");
|
|
2754
|
+
} catch (err) {
|
|
2755
|
+
error.value = String(err);
|
|
2756
|
+
return [];
|
|
2757
|
+
}
|
|
2758
|
+
}
|
|
2759
|
+
async function getActiveSubscriptions() {
|
|
2760
|
+
error.value = null;
|
|
2761
|
+
try {
|
|
2762
|
+
return await NativeBridge.invokeNativeModule("IAP", "getActiveSubscriptions");
|
|
2763
|
+
} catch (err) {
|
|
2764
|
+
error.value = String(err);
|
|
2765
|
+
return [];
|
|
2766
|
+
}
|
|
2767
|
+
}
|
|
2768
|
+
function onTransactionUpdate(callback) {
|
|
2769
|
+
const unsub = NativeBridge.onGlobalEvent("iap:transactionUpdate", callback);
|
|
2770
|
+
cleanups.push(unsub);
|
|
2771
|
+
return unsub;
|
|
2772
|
+
}
|
|
2773
|
+
onUnmounted15(() => {
|
|
2774
|
+
cleanups.forEach((fn) => fn());
|
|
2775
|
+
cleanups.length = 0;
|
|
2776
|
+
});
|
|
2777
|
+
return {
|
|
2778
|
+
products,
|
|
2779
|
+
isReady,
|
|
2780
|
+
error,
|
|
2781
|
+
getProducts,
|
|
2782
|
+
purchase,
|
|
2783
|
+
restorePurchases,
|
|
2784
|
+
getActiveSubscriptions,
|
|
2785
|
+
onTransactionUpdate
|
|
2786
|
+
};
|
|
2787
|
+
}
|
|
2788
|
+
|
|
2789
|
+
// src/composables/useAppleSignIn.ts
|
|
2790
|
+
import { ref as ref20, onUnmounted as onUnmounted16 } from "@vue/runtime-core";
|
|
2791
|
+
function useAppleSignIn() {
|
|
2792
|
+
const user = ref20(null);
|
|
2793
|
+
const isAuthenticated = ref20(false);
|
|
2794
|
+
const error = ref20(null);
|
|
2795
|
+
const cleanups = [];
|
|
2796
|
+
const unsubscribe = NativeBridge.onGlobalEvent("auth:appleCredentialRevoked", () => {
|
|
2797
|
+
user.value = null;
|
|
2798
|
+
isAuthenticated.value = false;
|
|
2799
|
+
});
|
|
2800
|
+
cleanups.push(unsubscribe);
|
|
2801
|
+
NativeBridge.invokeNativeModule("SocialAuth", "getCurrentUser", ["apple"]).then((result) => {
|
|
2802
|
+
if (result && result.userId) {
|
|
2803
|
+
user.value = { ...result, provider: "apple" };
|
|
2804
|
+
isAuthenticated.value = true;
|
|
2805
|
+
}
|
|
2806
|
+
}).catch(() => {
|
|
2807
|
+
});
|
|
2808
|
+
async function signIn() {
|
|
2809
|
+
error.value = null;
|
|
2810
|
+
try {
|
|
2811
|
+
const result = await NativeBridge.invokeNativeModule("SocialAuth", "signInWithApple");
|
|
2812
|
+
const socialUser = { ...result, provider: "apple" };
|
|
2813
|
+
user.value = socialUser;
|
|
2814
|
+
isAuthenticated.value = true;
|
|
2815
|
+
return { success: true, user: socialUser };
|
|
2816
|
+
} catch (err) {
|
|
2817
|
+
const message = String(err);
|
|
2818
|
+
error.value = message;
|
|
2819
|
+
return { success: false, error: message };
|
|
2820
|
+
}
|
|
2821
|
+
}
|
|
2822
|
+
async function signOut() {
|
|
2823
|
+
error.value = null;
|
|
2824
|
+
try {
|
|
2825
|
+
await NativeBridge.invokeNativeModule("SocialAuth", "signOut", ["apple"]);
|
|
2826
|
+
user.value = null;
|
|
2827
|
+
isAuthenticated.value = false;
|
|
2828
|
+
} catch (err) {
|
|
2829
|
+
error.value = String(err);
|
|
2830
|
+
}
|
|
2831
|
+
}
|
|
2832
|
+
onUnmounted16(() => {
|
|
2833
|
+
cleanups.forEach((fn) => fn());
|
|
2834
|
+
cleanups.length = 0;
|
|
2835
|
+
});
|
|
2836
|
+
return { signIn, signOut, user, isAuthenticated, error };
|
|
2837
|
+
}
|
|
2838
|
+
|
|
2839
|
+
// src/composables/useGoogleSignIn.ts
|
|
2840
|
+
import { ref as ref21, onUnmounted as onUnmounted17 } from "@vue/runtime-core";
|
|
2841
|
+
function useGoogleSignIn(clientId) {
|
|
2842
|
+
const user = ref21(null);
|
|
2843
|
+
const isAuthenticated = ref21(false);
|
|
2844
|
+
const error = ref21(null);
|
|
2845
|
+
const cleanups = [];
|
|
2846
|
+
NativeBridge.invokeNativeModule("SocialAuth", "getCurrentUser", ["google"]).then((result) => {
|
|
2847
|
+
if (result && result.userId) {
|
|
2848
|
+
user.value = { ...result, provider: "google" };
|
|
2849
|
+
isAuthenticated.value = true;
|
|
2850
|
+
}
|
|
2851
|
+
}).catch(() => {
|
|
2852
|
+
});
|
|
2853
|
+
async function signIn() {
|
|
2854
|
+
error.value = null;
|
|
2855
|
+
try {
|
|
2856
|
+
const result = await NativeBridge.invokeNativeModule("SocialAuth", "signInWithGoogle", [clientId]);
|
|
2857
|
+
const socialUser = { ...result, provider: "google" };
|
|
2858
|
+
user.value = socialUser;
|
|
2859
|
+
isAuthenticated.value = true;
|
|
2860
|
+
return { success: true, user: socialUser };
|
|
2861
|
+
} catch (err) {
|
|
2862
|
+
const message = String(err);
|
|
2863
|
+
error.value = message;
|
|
2864
|
+
return { success: false, error: message };
|
|
2865
|
+
}
|
|
2866
|
+
}
|
|
2867
|
+
async function signOut() {
|
|
2868
|
+
error.value = null;
|
|
2869
|
+
try {
|
|
2870
|
+
await NativeBridge.invokeNativeModule("SocialAuth", "signOut", ["google"]);
|
|
2871
|
+
user.value = null;
|
|
2872
|
+
isAuthenticated.value = false;
|
|
2873
|
+
} catch (err) {
|
|
2874
|
+
error.value = String(err);
|
|
2875
|
+
}
|
|
2876
|
+
}
|
|
2877
|
+
onUnmounted17(() => {
|
|
2878
|
+
cleanups.forEach((fn) => fn());
|
|
2879
|
+
cleanups.length = 0;
|
|
2880
|
+
});
|
|
2881
|
+
return { signIn, signOut, user, isAuthenticated, error };
|
|
2882
|
+
}
|
|
2883
|
+
|
|
2884
|
+
// src/composables/useBackgroundTask.ts
|
|
2885
|
+
import { ref as ref22, onUnmounted as onUnmounted18 } from "@vue/runtime-core";
|
|
2886
|
+
function useBackgroundTask() {
|
|
2887
|
+
const taskHandlers = /* @__PURE__ */ new Map();
|
|
2888
|
+
const defaultHandler = ref22(null);
|
|
2889
|
+
const unsubscribe = NativeBridge.onGlobalEvent("background:taskExecute", (payload) => {
|
|
2890
|
+
const handler = taskHandlers.get(payload.taskId) || defaultHandler.value;
|
|
2891
|
+
if (handler) {
|
|
2892
|
+
handler(payload.taskId);
|
|
2893
|
+
}
|
|
2894
|
+
});
|
|
2895
|
+
onUnmounted18(unsubscribe);
|
|
2896
|
+
function registerTask(taskId) {
|
|
2897
|
+
return NativeBridge.invokeNativeModule("BackgroundTask", "registerTask", [taskId]).then(() => void 0);
|
|
2898
|
+
}
|
|
2899
|
+
function scheduleTask(taskId, options = {}) {
|
|
2900
|
+
const type = options.type ?? "refresh";
|
|
2901
|
+
return NativeBridge.invokeNativeModule("BackgroundTask", "scheduleTask", [taskId, type, {
|
|
2902
|
+
earliestBeginDate: options.earliestBeginDate,
|
|
2903
|
+
requiresNetworkConnectivity: options.requiresNetworkConnectivity,
|
|
2904
|
+
requiresExternalPower: options.requiresExternalPower,
|
|
2905
|
+
interval: options.interval
|
|
2906
|
+
}]).then(() => void 0);
|
|
2907
|
+
}
|
|
2908
|
+
function cancelTask(taskId) {
|
|
2909
|
+
return NativeBridge.invokeNativeModule("BackgroundTask", "cancelTask", [taskId]).then(() => void 0);
|
|
2910
|
+
}
|
|
2911
|
+
function cancelAllTasks() {
|
|
2912
|
+
return NativeBridge.invokeNativeModule("BackgroundTask", "cancelAllTasks", []).then(() => void 0);
|
|
2913
|
+
}
|
|
2914
|
+
function completeTask(taskId, success = true) {
|
|
2915
|
+
return NativeBridge.invokeNativeModule("BackgroundTask", "completeTask", [taskId, success]).then(() => void 0);
|
|
2916
|
+
}
|
|
2917
|
+
function onTaskExecute(handler, taskId) {
|
|
2918
|
+
if (taskId) {
|
|
2919
|
+
taskHandlers.set(taskId, handler);
|
|
2920
|
+
return () => {
|
|
2921
|
+
taskHandlers.delete(taskId);
|
|
2922
|
+
};
|
|
2923
|
+
} else {
|
|
2924
|
+
defaultHandler.value = handler;
|
|
2925
|
+
return () => {
|
|
2926
|
+
defaultHandler.value = null;
|
|
2927
|
+
};
|
|
2928
|
+
}
|
|
2929
|
+
}
|
|
2930
|
+
return { registerTask, scheduleTask, cancelTask, cancelAllTasks, completeTask, onTaskExecute };
|
|
2931
|
+
}
|
|
2932
|
+
|
|
2933
|
+
// src/composables/useOTAUpdate.ts
|
|
2934
|
+
import { ref as ref23, onUnmounted as onUnmounted19 } from "@vue/runtime-core";
|
|
2935
|
+
function useOTAUpdate(serverUrl) {
|
|
2936
|
+
const currentVersion = ref23("embedded");
|
|
2937
|
+
const availableVersion = ref23(null);
|
|
2938
|
+
const downloadProgress = ref23(0);
|
|
2939
|
+
const isChecking = ref23(false);
|
|
2940
|
+
const isDownloading = ref23(false);
|
|
2941
|
+
const status = ref23("idle");
|
|
2942
|
+
const error = ref23(null);
|
|
2943
|
+
let lastUpdateInfo = null;
|
|
2944
|
+
const unsubscribe = NativeBridge.onGlobalEvent("ota:downloadProgress", (payload) => {
|
|
2945
|
+
downloadProgress.value = payload.progress;
|
|
2946
|
+
});
|
|
2947
|
+
onUnmounted19(unsubscribe);
|
|
2948
|
+
NativeBridge.invokeNativeModule("OTA", "getCurrentVersion", []).then((info) => {
|
|
2949
|
+
currentVersion.value = info.version;
|
|
2950
|
+
}).catch(() => {
|
|
2951
|
+
});
|
|
2952
|
+
async function checkForUpdate() {
|
|
2953
|
+
isChecking.value = true;
|
|
2954
|
+
status.value = "checking";
|
|
2955
|
+
error.value = null;
|
|
2956
|
+
try {
|
|
2957
|
+
const info = await NativeBridge.invokeNativeModule("OTA", "checkForUpdate", [serverUrl]);
|
|
2958
|
+
lastUpdateInfo = info;
|
|
2959
|
+
if (info.updateAvailable) {
|
|
2960
|
+
availableVersion.value = info.version;
|
|
2961
|
+
} else {
|
|
2962
|
+
availableVersion.value = null;
|
|
2963
|
+
}
|
|
2964
|
+
status.value = info.updateAvailable ? "idle" : "idle";
|
|
2965
|
+
return info;
|
|
2966
|
+
} catch (err) {
|
|
2967
|
+
error.value = err?.message || String(err);
|
|
2968
|
+
status.value = "error";
|
|
2969
|
+
throw err;
|
|
2970
|
+
} finally {
|
|
2971
|
+
isChecking.value = false;
|
|
2972
|
+
}
|
|
2973
|
+
}
|
|
2974
|
+
async function downloadUpdate(url, hash) {
|
|
2975
|
+
const downloadUrl = url || lastUpdateInfo?.downloadUrl;
|
|
2976
|
+
const expectedHash = hash || lastUpdateInfo?.hash;
|
|
2977
|
+
if (!downloadUrl) {
|
|
2978
|
+
const msg = "No download URL. Call checkForUpdate() first or provide a URL.";
|
|
2979
|
+
error.value = msg;
|
|
2980
|
+
status.value = "error";
|
|
2981
|
+
throw new Error(msg);
|
|
2982
|
+
}
|
|
2983
|
+
isDownloading.value = true;
|
|
2984
|
+
downloadProgress.value = 0;
|
|
2985
|
+
status.value = "downloading";
|
|
2986
|
+
error.value = null;
|
|
2987
|
+
try {
|
|
2988
|
+
await NativeBridge.invokeNativeModule("OTA", "downloadUpdate", [downloadUrl, expectedHash || ""]);
|
|
2989
|
+
status.value = "ready";
|
|
2990
|
+
} catch (err) {
|
|
2991
|
+
error.value = err?.message || String(err);
|
|
2992
|
+
status.value = "error";
|
|
2993
|
+
throw err;
|
|
2994
|
+
} finally {
|
|
2995
|
+
isDownloading.value = false;
|
|
2996
|
+
}
|
|
2997
|
+
}
|
|
2998
|
+
async function applyUpdate() {
|
|
2999
|
+
error.value = null;
|
|
3000
|
+
try {
|
|
3001
|
+
await NativeBridge.invokeNativeModule("OTA", "applyUpdate", []);
|
|
3002
|
+
const info = await NativeBridge.invokeNativeModule("OTA", "getCurrentVersion", []);
|
|
3003
|
+
currentVersion.value = info.version;
|
|
3004
|
+
availableVersion.value = null;
|
|
3005
|
+
status.value = "idle";
|
|
3006
|
+
} catch (err) {
|
|
3007
|
+
error.value = err?.message || String(err);
|
|
3008
|
+
status.value = "error";
|
|
3009
|
+
throw err;
|
|
3010
|
+
}
|
|
3011
|
+
}
|
|
3012
|
+
async function rollback() {
|
|
3013
|
+
error.value = null;
|
|
3014
|
+
try {
|
|
3015
|
+
await NativeBridge.invokeNativeModule("OTA", "rollback", []);
|
|
3016
|
+
const info = await NativeBridge.invokeNativeModule("OTA", "getCurrentVersion", []);
|
|
3017
|
+
currentVersion.value = info.version;
|
|
3018
|
+
status.value = "idle";
|
|
3019
|
+
} catch (err) {
|
|
3020
|
+
error.value = err?.message || String(err);
|
|
3021
|
+
status.value = "error";
|
|
3022
|
+
throw err;
|
|
3023
|
+
}
|
|
3024
|
+
}
|
|
3025
|
+
async function getCurrentVersion() {
|
|
3026
|
+
const info = await NativeBridge.invokeNativeModule("OTA", "getCurrentVersion", []);
|
|
3027
|
+
currentVersion.value = info.version;
|
|
3028
|
+
return info;
|
|
3029
|
+
}
|
|
3030
|
+
return {
|
|
3031
|
+
checkForUpdate,
|
|
3032
|
+
downloadUpdate,
|
|
3033
|
+
applyUpdate,
|
|
3034
|
+
rollback,
|
|
3035
|
+
getCurrentVersion,
|
|
3036
|
+
currentVersion,
|
|
3037
|
+
availableVersion,
|
|
3038
|
+
downloadProgress,
|
|
3039
|
+
isChecking,
|
|
3040
|
+
isDownloading,
|
|
3041
|
+
status,
|
|
3042
|
+
error
|
|
3043
|
+
};
|
|
3044
|
+
}
|
|
3045
|
+
|
|
3046
|
+
// src/composables/useBluetooth.ts
|
|
3047
|
+
import { ref as ref24, onUnmounted as onUnmounted20 } from "@vue/runtime-core";
|
|
3048
|
+
function useBluetooth() {
|
|
3049
|
+
const devices = ref24([]);
|
|
3050
|
+
const connectedDevice = ref24(null);
|
|
3051
|
+
const isScanning = ref24(false);
|
|
3052
|
+
const isAvailable = ref24(false);
|
|
3053
|
+
const error = ref24(null);
|
|
3054
|
+
const cleanups = [];
|
|
3055
|
+
NativeBridge.invokeNativeModule("Bluetooth", "getState").then((state) => {
|
|
3056
|
+
isAvailable.value = state === "poweredOn";
|
|
3057
|
+
}).catch(() => {
|
|
3058
|
+
isAvailable.value = false;
|
|
3059
|
+
});
|
|
3060
|
+
const unsubState = NativeBridge.onGlobalEvent("ble:stateChanged", (payload) => {
|
|
3061
|
+
isAvailable.value = payload.state === "poweredOn";
|
|
3062
|
+
});
|
|
3063
|
+
cleanups.push(unsubState);
|
|
3064
|
+
const unsubFound = NativeBridge.onGlobalEvent("ble:deviceFound", (payload) => {
|
|
3065
|
+
const existing = devices.value.findIndex((d) => d.id === payload.id);
|
|
3066
|
+
if (existing >= 0) {
|
|
3067
|
+
devices.value[existing] = payload;
|
|
3068
|
+
} else {
|
|
3069
|
+
devices.value = [...devices.value, payload];
|
|
3070
|
+
}
|
|
3071
|
+
});
|
|
3072
|
+
cleanups.push(unsubFound);
|
|
3073
|
+
const unsubConnected = NativeBridge.onGlobalEvent("ble:connected", (payload) => {
|
|
3074
|
+
connectedDevice.value = payload;
|
|
3075
|
+
});
|
|
3076
|
+
cleanups.push(unsubConnected);
|
|
3077
|
+
const unsubDisconnected = NativeBridge.onGlobalEvent("ble:disconnected", () => {
|
|
3078
|
+
connectedDevice.value = null;
|
|
3079
|
+
});
|
|
3080
|
+
cleanups.push(unsubDisconnected);
|
|
3081
|
+
const unsubError = NativeBridge.onGlobalEvent("ble:error", (payload) => {
|
|
3082
|
+
error.value = payload.message;
|
|
3083
|
+
});
|
|
3084
|
+
cleanups.push(unsubError);
|
|
3085
|
+
async function scan(serviceUUIDs) {
|
|
3086
|
+
devices.value = [];
|
|
3087
|
+
isScanning.value = true;
|
|
3088
|
+
error.value = null;
|
|
3089
|
+
try {
|
|
3090
|
+
await NativeBridge.invokeNativeModule("Bluetooth", "startScan", [serviceUUIDs]);
|
|
3091
|
+
} catch (e) {
|
|
3092
|
+
error.value = e?.message || String(e);
|
|
3093
|
+
isScanning.value = false;
|
|
3094
|
+
}
|
|
3095
|
+
}
|
|
3096
|
+
async function stopScan() {
|
|
3097
|
+
await NativeBridge.invokeNativeModule("Bluetooth", "stopScan");
|
|
3098
|
+
isScanning.value = false;
|
|
3099
|
+
}
|
|
3100
|
+
async function connect(deviceId) {
|
|
3101
|
+
error.value = null;
|
|
3102
|
+
const result = await NativeBridge.invokeNativeModule("Bluetooth", "connect", [deviceId]);
|
|
3103
|
+
return result;
|
|
3104
|
+
}
|
|
3105
|
+
async function disconnect(deviceId) {
|
|
3106
|
+
await NativeBridge.invokeNativeModule("Bluetooth", "disconnect", [deviceId]);
|
|
3107
|
+
connectedDevice.value = null;
|
|
3108
|
+
}
|
|
3109
|
+
async function read(deviceId, serviceUUID, charUUID) {
|
|
3110
|
+
return NativeBridge.invokeNativeModule("Bluetooth", "readCharacteristic", [deviceId, serviceUUID, charUUID]);
|
|
3111
|
+
}
|
|
3112
|
+
async function write(deviceId, serviceUUID, charUUID, data) {
|
|
3113
|
+
return NativeBridge.invokeNativeModule("Bluetooth", "writeCharacteristic", [deviceId, serviceUUID, charUUID, data]);
|
|
3114
|
+
}
|
|
3115
|
+
async function subscribe(deviceId, serviceUUID, charUUID, callback) {
|
|
3116
|
+
await NativeBridge.invokeNativeModule("Bluetooth", "subscribeToCharacteristic", [deviceId, serviceUUID, charUUID]);
|
|
3117
|
+
const unsubscribe = NativeBridge.onGlobalEvent("ble:characteristicChanged", (payload) => {
|
|
3118
|
+
if (payload.deviceId === deviceId && payload.serviceUUID === serviceUUID && payload.characteristicUUID === charUUID) {
|
|
3119
|
+
callback(payload);
|
|
3120
|
+
}
|
|
3121
|
+
});
|
|
3122
|
+
cleanups.push(unsubscribe);
|
|
3123
|
+
return async () => {
|
|
3124
|
+
unsubscribe();
|
|
3125
|
+
await NativeBridge.invokeNativeModule("Bluetooth", "unsubscribeFromCharacteristic", [
|
|
3126
|
+
deviceId,
|
|
3127
|
+
serviceUUID,
|
|
3128
|
+
charUUID
|
|
3129
|
+
]);
|
|
3130
|
+
};
|
|
3131
|
+
}
|
|
3132
|
+
onUnmounted20(() => {
|
|
3133
|
+
if (isScanning.value) {
|
|
3134
|
+
NativeBridge.invokeNativeModule("Bluetooth", "stopScan").catch(() => {
|
|
3135
|
+
});
|
|
3136
|
+
}
|
|
3137
|
+
cleanups.forEach((fn) => fn());
|
|
3138
|
+
cleanups.length = 0;
|
|
3139
|
+
});
|
|
3140
|
+
return {
|
|
3141
|
+
scan,
|
|
3142
|
+
stopScan,
|
|
3143
|
+
connect,
|
|
3144
|
+
disconnect,
|
|
3145
|
+
read,
|
|
3146
|
+
write,
|
|
3147
|
+
subscribe,
|
|
3148
|
+
devices,
|
|
3149
|
+
connectedDevice,
|
|
3150
|
+
isScanning,
|
|
3151
|
+
isAvailable,
|
|
3152
|
+
error
|
|
3153
|
+
};
|
|
3154
|
+
}
|
|
3155
|
+
|
|
3156
|
+
// src/composables/useCalendar.ts
|
|
3157
|
+
import { ref as ref25 } from "@vue/runtime-core";
|
|
3158
|
+
function useCalendar() {
|
|
3159
|
+
const hasAccess = ref25(false);
|
|
3160
|
+
const error = ref25(null);
|
|
3161
|
+
async function requestAccess() {
|
|
3162
|
+
try {
|
|
3163
|
+
const result = await NativeBridge.invokeNativeModule("Calendar", "requestAccess");
|
|
3164
|
+
hasAccess.value = result.granted;
|
|
3165
|
+
return result.granted;
|
|
3166
|
+
} catch (e) {
|
|
3167
|
+
error.value = e?.message || String(e);
|
|
3168
|
+
return false;
|
|
3169
|
+
}
|
|
3170
|
+
}
|
|
3171
|
+
async function getEvents(startDate, endDate) {
|
|
3172
|
+
return NativeBridge.invokeNativeModule("Calendar", "getEvents", [startDate, endDate]);
|
|
3173
|
+
}
|
|
3174
|
+
async function createEvent(options) {
|
|
3175
|
+
return NativeBridge.invokeNativeModule("Calendar", "createEvent", [
|
|
3176
|
+
options.title,
|
|
3177
|
+
options.startDate,
|
|
3178
|
+
options.endDate,
|
|
3179
|
+
options.notes,
|
|
3180
|
+
options.calendarId
|
|
3181
|
+
]);
|
|
3182
|
+
}
|
|
3183
|
+
async function deleteEvent(eventId) {
|
|
3184
|
+
return NativeBridge.invokeNativeModule("Calendar", "deleteEvent", [eventId]);
|
|
3185
|
+
}
|
|
3186
|
+
async function getCalendars() {
|
|
3187
|
+
return NativeBridge.invokeNativeModule("Calendar", "getCalendars");
|
|
3188
|
+
}
|
|
3189
|
+
return { requestAccess, getEvents, createEvent, deleteEvent, getCalendars, hasAccess, error };
|
|
3190
|
+
}
|
|
3191
|
+
|
|
3192
|
+
// src/composables/useContacts.ts
|
|
3193
|
+
import { ref as ref26 } from "@vue/runtime-core";
|
|
3194
|
+
function useContacts() {
|
|
3195
|
+
const hasAccess = ref26(false);
|
|
3196
|
+
const error = ref26(null);
|
|
3197
|
+
async function requestAccess() {
|
|
3198
|
+
try {
|
|
3199
|
+
const result = await NativeBridge.invokeNativeModule("Contacts", "requestAccess");
|
|
3200
|
+
hasAccess.value = result.granted;
|
|
3201
|
+
return result.granted;
|
|
3202
|
+
} catch (e) {
|
|
3203
|
+
error.value = e?.message || String(e);
|
|
3204
|
+
return false;
|
|
3205
|
+
}
|
|
3206
|
+
}
|
|
3207
|
+
async function getContacts(query) {
|
|
3208
|
+
return NativeBridge.invokeNativeModule("Contacts", "getContacts", [query]);
|
|
3209
|
+
}
|
|
3210
|
+
async function getContact(id) {
|
|
3211
|
+
return NativeBridge.invokeNativeModule("Contacts", "getContact", [id]);
|
|
3212
|
+
}
|
|
3213
|
+
async function createContact(data) {
|
|
3214
|
+
return NativeBridge.invokeNativeModule("Contacts", "createContact", [data]);
|
|
3215
|
+
}
|
|
3216
|
+
async function deleteContact(id) {
|
|
3217
|
+
return NativeBridge.invokeNativeModule("Contacts", "deleteContact", [id]);
|
|
3218
|
+
}
|
|
3219
|
+
return { requestAccess, getContacts, getContact, createContact, deleteContact, hasAccess, error };
|
|
3220
|
+
}
|
|
3221
|
+
|
|
1668
3222
|
// src/index.ts
|
|
1669
3223
|
function createApp(rootComponent, rootProps) {
|
|
1670
3224
|
const app = baseCreateApp(rootComponent, rootProps);
|
|
@@ -1688,6 +3242,15 @@ function createApp(rootComponent, rootProps) {
|
|
|
1688
3242
|
app.component("VPicker", VPicker);
|
|
1689
3243
|
app.component("VSegmentedControl", VSegmentedControl);
|
|
1690
3244
|
app.component("VActionSheet", VActionSheet);
|
|
3245
|
+
app.component("VRefreshControl", VRefreshControl);
|
|
3246
|
+
app.component("VPressable", VPressable);
|
|
3247
|
+
app.component("VSectionList", VSectionList);
|
|
3248
|
+
app.component("VCheckbox", VCheckbox);
|
|
3249
|
+
app.component("VRadio", VRadio);
|
|
3250
|
+
app.component("VDropdown", VDropdown);
|
|
3251
|
+
app.component("VVideo", VVideo);
|
|
3252
|
+
app.component("ErrorBoundary", ErrorBoundary);
|
|
3253
|
+
app.component("VErrorBoundary", ErrorBoundary);
|
|
1691
3254
|
app.directive("show", vShow);
|
|
1692
3255
|
app.config.errorHandler = (err, instance, info) => {
|
|
1693
3256
|
const error = err instanceof Error ? err : new Error(String(err));
|
|
@@ -1705,7 +3268,7 @@ function createApp(rootComponent, rootProps) {
|
|
|
1705
3268
|
}
|
|
1706
3269
|
};
|
|
1707
3270
|
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
1708
|
-
app.config.warnHandler = (msg, instance,
|
|
3271
|
+
app.config.warnHandler = (msg, instance, _trace) => {
|
|
1709
3272
|
const componentName = instance?.$options?.name || instance?.$.type?.name || "Anonymous";
|
|
1710
3273
|
console.warn(`[VueNative] Warning in ${componentName}: ${msg}`);
|
|
1711
3274
|
};
|
|
@@ -1722,52 +3285,84 @@ function createApp(rootComponent, rootProps) {
|
|
|
1722
3285
|
return app;
|
|
1723
3286
|
}
|
|
1724
3287
|
export {
|
|
3288
|
+
ErrorBoundary,
|
|
1725
3289
|
NativeBridge,
|
|
1726
3290
|
VActionSheet,
|
|
1727
3291
|
VActivityIndicator,
|
|
1728
3292
|
VAlertDialog,
|
|
1729
3293
|
VButton,
|
|
3294
|
+
VCheckbox,
|
|
3295
|
+
VDropdown,
|
|
1730
3296
|
VImage,
|
|
1731
3297
|
VInput,
|
|
1732
3298
|
VKeyboardAvoiding,
|
|
1733
3299
|
VList,
|
|
1734
3300
|
VModal,
|
|
1735
3301
|
VPicker,
|
|
3302
|
+
VPressable,
|
|
1736
3303
|
VProgressBar,
|
|
3304
|
+
VRadio,
|
|
3305
|
+
VRefreshControl,
|
|
1737
3306
|
VSafeArea,
|
|
1738
3307
|
VScrollView,
|
|
3308
|
+
VSectionList,
|
|
1739
3309
|
VSegmentedControl,
|
|
1740
3310
|
VSlider,
|
|
1741
3311
|
VStatusBar,
|
|
1742
3312
|
VSwitch,
|
|
1743
3313
|
VText,
|
|
3314
|
+
VVideo,
|
|
1744
3315
|
VView,
|
|
1745
3316
|
VWebView,
|
|
3317
|
+
clearSharedElementRegistry,
|
|
1746
3318
|
createApp,
|
|
1747
3319
|
createCommentNode,
|
|
1748
3320
|
createNativeNode,
|
|
1749
3321
|
createStyleSheet,
|
|
1750
3322
|
createTextNode,
|
|
3323
|
+
getRegisteredSharedElements,
|
|
3324
|
+
getSharedElementViewId,
|
|
3325
|
+
measureViewFrame,
|
|
1751
3326
|
render,
|
|
1752
3327
|
resetNodeId,
|
|
3328
|
+
useAccelerometer,
|
|
1753
3329
|
useAnimation,
|
|
1754
3330
|
useAppState,
|
|
3331
|
+
useAppleSignIn,
|
|
1755
3332
|
useAsyncStorage,
|
|
3333
|
+
useAudio,
|
|
1756
3334
|
useBackHandler,
|
|
3335
|
+
useBackgroundTask,
|
|
1757
3336
|
useBiometry,
|
|
3337
|
+
useBluetooth,
|
|
3338
|
+
useCalendar,
|
|
1758
3339
|
useCamera,
|
|
1759
3340
|
useClipboard,
|
|
1760
3341
|
useColorScheme,
|
|
3342
|
+
useContacts,
|
|
3343
|
+
useDatabase,
|
|
1761
3344
|
useDeviceInfo,
|
|
3345
|
+
useDimensions,
|
|
3346
|
+
useFileSystem,
|
|
1762
3347
|
useGeolocation,
|
|
3348
|
+
useGoogleSignIn,
|
|
3349
|
+
useGyroscope,
|
|
1763
3350
|
useHaptics,
|
|
1764
3351
|
useHttp,
|
|
3352
|
+
useI18n,
|
|
3353
|
+
useIAP,
|
|
1765
3354
|
useKeyboard,
|
|
1766
3355
|
useLinking,
|
|
1767
3356
|
useNetwork,
|
|
1768
3357
|
useNotifications,
|
|
3358
|
+
useOTAUpdate,
|
|
3359
|
+
usePerformance,
|
|
1769
3360
|
usePermissions,
|
|
3361
|
+
usePlatform,
|
|
3362
|
+
useSecureStorage,
|
|
1770
3363
|
useShare,
|
|
3364
|
+
useSharedElementTransition,
|
|
3365
|
+
useWebSocket,
|
|
1771
3366
|
vShow,
|
|
1772
3367
|
validStyleProperties
|
|
1773
3368
|
};
|