mirror of
https://github.com/XeroAlpha/CA.git
synced 2024-11-22 17:26:16 +00:00
feat: 基于sqlite数据库的配置存储
This commit is contained in:
parent
7af0b74559
commit
a30ba5c2fb
2
main.js
2
main.js
@ -703,4 +703,6 @@ Loader.fromFile("intl/index.js")
|
||||
Loader.fromFile("modules/builtinData.js")
|
||||
|
||||
Loader.fromFile("modules/LockClasses.js")
|
||||
|
||||
Loader.fromFile("modules/utils/DBSettings.js")
|
||||
});
|
@ -159,7 +159,7 @@ MapScript.loadModule("AndroidBridge", {
|
||||
}
|
||||
},
|
||||
onDismiss : function() {
|
||||
ctx.revokeUriPermission(ctx.getPackageName(), t);
|
||||
ctx.revokeUriPermission(t, 0x3); // Intent.FLAG_GRANT_READ_URI_PERMISSION | FLAG_GRANT_WRITE_URI_PERMISSION
|
||||
}
|
||||
});
|
||||
break;
|
||||
|
@ -68,7 +68,9 @@ MapScript.loadModule("NeteaseAdapter", {
|
||||
getNeteaseVersion : function(packageName) {
|
||||
var c = ctx.getPackageManager().getPackageInfo(packageName, 0).versionCode;
|
||||
this.supportWS = c >= 840035545 && c < 840094571;
|
||||
if (c >= 840213405) { // 2.4.5.213405
|
||||
if (c >= 840217492) { // 2.5.5.217492
|
||||
return "1.18.30.0.0";
|
||||
} else if (c >= 840213405) { // 2.4.5.213405
|
||||
return "1.18.2.0.0";
|
||||
} else if (c >= 840209578) { // 2.3.15.209578
|
||||
return "1.18.1.0.0";
|
||||
|
@ -2,7 +2,7 @@
|
||||
"$schema": "https://ca.projectxero.top/clib/schema_v1.json",
|
||||
"name": "默认命令库",
|
||||
"author": "CA制作组",
|
||||
"description": "该命令库主要包含了单人模式下与核心玩法相关的常用命令用法。",
|
||||
"description": "该命令库主要包含了单人模式下与核心玩法相关的常用命令用法,并且内置了1.19.70.20的ID表。",
|
||||
"uuid": "acf728c5-dd5d-4a38-b43d-7c4f18149fbd",
|
||||
"version": [1, 0, 0],
|
||||
"require": [],
|
||||
@ -132,6 +132,7 @@
|
||||
"black_candle": "黑色蜡烛",
|
||||
"black_candle_cake": "插上黑色蜡烛的蛋糕",
|
||||
"black_glazed_terracotta": "黑色带釉陶瓦",
|
||||
"black_wool": "黑色羊毛",
|
||||
"blackstone": "黑石",
|
||||
"blackstone_double_slab": "双层黑石台阶",
|
||||
"blackstone_slab": "黑石台阶",
|
||||
@ -142,6 +143,7 @@
|
||||
"blue_candle_cake": "插上蓝色蜡烛的蛋糕",
|
||||
"blue_glazed_terracotta": "蓝色带釉陶瓦",
|
||||
"blue_ice": "蓝冰",
|
||||
"blue_wool": "蓝色羊毛",
|
||||
"bone_block": "骨块",
|
||||
"bookshelf": "书架",
|
||||
"border_block": "边界",
|
||||
@ -153,6 +155,7 @@
|
||||
"brown_glazed_terracotta": "棕色带釉陶瓦",
|
||||
"brown_mushroom": "棕色蘑菇",
|
||||
"brown_mushroom_block": "棕色蘑菇方块",
|
||||
"brown_wool": "棕色羊毛",
|
||||
"bubble_column": "气泡柱",
|
||||
"budding_amethyst": "紫水晶母岩",
|
||||
"cactus": "仙人掌",
|
||||
@ -231,6 +234,7 @@
|
||||
"cyan_candle": "青色蜡烛",
|
||||
"cyan_candle_cake": "插上青色蜡烛的蛋糕",
|
||||
"cyan_glazed_terracotta": "青色带釉陶瓦",
|
||||
"cyan_wool": "青色羊毛",
|
||||
"dark_oak_button": "深色橡木按钮",
|
||||
"dark_oak_door": "深色橡木门",
|
||||
"dark_oak_fence_gate": "深色橡木栅栏门",
|
||||
@ -325,9 +329,11 @@
|
||||
"gray_candle": "灰色蜡烛",
|
||||
"gray_candle_cake": "插上灰色蜡烛的蛋糕",
|
||||
"gray_glazed_terracotta": "灰色带釉陶瓦",
|
||||
"gray_wool": "灰色羊毛",
|
||||
"green_candle": "绿色蜡烛",
|
||||
"green_candle_cake": "插上绿色蜡烛的蛋糕",
|
||||
"green_glazed_terracotta": "绿色带釉陶瓦",
|
||||
"green_wool": "绿色羊毛",
|
||||
"grindstone": "砂轮",
|
||||
"hanging_roots": "垂根",
|
||||
"hardened_clay": "陶瓦",
|
||||
@ -368,13 +374,16 @@
|
||||
"light_blue_candle": "淡蓝色蜡烛",
|
||||
"light_blue_candle_cake": "插上淡蓝色蜡烛的蛋糕",
|
||||
"light_blue_glazed_terracotta": "淡蓝色带釉陶瓦",
|
||||
"light_blue_wool": "淡蓝色羊毛",
|
||||
"light_gray_candle": "淡灰色蜡烛",
|
||||
"light_gray_candle_cake": "插上淡灰色蜡烛的蛋糕",
|
||||
"light_gray_wool": "淡灰色羊毛",
|
||||
"light_weighted_pressure_plate": "轻质测重压力板",
|
||||
"lightning_rod": "避雷针",
|
||||
"lime_candle": "黄绿色蜡烛",
|
||||
"lime_candle_cake": "插上黄绿色蜡烛的蛋糕",
|
||||
"lime_glazed_terracotta": "黄绿色带釉陶瓦",
|
||||
"lime_wool": "黄绿色羊毛",
|
||||
"lit_blast_furnace": "燃烧中的高炉",
|
||||
"lit_deepslate_redstone_ore": "点亮的深层红石矿石",
|
||||
"lit_furnace": "燃烧中的熔炉",
|
||||
@ -389,6 +398,7 @@
|
||||
"magenta_candle": "品红色蜡烛",
|
||||
"magenta_candle_cake": "插上品红色蜡烛的蛋糕",
|
||||
"magenta_glazed_terracotta": "品红色带釉陶瓦",
|
||||
"magenta_wool": "品红色羊毛",
|
||||
"magma": "岩浆块",
|
||||
"mangrove_button": "红树木按钮",
|
||||
"mangrove_door": "红树木门",
|
||||
@ -424,7 +434,7 @@
|
||||
"mud_brick_wall": "泥砖墙",
|
||||
"mud_bricks": "泥砖",
|
||||
"muddy_mangrove_roots": "沾泥的红树根",
|
||||
"mycelium": "菌丝",
|
||||
"mycelium": "菌丝体",
|
||||
"nether_brick": "下界砖",
|
||||
"nether_brick_fence": "下界砖栅栏",
|
||||
"nether_brick_stairs": "下界砖楼梯",
|
||||
@ -443,6 +453,7 @@
|
||||
"orange_candle": "橙色蜡烛",
|
||||
"orange_candle_cake": "插上橙色蜡烛的蛋糕",
|
||||
"orange_glazed_terracotta": "橙色带釉陶瓦",
|
||||
"orange_wool": "橙色羊毛",
|
||||
"oxidized_copper": "氧化的铜块",
|
||||
"oxidized_cut_copper": "氧化的切制铜块",
|
||||
"oxidized_cut_copper_slab": "氧化的切制铜台阶",
|
||||
@ -454,6 +465,7 @@
|
||||
"pink_candle": "粉红色蜡烛",
|
||||
"pink_candle_cake": "插上粉红色蜡烛的蛋糕",
|
||||
"pink_glazed_terracotta": "粉红色带釉陶瓦",
|
||||
"pink_wool": "粉红色羊毛",
|
||||
"piston": "活塞",
|
||||
"piston_arm_collision": "活塞头",
|
||||
"planks": "橡木木板/云杉木板/白桦木板/丛林木板/金合欢木板/深色橡木木板",
|
||||
@ -493,6 +505,7 @@
|
||||
"purple_candle": "紫色蜡烛",
|
||||
"purple_candle_cake": "插上紫色蜡烛的蛋糕",
|
||||
"purple_glazed_terracotta": "紫色带釉陶瓦",
|
||||
"purple_wool": "紫色羊毛",
|
||||
"purpur_block": "紫珀块/雕纹紫珀块/紫珀柱/平滑紫珀块",
|
||||
"purpur_stairs": "紫珀楼梯",
|
||||
"quartz_block": "石英块/雕纹石英块/石英柱/平滑石英块",
|
||||
@ -513,6 +526,7 @@
|
||||
"red_nether_brick_stairs": "红色下界砖楼梯",
|
||||
"red_sandstone": "红砂岩/雕纹红砂岩/切制红砂岩/平滑红砂岩",
|
||||
"red_sandstone_stairs": "红砂岩楼梯",
|
||||
"red_wool": "红色羊毛",
|
||||
"redstone_block": "红石块",
|
||||
"redstone_lamp": "红石灯",
|
||||
"redstone_ore": "红石矿石",
|
||||
@ -672,17 +686,18 @@
|
||||
"white_candle": "白色蜡烛",
|
||||
"white_candle_cake": "插上白色蜡烛的蛋糕",
|
||||
"white_glazed_terracotta": "白色带釉陶瓦",
|
||||
"white_wool": "白色羊毛",
|
||||
"wither_rose": "凋灵玫瑰",
|
||||
"wood": "橡木/云杉木/白桦木/丛林木/金合欢木/深色橡木/去皮橡木/去皮云杉木/去皮白桦木/去皮丛林木/去皮金合欢木/去皮深色橡木",
|
||||
"wooden_button": "橡木按钮",
|
||||
"wooden_door": "橡木门",
|
||||
"wooden_pressure_plate": "橡木压力板",
|
||||
"wooden_slab": "橡木台阶/云杉木台阶/白桦木台阶/丛林木台阶/金合欢木台阶/深色橡木台阶",
|
||||
"wool": "羊毛",
|
||||
"yellow_candle": "黄色蜡烛",
|
||||
"yellow_candle_cake": "插上黄色蜡烛的蛋糕",
|
||||
"yellow_flower": "蒲公英",
|
||||
"yellow_glazed_terracotta": "黄色带釉陶瓦"
|
||||
"yellow_glazed_terracotta": "黄色带釉陶瓦",
|
||||
"yellow_wool": "黄色羊毛"
|
||||
},
|
||||
"item": {
|
||||
"acacia_boat": "金合欢木船",
|
||||
@ -743,6 +758,7 @@
|
||||
"black_candle": "黑色蜡烛",
|
||||
"black_dye": "黑色染料",
|
||||
"black_glazed_terracotta": "黑色带釉陶瓦",
|
||||
"black_wool": "黑色羊毛",
|
||||
"blackstone": "黑石",
|
||||
"blackstone_slab": "黑石台阶",
|
||||
"blackstone_stairs": "黑石楼梯",
|
||||
@ -755,6 +771,7 @@
|
||||
"blue_dye": "蓝色染料",
|
||||
"blue_glazed_terracotta": "蓝色带釉陶瓦",
|
||||
"blue_ice": "蓝冰",
|
||||
"blue_wool": "蓝色羊毛",
|
||||
"bone": "骨头",
|
||||
"bone_block": "骨块",
|
||||
"bone_meal": "骨粉",
|
||||
@ -774,6 +791,7 @@
|
||||
"brown_glazed_terracotta": "棕色带釉陶瓦",
|
||||
"brown_mushroom": "棕色蘑菇",
|
||||
"brown_mushroom_block": "棕色蘑菇方块",
|
||||
"brown_wool": "棕色羊毛",
|
||||
"bucket": "桶",
|
||||
"budding_amethyst": "紫水晶母岩",
|
||||
"cactus": "仙人掌",
|
||||
@ -876,6 +894,7 @@
|
||||
"cyan_candle": "青色蜡烛",
|
||||
"cyan_dye": "青色染料",
|
||||
"cyan_glazed_terracotta": "青色带釉陶瓦",
|
||||
"cyan_wool": "青色羊毛",
|
||||
"dark_oak_boat": "深色橡木船",
|
||||
"dark_oak_button": "深色橡木按钮",
|
||||
"dark_oak_chest_boat": "深色橡木运输船",
|
||||
@ -1028,9 +1047,11 @@
|
||||
"gray_candle": "灰色蜡烛",
|
||||
"gray_dye": "灰色染料",
|
||||
"gray_glazed_terracotta": "灰色带釉陶瓦",
|
||||
"gray_wool": "灰色羊毛",
|
||||
"green_candle": "绿色蜡烛",
|
||||
"green_dye": "绿色染料",
|
||||
"green_glazed_terracotta": "绿色带釉陶瓦",
|
||||
"green_wool": "绿色羊毛",
|
||||
"grindstone": "砂轮",
|
||||
"guardian_spawn_egg": "守卫者刷怪蛋",
|
||||
"gunpowder": "火药",
|
||||
@ -1103,13 +1124,16 @@
|
||||
"light_blue_candle": "淡蓝色蜡烛",
|
||||
"light_blue_dye": "淡蓝色染料",
|
||||
"light_blue_glazed_terracotta": "淡蓝色带釉陶瓦",
|
||||
"light_blue_wool": "淡蓝色羊毛",
|
||||
"light_gray_candle": "淡灰色蜡烛",
|
||||
"light_gray_dye": "淡灰色染料",
|
||||
"light_gray_wool": "淡灰色羊毛",
|
||||
"light_weighted_pressure_plate": "轻质测重压力板",
|
||||
"lightning_rod": "避雷针",
|
||||
"lime_candle": "黄绿色蜡烛",
|
||||
"lime_dye": "黄绿色染料",
|
||||
"lime_glazed_terracotta": "黄绿色带釉陶瓦",
|
||||
"lime_wool": "黄绿色羊毛",
|
||||
"lingering_potion": "滞留药水",
|
||||
"lit_pumpkin": "南瓜灯",
|
||||
"llama_spawn_egg": "羊驼刷怪蛋",
|
||||
@ -1121,6 +1145,7 @@
|
||||
"magenta_candle": "品红色蜡烛",
|
||||
"magenta_dye": "品红色染料",
|
||||
"magenta_glazed_terracotta": "品红色带釉陶瓦",
|
||||
"magenta_wool": "品红色羊毛",
|
||||
"magma": "岩浆块",
|
||||
"magma_cream": "岩浆膏",
|
||||
"magma_cube_spawn_egg": "岩浆怪刷怪蛋",
|
||||
@ -1180,7 +1205,7 @@
|
||||
"music_disc_wait": "音乐唱片 C418 - wait",
|
||||
"music_disc_ward": "音乐唱片 C418 - ward",
|
||||
"mutton": "生羊肉",
|
||||
"mycelium": "菌丝",
|
||||
"mycelium": "菌丝体",
|
||||
"name_tag": "命名牌",
|
||||
"nautilus_shell": "鹦鹉螺壳",
|
||||
"nether_brick": "下界砖",
|
||||
@ -1218,6 +1243,7 @@
|
||||
"orange_candle": "橙色蜡烛",
|
||||
"orange_dye": "橙色染料",
|
||||
"orange_glazed_terracotta": "橙色带釉陶瓦",
|
||||
"orange_wool": "橙色羊毛",
|
||||
"oxidized_copper": "氧化的铜块",
|
||||
"oxidized_cut_copper": "氧化的切制铜块",
|
||||
"oxidized_cut_copper_slab": "氧化的切制铜台阶",
|
||||
@ -1239,6 +1265,7 @@
|
||||
"pink_candle": "粉红色蜡烛",
|
||||
"pink_dye": "粉红色染料",
|
||||
"pink_glazed_terracotta": "粉红色带釉陶瓦",
|
||||
"pink_wool": "粉红色羊毛",
|
||||
"piston": "活塞",
|
||||
"planks": "橡木木板/云杉木板/白桦木板/丛林木板/金合欢木板/深色橡木木板",
|
||||
"podzol": "灰化土",
|
||||
@ -1282,6 +1309,7 @@
|
||||
"purple_candle": "紫色蜡烛",
|
||||
"purple_dye": "紫色染料",
|
||||
"purple_glazed_terracotta": "紫色带釉陶瓦",
|
||||
"purple_wool": "紫色羊毛",
|
||||
"purpur_block": "紫珀块/雕纹紫珀块/紫珀柱/平滑紫珀块",
|
||||
"purpur_stairs": "紫珀楼梯",
|
||||
"quartz": "下界石英",
|
||||
@ -1313,6 +1341,7 @@
|
||||
"red_nether_brick_stairs": "红色下界砖楼梯",
|
||||
"red_sandstone": "红砂岩/雕纹红砂岩/切制红砂岩/平滑红砂岩",
|
||||
"red_sandstone_stairs": "红砂岩楼梯",
|
||||
"red_wool": "红色羊毛",
|
||||
"redstone": "红石粉",
|
||||
"redstone_block": "红石块",
|
||||
"redstone_lamp": "红石灯",
|
||||
@ -1509,6 +1538,7 @@
|
||||
"white_candle": "白色蜡烛",
|
||||
"white_dye": "白色染料",
|
||||
"white_glazed_terracotta": "白色带釉陶瓦",
|
||||
"white_wool": "白色羊毛",
|
||||
"witch_spawn_egg": "女巫刷怪蛋",
|
||||
"wither_rose": "凋灵玫瑰",
|
||||
"wither_skeleton_spawn_egg": "凋灵骷髅刷怪蛋",
|
||||
@ -1524,12 +1554,12 @@
|
||||
"wooden_shovel": "木锹",
|
||||
"wooden_slab": "橡木台阶/云杉木台阶/白桦木台阶/丛林木台阶/金合欢木台阶/深色橡木台阶",
|
||||
"wooden_sword": "木剑",
|
||||
"wool": "羊毛",
|
||||
"writable_book": "书与笔",
|
||||
"yellow_candle": "黄色蜡烛",
|
||||
"yellow_dye": "黄色染料",
|
||||
"yellow_flower": "蒲公英",
|
||||
"yellow_glazed_terracotta": "黄色带釉陶瓦",
|
||||
"yellow_wool": "黄色羊毛",
|
||||
"zoglin_spawn_egg": "僵尸疣猪兽刷怪蛋",
|
||||
"zombie_horse_spawn_egg": "僵尸马刷怪蛋",
|
||||
"zombie_pigman_spawn_egg": "僵尸猪人刷怪蛋",
|
||||
@ -1684,7 +1714,7 @@
|
||||
"minecraft:strider": "炽足兽",
|
||||
"minecraft:tadpole": "蝌蚪",
|
||||
"minecraft:thrown_trident": "三叉戟",
|
||||
"minecraft:tnt": "TNT",
|
||||
"minecraft:tnt": "被激活的TNT",
|
||||
"minecraft:tnt_minecart": "TNT矿车",
|
||||
"minecraft:trader_llama": "行商羊驼",
|
||||
"minecraft:tropicalfish": "热带鱼",
|
||||
@ -1744,7 +1774,7 @@
|
||||
"strider": "炽足兽",
|
||||
"tadpole": "蝌蚪",
|
||||
"thrown_trident": "三叉戟",
|
||||
"tnt": "TNT",
|
||||
"tnt": "被激活的TNT",
|
||||
"tnt_minecart": "TNT矿车",
|
||||
"trader_llama": "行商羊驼",
|
||||
"tropicalfish": "热带鱼",
|
||||
@ -2472,6 +2502,9 @@
|
||||
"animation.actor.billboard": "",
|
||||
"animation.agent.move": "",
|
||||
"animation.agent.swing_arms": "",
|
||||
"animation.armor.helmet.offset": "",
|
||||
"animation.armor.chestplate.offset": "",
|
||||
"animation.armor.leggings.offset": "",
|
||||
"animation.armor.boots.offset": "",
|
||||
"animation.armor_stand.athena_pose": "",
|
||||
"animation.armor_stand.brandish_pose": "",
|
||||
@ -2894,7 +2927,8 @@
|
||||
"animation.allay.look_at_target.default": "",
|
||||
"animation.allay.hold_item_fly": "",
|
||||
"animation.vex.idle": "",
|
||||
"animation.vex.charge": ""
|
||||
"animation.vex.charge": "",
|
||||
"animation.evoker.move": ""
|
||||
},
|
||||
"animation_controller": {
|
||||
"controller.animation.agent.move": "",
|
||||
@ -3038,6 +3072,7 @@
|
||||
"controller.animation.allay.look_at_target": "",
|
||||
"controller.animation.vex.idle": "",
|
||||
"controller.animation.vex.charge": "",
|
||||
"controller.animation.humanoid.riding_legs_only": "",
|
||||
"controller.animation.player.base": ""
|
||||
},
|
||||
"particle_emitter": {
|
||||
@ -3311,6 +3346,7 @@
|
||||
"break.hanging_roots": "垂根:被破坏",
|
||||
"break.large_amethyst_bud": "大型紫晶芽:被破坏",
|
||||
"break.medium_amethyst_bud": "中型紫晶芽:被破坏",
|
||||
"break.nether_wood": "",
|
||||
"break.pointed_dripstone": "滴水石锥:被破坏",
|
||||
"break.sculk": "幽匿块:被破坏",
|
||||
"break.sculk_catalyst": "幽匿催发体:被破坏",
|
||||
@ -3348,6 +3384,24 @@
|
||||
"cauldron_drip.water.pointed_dripstone": "水:滴入炼药锅",
|
||||
"charge.sculk": "幽匿块:充能",
|
||||
"chime.amethyst_block": "紫水晶:叮铃",
|
||||
"click_off.metal_pressure_plate": "",
|
||||
"click_off.nether_wood_button": "",
|
||||
"click_off.nether_wood_pressure_plate": "",
|
||||
"click_off.stone_pressure_plate": "",
|
||||
"click_off.wooden_pressure_plate": "",
|
||||
"click_on.metal_pressure_plate": "",
|
||||
"click_on.nether_wood_button": "",
|
||||
"click_on.nether_wood_pressure_plate": "",
|
||||
"click_on.stone_pressure_plate": "",
|
||||
"click_on.wooden_pressure_plate": "",
|
||||
"close.fence_gate": "",
|
||||
"close.iron_door": "",
|
||||
"close.iron_trapdoor": "",
|
||||
"close.nether_wood_door": "",
|
||||
"close.nether_wood_fence_gate": "",
|
||||
"close.nether_wood_trapdoor": "",
|
||||
"close.wooden_door": "",
|
||||
"close.wooden_trapdoor": "",
|
||||
"component.jump_to_block": "实体:跳跃",
|
||||
"conduit.activate": "潮涌核心:激活",
|
||||
"conduit.ambient": "潮涌核心:涌动",
|
||||
@ -3435,6 +3489,7 @@
|
||||
"fall.nether_gold_ore": "下界金矿石:某物摔落",
|
||||
"fall.nether_sprouts": "下界苗:某物摔落",
|
||||
"fall.nether_wart": "下界疣:某物摔落",
|
||||
"fall.nether_wood": "",
|
||||
"fall.netherite": "下界合金块:某物摔落",
|
||||
"fall.netherrack": "下界岩:某物摔落",
|
||||
"fall.nylium": "菌岩:某物摔落",
|
||||
@ -3497,6 +3552,7 @@
|
||||
"hit.nether_gold_ore": "下界金矿石:损坏中",
|
||||
"hit.nether_sprouts": "下界苗:损坏中",
|
||||
"hit.nether_wart": "下界疣:损坏中",
|
||||
"hit.nether_wood": "",
|
||||
"hit.netherite": "下界合金块:损坏中",
|
||||
"hit.netherrack": "下界岩:损坏中",
|
||||
"hit.nylium": "菌岩:损坏中",
|
||||
@ -4094,6 +4150,14 @@
|
||||
"note.pling": "音符盒:播放电钢琴",
|
||||
"note.snare": "音符盒:播放小军鼓",
|
||||
"note.xylophone": "音符盒:播放木琴",
|
||||
"open.fence_gate": "",
|
||||
"open.iron_door": "",
|
||||
"open.iron_trapdoor": "",
|
||||
"open.nether_wood_door": "",
|
||||
"open.nether_wood_fence_gate": "",
|
||||
"open.nether_wood_trapdoor": "",
|
||||
"open.wooden_door": "",
|
||||
"open.wooden_trapdoor": "",
|
||||
"particle.soul_escape": "灵魂:逸散",
|
||||
"pick_berries.cave_vines": "发光浆果:弹出",
|
||||
"place.amethyst_block": "紫水晶块:被放置",
|
||||
@ -4111,6 +4175,7 @@
|
||||
"place.large_amethyst_bud": "大型紫晶芽:被放置",
|
||||
"place.medium_amethyst_bud": "中型紫晶芽:被放置",
|
||||
"place.moss": "苔藓:被放置",
|
||||
"place.nether_wood": "",
|
||||
"place.pointed_dripstone": "滴水石锥:被放置",
|
||||
"place.powder_snow": "细雪:被放置",
|
||||
"place.sculk": "幽匿块:被放置",
|
||||
@ -4160,6 +4225,7 @@
|
||||
"random.swim": "游泳",
|
||||
"random.toast": "UI:弹出",
|
||||
"random.totem": "图腾:发动",
|
||||
"random.wood_click": "按钮:咔哒",
|
||||
"record.11": "音乐唱片(C418 - 11)",
|
||||
"record.13": "音乐唱片(C418 - 13)",
|
||||
"record.5": "音乐唱片(Samuel Åberg - 5)",
|
||||
@ -4216,6 +4282,7 @@
|
||||
"step.nether_gold_ore": "下界金矿石:踩上",
|
||||
"step.nether_sprouts": "下界苗:踩上",
|
||||
"step.nether_wart": "下界疣:踩上",
|
||||
"step.nether_wood": "",
|
||||
"step.netherite": "下界合金块:踩上",
|
||||
"step.netherrack": "下界岩:踩上",
|
||||
"step.nylium": "菌岩:踩上",
|
||||
@ -4305,6 +4372,7 @@
|
||||
"slot.weapon.offhand": "副手持有"
|
||||
},
|
||||
"loot_table": {
|
||||
"blocks/tallgrass": "",
|
||||
"chests/abandoned_mineshaft": "废弃矿井宝箱",
|
||||
"chests/ancient_city": "远古城市宝箱",
|
||||
"chests/ancient_city_ice_box": "远古城市冰窖宝箱",
|
||||
@ -4460,6 +4528,7 @@
|
||||
"gameplay/jungle_fishing": "在丛林生物群系中的钓鱼钓到的物品"
|
||||
},
|
||||
"loot_table_wrapped": {
|
||||
"\"blocks/tallgrass\"": "",
|
||||
"\"chests/abandoned_mineshaft\"": "废弃矿井宝箱",
|
||||
"\"chests/ancient_city\"": "远古城市宝箱",
|
||||
"\"chests/ancient_city_ice_box\"": "远古城市冰窖宝箱",
|
||||
@ -4814,7 +4883,7 @@
|
||||
"minecraft:stray": "流浪者",
|
||||
"minecraft:strider": "炽足兽",
|
||||
"minecraft:tadpole": "蝌蚪",
|
||||
"minecraft:tnt": "TNT",
|
||||
"minecraft:tnt": "被激活的TNT",
|
||||
"minecraft:tnt_minecart": "TNT矿车",
|
||||
"minecraft:trader_llama": "行商羊驼",
|
||||
"minecraft:tropicalfish": "热带鱼",
|
||||
@ -4865,7 +4934,7 @@
|
||||
"stray": "流浪者",
|
||||
"strider": "炽足兽",
|
||||
"tadpole": "蝌蚪",
|
||||
"tnt": "TNT",
|
||||
"tnt": "被激活的TNT",
|
||||
"tnt_minecart": "TNT矿车",
|
||||
"trader_llama": "行商羊驼",
|
||||
"tropicalfish": "热带鱼",
|
||||
@ -4978,6 +5047,7 @@
|
||||
"minecraft:black_candle_cake": "",
|
||||
"minecraft:black_dye": "黑色染料",
|
||||
"minecraft:black_glazed_terracotta": "黑色带釉陶瓦",
|
||||
"minecraft:black_wool": "黑色羊毛",
|
||||
"minecraft:blackstone": "黑石",
|
||||
"minecraft:blackstone_double_slab": "",
|
||||
"minecraft:blackstone_slab": "黑石台阶",
|
||||
@ -4993,6 +5063,7 @@
|
||||
"minecraft:blue_dye": "蓝色染料",
|
||||
"minecraft:blue_glazed_terracotta": "蓝色带釉陶瓦",
|
||||
"minecraft:blue_ice": "蓝冰",
|
||||
"minecraft:blue_wool": "蓝色羊毛",
|
||||
"minecraft:boat": "",
|
||||
"minecraft:bone": "骨头",
|
||||
"minecraft:bone_block": "骨块",
|
||||
@ -5014,6 +5085,7 @@
|
||||
"minecraft:brown_glazed_terracotta": "棕色带釉陶瓦",
|
||||
"minecraft:brown_mushroom": "棕色蘑菇",
|
||||
"minecraft:brown_mushroom_block": "棕色蘑菇方块",
|
||||
"minecraft:brown_wool": "棕色羊毛",
|
||||
"minecraft:bubble_column": "",
|
||||
"minecraft:bucket": "桶",
|
||||
"minecraft:budding_amethyst": "紫水晶母岩",
|
||||
@ -5142,6 +5214,7 @@
|
||||
"minecraft:cyan_candle_cake": "",
|
||||
"minecraft:cyan_dye": "青色染料",
|
||||
"minecraft:cyan_glazed_terracotta": "青色带釉陶瓦",
|
||||
"minecraft:cyan_wool": "青色羊毛",
|
||||
"minecraft:dark_oak_boat": "深色橡木船",
|
||||
"minecraft:dark_oak_button": "深色橡木按钮",
|
||||
"minecraft:dark_oak_chest_boat": "深色橡木运输船",
|
||||
@ -5435,10 +5508,12 @@
|
||||
"minecraft:gray_candle_cake": "",
|
||||
"minecraft:gray_dye": "灰色染料",
|
||||
"minecraft:gray_glazed_terracotta": "灰色带釉陶瓦",
|
||||
"minecraft:gray_wool": "灰色羊毛",
|
||||
"minecraft:green_candle": "绿色蜡烛",
|
||||
"minecraft:green_candle_cake": "",
|
||||
"minecraft:green_dye": "绿色染料",
|
||||
"minecraft:green_glazed_terracotta": "绿色带釉陶瓦",
|
||||
"minecraft:green_wool": "绿色羊毛",
|
||||
"minecraft:grindstone": "砂轮",
|
||||
"minecraft:guardian_spawn_egg": "守卫者刷怪蛋",
|
||||
"minecraft:gunpowder": "火药",
|
||||
@ -5554,15 +5629,18 @@
|
||||
"minecraft:light_blue_candle_cake": "",
|
||||
"minecraft:light_blue_dye": "淡蓝色染料",
|
||||
"minecraft:light_blue_glazed_terracotta": "淡蓝色带釉陶瓦",
|
||||
"minecraft:light_blue_wool": "淡蓝色羊毛",
|
||||
"minecraft:light_gray_candle": "淡灰色蜡烛",
|
||||
"minecraft:light_gray_candle_cake": "",
|
||||
"minecraft:light_gray_dye": "淡灰色染料",
|
||||
"minecraft:light_gray_wool": "淡灰色羊毛",
|
||||
"minecraft:light_weighted_pressure_plate": "轻质测重压力板",
|
||||
"minecraft:lightning_rod": "避雷针",
|
||||
"minecraft:lime_candle": "黄绿色蜡烛",
|
||||
"minecraft:lime_candle_cake": "",
|
||||
"minecraft:lime_dye": "黄绿色染料",
|
||||
"minecraft:lime_glazed_terracotta": "黄绿色带釉陶瓦",
|
||||
"minecraft:lime_wool": "黄绿色羊毛",
|
||||
"minecraft:lingering_potion": "滞留药水",
|
||||
"minecraft:lit_blast_furnace": "",
|
||||
"minecraft:lit_deepslate_redstone_ore": "",
|
||||
@ -5581,6 +5659,7 @@
|
||||
"minecraft:magenta_candle_cake": "",
|
||||
"minecraft:magenta_dye": "品红色染料",
|
||||
"minecraft:magenta_glazed_terracotta": "品红色带釉陶瓦",
|
||||
"minecraft:magenta_wool": "品红色羊毛",
|
||||
"minecraft:magma": "岩浆块",
|
||||
"minecraft:magma_cream": "岩浆膏",
|
||||
"minecraft:magma_cube_spawn_egg": "岩浆怪刷怪蛋",
|
||||
@ -5648,7 +5727,7 @@
|
||||
"minecraft:music_disc_wait": "音乐唱片 C418 - wait",
|
||||
"minecraft:music_disc_ward": "音乐唱片 C418 - ward",
|
||||
"minecraft:mutton": "生羊肉",
|
||||
"minecraft:mycelium": "菌丝",
|
||||
"minecraft:mycelium": "菌丝体",
|
||||
"minecraft:name_tag": "命名牌",
|
||||
"minecraft:nautilus_shell": "鹦鹉螺壳",
|
||||
"minecraft:nether_brick": "下界砖",
|
||||
@ -5690,6 +5769,7 @@
|
||||
"minecraft:orange_candle_cake": "",
|
||||
"minecraft:orange_dye": "橙色染料",
|
||||
"minecraft:orange_glazed_terracotta": "橙色带釉陶瓦",
|
||||
"minecraft:orange_wool": "橙色羊毛",
|
||||
"minecraft:oxidized_copper": "氧化的铜块",
|
||||
"minecraft:oxidized_cut_copper": "氧化的切制铜块",
|
||||
"minecraft:oxidized_cut_copper_slab": "氧化的切制铜台阶",
|
||||
@ -5713,6 +5793,7 @@
|
||||
"minecraft:pink_candle_cake": "",
|
||||
"minecraft:pink_dye": "粉红色染料",
|
||||
"minecraft:pink_glazed_terracotta": "粉红色带釉陶瓦",
|
||||
"minecraft:pink_wool": "粉红色羊毛",
|
||||
"minecraft:piston": "活塞",
|
||||
"minecraft:piston_arm_collision": "",
|
||||
"minecraft:planks": "橡木木板/云杉木板/白桦木板/丛林木板/金合欢木板/深色橡木木板",
|
||||
@ -5767,6 +5848,7 @@
|
||||
"minecraft:purple_candle_cake": "",
|
||||
"minecraft:purple_dye": "紫色染料",
|
||||
"minecraft:purple_glazed_terracotta": "紫色带釉陶瓦",
|
||||
"minecraft:purple_wool": "紫色羊毛",
|
||||
"minecraft:purpur_block": "紫珀块/雕纹紫珀块/紫珀柱/平滑紫珀块",
|
||||
"minecraft:purpur_stairs": "紫珀楼梯",
|
||||
"minecraft:quartz": "下界石英",
|
||||
@ -5800,6 +5882,7 @@
|
||||
"minecraft:red_nether_brick_stairs": "红色下界砖楼梯",
|
||||
"minecraft:red_sandstone": "红砂岩/雕纹红砂岩/切制红砂岩/平滑红砂岩",
|
||||
"minecraft:red_sandstone_stairs": "红砂岩楼梯",
|
||||
"minecraft:red_wool": "红色羊毛",
|
||||
"minecraft:redstone": "红石粉",
|
||||
"minecraft:redstone_block": "红石块",
|
||||
"minecraft:redstone_lamp": "红石灯",
|
||||
@ -6030,6 +6113,7 @@
|
||||
"minecraft:white_candle_cake": "",
|
||||
"minecraft:white_dye": "白色染料",
|
||||
"minecraft:white_glazed_terracotta": "白色带釉陶瓦",
|
||||
"minecraft:white_wool": "白色羊毛",
|
||||
"minecraft:witch_spawn_egg": "女巫刷怪蛋",
|
||||
"minecraft:wither_rose": "凋灵玫瑰",
|
||||
"minecraft:wither_skeleton_spawn_egg": "凋灵骷髅刷怪蛋",
|
||||
@ -6045,7 +6129,7 @@
|
||||
"minecraft:wooden_shovel": "木锹",
|
||||
"minecraft:wooden_slab": "橡木台阶/云杉木台阶/白桦木台阶/丛林木台阶/金合欢木台阶/深色橡木台阶",
|
||||
"minecraft:wooden_sword": "木剑",
|
||||
"minecraft:wool": "羊毛",
|
||||
"minecraft:wool": "",
|
||||
"minecraft:writable_book": "书与笔",
|
||||
"minecraft:written_book": "",
|
||||
"minecraft:yellow_candle": "黄色蜡烛",
|
||||
@ -6053,6 +6137,7 @@
|
||||
"minecraft:yellow_dye": "黄色染料",
|
||||
"minecraft:yellow_flower": "蒲公英",
|
||||
"minecraft:yellow_glazed_terracotta": "黄色带釉陶瓦",
|
||||
"minecraft:yellow_wool": "黄色羊毛",
|
||||
"minecraft:zoglin_spawn_egg": "僵尸疣猪兽刷怪蛋",
|
||||
"minecraft:zombie_horse_spawn_egg": "僵尸马刷怪蛋",
|
||||
"minecraft:zombie_pigman_spawn_egg": "僵尸猪人刷怪蛋",
|
||||
@ -6199,6 +6284,45 @@
|
||||
"versionPack": {
|
||||
"default_enum": {
|
||||
"enums": {
|
||||
"clone_mask_mode": {
|
||||
"masked": "仅复制非空气方块:保留目标区域中对应指定区域中空气的方块",
|
||||
"replace": "[默认]复制所有方块:用指定区域的方块覆盖所有目标区域的方块"
|
||||
},
|
||||
"clone_mode": {
|
||||
"force": "强制复制:即使指定区域与目标区域有重叠也执行复制",
|
||||
"move": "仅移动:复制方块的同时将被复制的方块替换为空气",
|
||||
"normal": "[默认]不执行force与move"
|
||||
},
|
||||
"fill_old_block_handling": {
|
||||
"destroy": "破坏所有:摧毁填充区域内原有的方块,并用指定方块替换填充区域内所有方块。",
|
||||
"hollow": "空心长方体:用指定方块替换填充区域外层的方块,内部方块被替换为空气。",
|
||||
"keep": "仅替换空气:仅用指定方块替换填充区域内的空气方块。",
|
||||
"outline": "仅替换外层:仅用指定方块替换填充区域外层的方块,内部方块保持原样。",
|
||||
"replace": "[默认]替换所有:用指定方块替换填充区域内所有方块或另一指定方块。"
|
||||
},
|
||||
"setblock_old_block_handling": {
|
||||
"destroy": "破坏:摧毁原方块,并用指定方块替换原方块。",
|
||||
"keep": "仅替换空气:仅当原方块为空气时才用指定方块替换原方块。",
|
||||
"replace": "[默认]替换:用指定方块替换原方块。"
|
||||
},
|
||||
"time_query": {
|
||||
"daytime": "一天中的时间(从午夜开始的游戏刻)",
|
||||
"gametime": "游戏时间(从世界创建时开始计算的游戏刻)",
|
||||
"day": "日期(从世界创建时开始计算的游戏日)"
|
||||
},
|
||||
"time_spec": {
|
||||
"day": "上午(1000)",
|
||||
"midnight": "深夜(18000)",
|
||||
"night": "晚上(13000)",
|
||||
"noon": "中午(6000)",
|
||||
"sunrise": "凌晨(23000)",
|
||||
"sunset": "傍晚(12000)"
|
||||
},
|
||||
"weather_type": {
|
||||
"clear": "晴天",
|
||||
"rain": "雨天",
|
||||
"thunder": "雷雨天"
|
||||
},
|
||||
"gamerule_bool": {
|
||||
"commandblockoutput": "命令执行时是否在控制台进行文本提示",
|
||||
"dodaylightcycle": "是否启用日夜交替",
|
||||
@ -6221,7 +6345,6 @@
|
||||
"tntexplodes": "TNT激活后是否爆炸"
|
||||
},
|
||||
"gamerule_int": {},
|
||||
"particle": {},
|
||||
"difficulty": {
|
||||
"peaceful": "和平",
|
||||
"easy": "简单",
|
||||
@ -6375,20 +6498,13 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "遮罩模式",
|
||||
"list": {
|
||||
"masked": "仅复制非空气方块:保留目标区域中对应指定区域中空气的方块",
|
||||
"replace": "[默认]复制所有方块:用指定区域的方块覆盖所有目标区域的方块"
|
||||
},
|
||||
"list": "clone_mask_mode",
|
||||
"optional": true
|
||||
},
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "复制模式",
|
||||
"list": {
|
||||
"force": "强制复制:即使指定区域与目标区域有重叠也执行复制",
|
||||
"move": "仅移动:复制方块的同时将被复制的方块替换为空气",
|
||||
"normal": "[默认]不执行force与move"
|
||||
},
|
||||
"list": "clone_mode",
|
||||
"optional": true
|
||||
}
|
||||
]
|
||||
@ -6416,11 +6532,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "复制模式",
|
||||
"list": {
|
||||
"force": "强制复制:即使指定区域与目标区域有重叠也执行复制",
|
||||
"move": "仅移动:复制方块的同时将被复制的方块替换为空气",
|
||||
"normal": "[默认]不执行force与move"
|
||||
}
|
||||
"list": "clone_mode"
|
||||
},
|
||||
{
|
||||
"type": "string",
|
||||
@ -6488,13 +6600,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "旧方块处理方式",
|
||||
"list": {
|
||||
"destroy": "破坏所有:摧毁填充区域内原有的方块,并用指定方块替换填充区域内所有方块。",
|
||||
"hollow": "空心长方体:用指定方块替换填充区域外层的方块,内部方块被替换为空气。",
|
||||
"keep": "仅替换空气:仅用指定方块替换填充区域内的空气方块。",
|
||||
"outline": "仅替换外层:仅用指定方块替换填充区域外层的方块,内部方块保持原样。",
|
||||
"replace": "[默认]替换所有:用指定方块替换填充区域内所有方块或另一指定方块。"
|
||||
},
|
||||
"list": "fill_old_block_handling",
|
||||
"optional": true
|
||||
}
|
||||
]
|
||||
@ -6668,11 +6774,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "旧方块处理方式",
|
||||
"list": {
|
||||
"destroy": "破坏:摧毁原方块,并用指定方块替换原方块。",
|
||||
"keep": "仅替换空气:仅当原方块为空气时才用指定方块替换原方块。",
|
||||
"replace": "[默认]替换:用指定方块替换原方块。"
|
||||
},
|
||||
"list": "setblock_old_block_handling",
|
||||
"optional": true
|
||||
}
|
||||
]
|
||||
@ -6851,11 +6953,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "时间类型",
|
||||
"list": {
|
||||
"daytime": "这一天的时间(从午夜开始的游戏刻)",
|
||||
"gametime": "游戏时间(从世界创建时开始计算的游戏刻)",
|
||||
"day": "日期(从世界创建时开始计算的游戏日)"
|
||||
}
|
||||
"list": "time_query"
|
||||
}
|
||||
]
|
||||
},
|
||||
@ -6884,14 +6982,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "时间",
|
||||
"list": {
|
||||
"day": "上午(1000)",
|
||||
"midnight": "深夜(18000)",
|
||||
"night": "晚上(13000)",
|
||||
"noon": "中午(6000)",
|
||||
"sunrise": "凌晨(23000)",
|
||||
"sunset": "傍晚(12000)"
|
||||
}
|
||||
"list": "time_spec"
|
||||
}
|
||||
]
|
||||
}
|
||||
@ -6994,11 +7085,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "天气类型",
|
||||
"list": {
|
||||
"clear": "晴天",
|
||||
"rain": "雨天",
|
||||
"thunder": "雷雨天"
|
||||
}
|
||||
"list": "weather_type"
|
||||
},
|
||||
{
|
||||
"type": "uint",
|
||||
@ -8722,7 +8809,8 @@
|
||||
{
|
||||
"type": "selector",
|
||||
"name": "目标",
|
||||
"target": "entity"
|
||||
"target": "entity",
|
||||
"suggestion": "scoreboard_player"
|
||||
},
|
||||
{
|
||||
"type": "plain",
|
||||
@ -8737,7 +8825,8 @@
|
||||
{
|
||||
"type": "selector",
|
||||
"name": "目标",
|
||||
"target": "entity"
|
||||
"target": "entity",
|
||||
"suggestion": "scoreboard_player"
|
||||
},
|
||||
{
|
||||
"type": "plain",
|
||||
@ -8756,7 +8845,8 @@
|
||||
{
|
||||
"type": "selector",
|
||||
"name": "目标",
|
||||
"target": "entity"
|
||||
"target": "entity",
|
||||
"suggestion": "scoreboard_player"
|
||||
},
|
||||
{
|
||||
"type": "plain",
|
||||
@ -9390,10 +9480,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "旧物品处理方式",
|
||||
"list": {
|
||||
"destroy": "[默认]直接替换为目标物品",
|
||||
"keep": "如果目标槽位被占据,则不替换该格内的物品"
|
||||
}
|
||||
"list": "replaceitem_old_item_handling"
|
||||
},
|
||||
{
|
||||
"type": "string",
|
||||
@ -9443,10 +9530,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "旧物品处理方式",
|
||||
"list": {
|
||||
"destroy": "[默认]直接替换为目标物品",
|
||||
"keep": "如果目标槽位被占据,则不替换该格内的物品"
|
||||
}
|
||||
"list": "replaceitem_old_item_handling"
|
||||
},
|
||||
{
|
||||
"type": "string",
|
||||
@ -9474,6 +9558,12 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"enums": {
|
||||
"replaceitem_old_item_handling": {
|
||||
"destroy": "[默认]直接替换为目标物品",
|
||||
"keep": "如果目标槽位被占据,则不替换该格内的物品"
|
||||
}
|
||||
},
|
||||
"supportVer": [
|
||||
{
|
||||
"min": "1.16.0.2",
|
||||
@ -9567,19 +9657,13 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "传送规则",
|
||||
"list": {
|
||||
"teleport_ride": "传送坐骑至骑手(仅在骑手只有一个时有效)",
|
||||
"teleport_rider": "[默认]传送骑手至坐骑"
|
||||
},
|
||||
"list": "ride_teleport_rule",
|
||||
"optional": true
|
||||
},
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "骑乘规则",
|
||||
"list": {
|
||||
"if_group_fits": "仅在骑手都可骑乘指定坐骑时才建立骑乘关系",
|
||||
"until_full": "[默认]为每个可骑乘指定坐骑的骑手建立骑乘关系,直至坐骑已满"
|
||||
},
|
||||
"name": "座位填充方式",
|
||||
"list": "ride_fill_type",
|
||||
"optional": true
|
||||
}
|
||||
]
|
||||
@ -9666,11 +9750,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "骑乘规则",
|
||||
"list": {
|
||||
"no_ride_change": "仅为未骑乘也未被骑乘的骑手生成坐骑",
|
||||
"reassign_rides": "[默认]为骑手解除骑乘关系,随后生成坐骑",
|
||||
"skip_riders": "仅为未骑乘其他坐骑的骑手生成坐骑"
|
||||
},
|
||||
"list": "ride_ride_rule",
|
||||
"optional": true
|
||||
},
|
||||
{
|
||||
@ -9816,6 +9896,21 @@
|
||||
"help": "https://wiki.biligame.com/mc/%E5%91%BD%E4%BB%A4/structure"
|
||||
}
|
||||
},
|
||||
"enums": {
|
||||
"ride_teleport_rule": {
|
||||
"teleport_ride": "传送坐骑至骑手(仅在骑手只有一个时有效)",
|
||||
"teleport_rider": "[默认]传送骑手至坐骑"
|
||||
},
|
||||
"ride_fill_type": {
|
||||
"if_group_fits": "仅在骑手都可骑乘指定坐骑时才建立骑乘关系",
|
||||
"until_full": "[默认]为每个可骑乘指定坐骑的骑手建立骑乘关系,直至坐骑已满"
|
||||
},
|
||||
"ride_ride_rule": {
|
||||
"no_ride_change": "仅为未骑乘也未被骑乘的骑手生成坐骑",
|
||||
"reassign_rides": "[默认]为骑手解除骑乘关系,随后生成坐骑",
|
||||
"skip_riders": "仅为未骑乘其他坐骑的骑手生成坐骑"
|
||||
}
|
||||
},
|
||||
"supportVer": [
|
||||
{
|
||||
"min": "1.16.100.04",
|
||||
@ -10155,10 +10250,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "摇晃方式",
|
||||
"list": {
|
||||
"positional": "[默认]平移镜头摇晃",
|
||||
"rotational": "旋转镜头摇晃"
|
||||
},
|
||||
"list": "camerashake_type",
|
||||
"optional": true
|
||||
}
|
||||
]
|
||||
@ -10249,6 +10341,12 @@
|
||||
"help": "https://wiki.biligame.com/mc/%E5%91%BD%E4%BB%A4/schedule"
|
||||
}
|
||||
},
|
||||
"enums": {
|
||||
"camerashake_type": {
|
||||
"positional": "[默认]平移镜头摇晃",
|
||||
"rotational": "旋转镜头摇晃"
|
||||
}
|
||||
},
|
||||
"supportVer": [
|
||||
{
|
||||
"min": "1.16.100.04",
|
||||
@ -10294,10 +10392,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "动画模式",
|
||||
"list": {
|
||||
"block_by_block": "逐个方块加载",
|
||||
"layer_by_layer": "逐层加载"
|
||||
},
|
||||
"list": "structure_load_animation_mode",
|
||||
"optional": true
|
||||
},
|
||||
{
|
||||
@ -10332,6 +10427,12 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"enums": {
|
||||
"structure_load_animation_mode": {
|
||||
"block_by_block": "逐个方块加载",
|
||||
"layer_by_layer": "逐层加载"
|
||||
}
|
||||
},
|
||||
"supportVer": [
|
||||
{
|
||||
"min": "1.16.100.04",
|
||||
@ -10369,11 +10470,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "复制模式",
|
||||
"list": {
|
||||
"force": "强制复制:即使指定区域与目标区域有重叠也执行复制",
|
||||
"move": "仅移动:复制方块的同时将被复制的方块替换为空气",
|
||||
"normal": "[默认]不执行force与move"
|
||||
}
|
||||
"list": "clone_mode"
|
||||
},
|
||||
{
|
||||
"type": "string",
|
||||
@ -10414,13 +10511,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "旧方块处理方式",
|
||||
"list": { // TODO: global it
|
||||
"destroy": "破坏所有:摧毁填充区域内原有的方块,并用指定方块替换填充区域内所有方块。",
|
||||
"hollow": "空心长方体:用指定方块替换填充区域外层的方块,内部方块被替换为空气。",
|
||||
"keep": "仅替换空气:仅用指定方块替换填充区域内的空气方块。",
|
||||
"outline": "仅替换外层:仅用指定方块替换填充区域外层的方块,内部方块保持原样。",
|
||||
"replace": "[默认]替换所有:用指定方块替换填充区域内所有方块或另一指定方块。"
|
||||
},
|
||||
"list": "fill_old_block_handling",
|
||||
"optional": true
|
||||
}
|
||||
]
|
||||
@ -10485,11 +10576,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "旧方块处理方式",
|
||||
"list": {
|
||||
"destroy": "破坏:摧毁原方块,并用指定方块替换原方块。",
|
||||
"keep": "仅替换空气:仅当原方块为空气时才用指定方块替换原方块。",
|
||||
"replace": "[默认]替换:用指定方块替换原方块。"
|
||||
},
|
||||
"list": "setblock_old_block_handling",
|
||||
"optional": true
|
||||
}
|
||||
]
|
||||
@ -11528,10 +11615,7 @@
|
||||
{
|
||||
"type": "enum",
|
||||
"name": "动画模式",
|
||||
"list": {
|
||||
"block_by_block": "逐个方块加载",
|
||||
"layer_by_layer": "逐层加载"
|
||||
},
|
||||
"list": "structure_load_animation_mode",
|
||||
"optional": true
|
||||
},
|
||||
{
|
||||
@ -11801,8 +11885,15 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"minSupportVer": "1.19.40.21",
|
||||
"maxSupportVer": "1.19.40.22"
|
||||
"supportVer": [
|
||||
{
|
||||
"min": "1.19.40.21",
|
||||
"max": "1.19.40.22"
|
||||
},
|
||||
{
|
||||
"min": "1.19.70.23"
|
||||
}
|
||||
]
|
||||
},
|
||||
"1.19.50.20": {
|
||||
"enums": {
|
||||
@ -12352,6 +12443,42 @@
|
||||
"min": "1.19.50.23"
|
||||
}
|
||||
]
|
||||
},
|
||||
"1.19.70.21": {
|
||||
"commands": {
|
||||
"clone": {
|
||||
"patterns": {
|
||||
"filtered": null
|
||||
}
|
||||
},
|
||||
"execute": {
|
||||
"patterns": {
|
||||
"conditional_block_withData": null
|
||||
}
|
||||
},
|
||||
"fill": {
|
||||
"patterns": {
|
||||
"default": null,
|
||||
"replace": null
|
||||
}
|
||||
},
|
||||
"setblock": {
|
||||
"patterns": {
|
||||
"default": null
|
||||
}
|
||||
},
|
||||
"testforblock": {
|
||||
"patterns": {
|
||||
"default": null
|
||||
}
|
||||
}
|
||||
},
|
||||
"supportVer": [
|
||||
{
|
||||
"min": "1.19.70.21"
|
||||
}
|
||||
],
|
||||
"mode": "remove"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -107,37 +107,16 @@
|
||||
"break.bamboo_wood": "",
|
||||
"break.chiseled_bookshelf": "",
|
||||
"break.hanging_sign": "",
|
||||
"break.nether_wood": "",
|
||||
"click_off.bamboo_wood_button": "",
|
||||
"click_off.bamboo_wood_pressure_plate": "",
|
||||
"click_off.metal_pressure_plate": "",
|
||||
"click_off.nether_wood_button": "",
|
||||
"click_off.nether_wood_pressure_plate": "",
|
||||
"click_off.stone_pressure_plate": "",
|
||||
"click_off.wooden_pressure_plate": "",
|
||||
"click_on.bamboo_wood_button": "",
|
||||
"click_on.bamboo_wood_pressure_plate": "",
|
||||
"click_on.metal_pressure_plate": "",
|
||||
"click_on.nether_wood_button": "",
|
||||
"click_on.nether_wood_pressure_plate": "",
|
||||
"click_on.stone_pressure_plate": "",
|
||||
"click_on.wooden_pressure_plate": "",
|
||||
"close.bamboo_wood_door": "",
|
||||
"close.bamboo_wood_fence_gate": "",
|
||||
"close.bamboo_wood_trapdoor": "",
|
||||
"close.fence_gate": "",
|
||||
"close.iron_door": "",
|
||||
"close.iron_trapdoor": "",
|
||||
"close.nether_wood_door": "",
|
||||
"close.nether_wood_fence_gate": "",
|
||||
"close.nether_wood_trapdoor": "",
|
||||
"close.wooden_door": "",
|
||||
"close.wooden_trapdoor": "",
|
||||
"fall.bamboo_wood": "",
|
||||
"fall.nether_wood": "",
|
||||
"hit.bamboo_wood": "",
|
||||
"hit.chiseled_bookshelf": "",
|
||||
"hit.nether_wood": "",
|
||||
"insert.chiseled_bookshelf": "",
|
||||
"insert_enchanted.chiseled_bookshelf": "",
|
||||
"mob.camel.ambient": "骆驼:呼噜",
|
||||
@ -159,24 +138,13 @@
|
||||
"open.bamboo_wood_door": "",
|
||||
"open.bamboo_wood_fence_gate": "",
|
||||
"open.bamboo_wood_trapdoor": "",
|
||||
"open.fence_gate": "",
|
||||
"open.iron_door": "",
|
||||
"open.iron_trapdoor": "",
|
||||
"open.nether_wood_door": "",
|
||||
"open.nether_wood_fence_gate": "",
|
||||
"open.nether_wood_trapdoor": "",
|
||||
"open.wooden_door": "",
|
||||
"open.wooden_trapdoor": "",
|
||||
"pickup.chiseled_bookshelf": "",
|
||||
"pickup_enchanted.chiseled_bookshelf": "",
|
||||
"place.bamboo_wood": "",
|
||||
"place.chiseled_bookshelf": "",
|
||||
"place.nether_wood": "",
|
||||
"random.wood_click": "按钮:咔哒",
|
||||
"step.bamboo_wood": "",
|
||||
"step.chiseled_bookshelf": "",
|
||||
"step.hanging_sign": "",
|
||||
"step.nether_wood": ""
|
||||
"step.hanging_sign": ""
|
||||
},
|
||||
"summonable_entity": {
|
||||
"camel": "骆驼",
|
||||
|
598
modules/utils/DBSettings.js
Normal file
598
modules/utils/DBSettings.js
Normal file
@ -0,0 +1,598 @@
|
||||
MapScript.loadModule("DBSettings", {
|
||||
dbFile: "settings.db",
|
||||
db: null,
|
||||
onCreate() {
|
||||
// const file = new java.io.File(ctx.getDir("rhino", 0), this.dbFile);
|
||||
const file = new java.io.File(ExternalStorage.getAppSpecificDirectory("settings"), this.dbFile);
|
||||
try {
|
||||
this.db = android.database.sqlite.SQLiteDatabase.openOrCreateDatabase(file, null);
|
||||
} catch(err) {
|
||||
erp(err);
|
||||
this.db = android.database.sqlite.SQLiteDatabase.create(null);
|
||||
}
|
||||
this.transaction(() => {
|
||||
const dbVersion = this.db.getVersion();
|
||||
if (dbVersion < 1) {
|
||||
this.createVersionStore();
|
||||
this.db.setVersion(1);
|
||||
}
|
||||
});
|
||||
},
|
||||
transaction(f) {
|
||||
this.db.beginTransaction();
|
||||
try {
|
||||
f();
|
||||
this.db.setTransactionSuccessful();
|
||||
} finally {
|
||||
this.db.endTransaction();
|
||||
}
|
||||
},
|
||||
objectToContentValues(obj) {
|
||||
const keys = Object.keys(obj);
|
||||
const ret = new android.content.ContentValues(keys.length);
|
||||
keys.forEach((k) => {
|
||||
if (typeof obj[k] == "number") {
|
||||
ret.put(k, new java.lang.Double(obj[k]));
|
||||
} else {
|
||||
ret.put(k, obj[k]);
|
||||
}
|
||||
});
|
||||
return ret;
|
||||
},
|
||||
readCursorRow(cursor) {
|
||||
const ret = {};
|
||||
const columnNames = cursor.getColumnNames();
|
||||
let columnType, columnValue = undefined;
|
||||
for (let i = 0; i < columnNames.length; i++) {
|
||||
columnType = cursor.getType(i);
|
||||
if (columnType == 0) { // FIELD_TYPE_NULL
|
||||
columnValue = null;
|
||||
} else if (columnType == 1) { // FIELD_TYPE_INTEGER
|
||||
columnValue = new java.lang.Long(cursor.getLong(i));
|
||||
} else if (columnType == 2) { // FIELD_TYPE_FLOAT
|
||||
columnValue = cursor.getDouble(i);
|
||||
} else if (columnType == 3) { // FIELD_TYPE_STRING
|
||||
columnValue = cursor.getString(i);
|
||||
} else if (columnType == 4) { // FIELD_TYPE_BLOB
|
||||
columnValue = cursor.getBlob(i);
|
||||
}
|
||||
ret[columnNames[i]] = columnValue;
|
||||
}
|
||||
return ret;
|
||||
},
|
||||
readCursorOnce(cursor) {
|
||||
if (cursor.moveToFirst()) {
|
||||
return this.readCursorRow(cursor);
|
||||
}
|
||||
return null;
|
||||
},
|
||||
readCursorAll(cursor) {
|
||||
const ret = new Array(cursor.getCount());
|
||||
cursor.moveToPosition(-1);
|
||||
while (cursor.moveToNext()) {
|
||||
ret[cursor.getPosition()] = this.readCursorRow(cursor);
|
||||
}
|
||||
return ret;
|
||||
},
|
||||
forEachColumn(cursor, f) {
|
||||
cursor.moveToPosition(-1);
|
||||
let column;
|
||||
while (cursor.moveToNext()) {
|
||||
column = this.readCursorRow(cursor);
|
||||
f(column, cursor.getPosition(), cursor);
|
||||
}
|
||||
},
|
||||
escapeIdentifier(identifier) {
|
||||
return '"' + identifier.replace(/"/g, '""') + '"';
|
||||
},
|
||||
buildColumnDefinition(statement, key, value) {
|
||||
statement.push(this.escapeIdentifier(key));
|
||||
if (typeof value == "object" && value != null) {
|
||||
if (value.type) {
|
||||
statement.push(" " + value.type.toUpperCase());
|
||||
}
|
||||
if (value.primaryKey) {
|
||||
statement.push(" PRIMARY KEY");
|
||||
if (value.autoIncrement) {
|
||||
statement.push(" AUTOINCREMENT");
|
||||
}
|
||||
}
|
||||
if (value.unique) {
|
||||
statement.push(" UNIQUE");
|
||||
}
|
||||
if (value.notNull) {
|
||||
statement.push(" NOT NULL");
|
||||
}
|
||||
} else if (typeof value == "string") {
|
||||
statement.push(" " + value.toUpperCase());
|
||||
}
|
||||
},
|
||||
|
||||
BlobType: Packages["[B"],
|
||||
// Android do not enforce identifier escapes, so use custom execSql
|
||||
prepareSql(statement) {
|
||||
const sql = [], args = [];
|
||||
let i, j, part;
|
||||
if (Array.isArray(statement)) {
|
||||
for (i = 0; i < statement.length; i++) {
|
||||
part = statement[i];
|
||||
if (Array.isArray(part)) {
|
||||
sql.push(part[0]);
|
||||
for (j = 1; j < part.length; j++) {
|
||||
args.push(part[j]);
|
||||
}
|
||||
} else {
|
||||
sql.push(part);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
sql.push(statement);
|
||||
}
|
||||
return [sql.join(""), args];
|
||||
},
|
||||
compileSQL(statement) {
|
||||
const [sql, args] = this.prepareSql(statement);
|
||||
let i, arg;
|
||||
const stmt = this.db.compileStatement(sql);
|
||||
for (i = 1; i <= args.length; i++) {
|
||||
arg = args[i - 1];
|
||||
if (arg == null) {
|
||||
stmt.bindNull(i);
|
||||
} else if (typeof arg == "number") {
|
||||
stmt.bindDouble(i, arg);
|
||||
} else if (typeof arg == "boolean") { // Will cast to 0l or 1l
|
||||
stmt.bindLong(i, arg ? 1 : 0);
|
||||
} else if (arg instanceof java.lang.Long) {
|
||||
stmt.bindLong(i, arg);
|
||||
} else if (arg instanceof this.BlobType) {
|
||||
stmt.bindBlob(i, arg);
|
||||
} else {
|
||||
stmt.bindString(i, String(arg));
|
||||
}
|
||||
}
|
||||
return stmt;
|
||||
},
|
||||
doQuery(statement) {
|
||||
const [sql, args] = this.prepareSql(statement);
|
||||
return this.db.rawQuery(sql, args);
|
||||
},
|
||||
createStore(name, fields, throwIfExists) {
|
||||
const statement = [];
|
||||
statement.push("CREATE TABLE ");
|
||||
if (!throwIfExists) {
|
||||
statement.push("IF NOT EXISTS ");
|
||||
}
|
||||
statement.push(this.escapeIdentifier(name));
|
||||
statement.push("(");
|
||||
Object.entries(fields).forEach((entry, i) => {
|
||||
if (i > 0) {
|
||||
statement.push(",");
|
||||
}
|
||||
this.buildColumnDefinition(statement, entry[0], entry[1]);
|
||||
});
|
||||
statement.push(")");
|
||||
this.compileSQL(statement).execute();
|
||||
},
|
||||
deleteStore(name, ignoreIfExists) {
|
||||
const statement = [];
|
||||
statement.push("DROP TABLE ");
|
||||
if (ignoreIfExists) {
|
||||
statement.push("IF EXISTS ");
|
||||
}
|
||||
statement.push(this.escapeIdentifier(name));
|
||||
this.compileSQL(statement).execute();
|
||||
},
|
||||
renameStore(oldName, newName) {
|
||||
const statement = [];
|
||||
statement.push("ALTER TABLE ");
|
||||
statement.push(this.escapeIdentifier(oldName));
|
||||
statement.push(" RENAME TO ");
|
||||
statement.push(this.escapeIdentifier(newName));
|
||||
this.compileSQL(statement).execute();
|
||||
},
|
||||
migrateStore(name, changes) {
|
||||
Object.entries(changes).forEach((entry) => {
|
||||
const key = entry[0], value = entry[1];
|
||||
const statement = [];
|
||||
statement.push("ALTER TABLE ");
|
||||
statement.push(this.escapeIdentifier(name));
|
||||
if (value == null) {
|
||||
statement.push(" DROP ");
|
||||
statement.push(this.escapeIdentifier(key));
|
||||
} else if (typeof value == "string") {
|
||||
statement.push(" RENAME ");
|
||||
statement.push(this.escapeIdentifier(key));
|
||||
statement.push(" TO ");
|
||||
statement.push(this.escapeIdentifier(value));
|
||||
} else if (typeof value == "object") {
|
||||
statement.push(" ADD ");
|
||||
this.buildColumnDefinition(statement, key, value);
|
||||
}
|
||||
this.compileSQL(statement).execute();
|
||||
});
|
||||
},
|
||||
isStoreExists(name) {
|
||||
const statement = [[
|
||||
"SELECT COUNT(*) FROM sqlite_master WHERE type = 'table' AND name = ?",
|
||||
name
|
||||
]];
|
||||
return this.compileSQL(statement).simpleQueryForLong() > 0;
|
||||
},
|
||||
clearStore(name) {
|
||||
return this.deleteItems({ store: name });
|
||||
},
|
||||
queryItems(options) {
|
||||
const statement = [];
|
||||
statement.push("SELECT ");
|
||||
if (options.distinct) {
|
||||
statement.push("DISTINCT ");
|
||||
}
|
||||
if (options.fields) {
|
||||
let escapedFields;
|
||||
if (Array.isArray(options.fields)) {
|
||||
escapedFields = options.fields.map((e) => this.escapeIdentifier(e));
|
||||
} else {
|
||||
escapedFields = Object.entries(options.fields).map((e) => {
|
||||
return e[1] + " AS " + this.escapeIdentifier(e[0]);
|
||||
});
|
||||
}
|
||||
statement.push(escapedFields.join(","));
|
||||
} else {
|
||||
statement.push("*");
|
||||
}
|
||||
statement.push(" FROM ", this.escapeIdentifier(options.store));
|
||||
if (options.selection) {
|
||||
statement.push(" WHERE ", options.selection);
|
||||
}
|
||||
if (options.groupBy) {
|
||||
statement.push(" GROUP BY ", options.groupBy);
|
||||
if (options.having) {
|
||||
statement.push(" HAVING ", options.having);
|
||||
}
|
||||
}
|
||||
if (options.orderBy) {
|
||||
statement.push(" ORDER BY ", options.orderBy);
|
||||
}
|
||||
if (options.limit) {
|
||||
statement.push(" LIMIT ", options.limit);
|
||||
}
|
||||
return this.doQuery(statement);
|
||||
},
|
||||
ConflictAlgorithm: {
|
||||
none: "",
|
||||
rollback: " OR ROLLBACK",
|
||||
abort: " OR ABORT",
|
||||
fail: " OR FAIL",
|
||||
ignore: " OR IGNORE",
|
||||
replace: " OR REPLACE"
|
||||
},
|
||||
putItems(options) {
|
||||
const statement = [];
|
||||
statement.push("INSERT");
|
||||
statement.push(this.ConflictAlgorithm[options.onConflict || "none"]);
|
||||
statement.push(" INTO ")
|
||||
statement.push(this.escapeIdentifier(options.store));
|
||||
statement.push("(");
|
||||
const items = options.items;
|
||||
const keys = Object.keys(items[0]);
|
||||
keys.forEach((k, i) => {
|
||||
if (i > 0) {
|
||||
statement.push(",");
|
||||
}
|
||||
statement.push(this.escapeIdentifier(k));
|
||||
});
|
||||
statement.push(") VALUES ");
|
||||
items.forEach((item, i) => {
|
||||
if (i > 0) {
|
||||
statement.push(",");
|
||||
}
|
||||
statement.push("(");
|
||||
keys.forEach((k, j) => {
|
||||
if (j > 0) {
|
||||
statement.push(",");
|
||||
}
|
||||
statement.push(["?", item[k]]);
|
||||
});
|
||||
statement.push(")");
|
||||
});
|
||||
return this.compileSQL(statement).executeInsert();
|
||||
},
|
||||
setItem(options) {
|
||||
return this.putItems({
|
||||
store: options.store,
|
||||
items: [options.item],
|
||||
onConflict: "replace"
|
||||
});
|
||||
},
|
||||
updateItems(options) {
|
||||
const statement = [];
|
||||
statement.push("UPDATE");
|
||||
statement.push(this.ConflictAlgorithm[options.onConflict || "none"]);
|
||||
statement.push(this.escapeIdentifier(options.store));
|
||||
statement.push(" SET ");
|
||||
const changes = options.changes;
|
||||
Object.keys(changes).forEach((k, i) => {
|
||||
if (i > 0) {
|
||||
statement.push(",");
|
||||
}
|
||||
statement.push(this.escapeIdentifier(k));
|
||||
statement.push(["=?", changes[k]]);
|
||||
});
|
||||
if (options.selection) {
|
||||
statement.push(" WHERE ", options.selection);
|
||||
}
|
||||
return this.compileSQL(statement).executeUpdateDelete();
|
||||
},
|
||||
deleteItems(options) {
|
||||
const statement = [];
|
||||
statement.push("DELETE FROM ");
|
||||
statement.push(this.escapeIdentifier(options.store));
|
||||
if (options.selection) {
|
||||
statement.push(" WHERE ", options.selection);
|
||||
}
|
||||
return this.compileSQL(statement).executeUpdateDelete();
|
||||
},
|
||||
checkFieldType(value) {
|
||||
const type = typeof value;
|
||||
if (type == "object" && (value == null || value instanceof this.BlobType)) {
|
||||
return;
|
||||
}
|
||||
if (type == "object"
|
||||
|| type == "undefined"
|
||||
|| type == "bigint"
|
||||
|| type == "symbol"
|
||||
|| type == "function") {
|
||||
throw new Error("DBSettings cannot storage " + type);
|
||||
}
|
||||
},
|
||||
|
||||
createVersionStore() {
|
||||
this.createStore("version", {
|
||||
store_name: { type: "text", primaryKey: true },
|
||||
version: "int"
|
||||
});
|
||||
},
|
||||
getStoreVersion(name) {
|
||||
const cursor = this.queryItems({
|
||||
store: "version",
|
||||
fields: ["version"],
|
||||
selection: ["store_name = ?", name],
|
||||
limit: "1",
|
||||
});
|
||||
const ret = this.readCursorOnce(cursor);
|
||||
return ret ? ret.version : 0;
|
||||
},
|
||||
setStoreVersion(name, version) {
|
||||
this.setItem({
|
||||
store: "version",
|
||||
item: {
|
||||
store_name: name,
|
||||
version: version
|
||||
}
|
||||
});
|
||||
},
|
||||
deleteStoreWithVersion(name) {
|
||||
this.deleteStore(name);
|
||||
this.deleteItems({
|
||||
store: "version",
|
||||
selection: ["store_name = ?", name]
|
||||
});
|
||||
},
|
||||
|
||||
getUndefinedInstance(cx, scope) {
|
||||
return com.xero.ca.script.WrappedUndefined.get(cx, scope);
|
||||
},
|
||||
createProxy(target, handler) {
|
||||
const cx = org.mozilla.javascript.Context.getCurrentContext();
|
||||
const topScope = eval.call(null, "this");
|
||||
const targetScriptable = new org.mozilla.javascript.NativeJavaObject(topScope, target, org.mozilla.javascript.Scriptable);
|
||||
const OriginCall = (method) => targetScriptable[method].bind(targetScriptable);
|
||||
const Undefined = this.getUndefinedInstance(cx, topScope);
|
||||
const scriptable = new org.mozilla.javascript.Scriptable({
|
||||
delete: handler.deleteProperty ? (key) => {
|
||||
handler.deleteProperty(target, key);
|
||||
} : OriginCall("delete"),
|
||||
get: handler.get ? (key, start) => {
|
||||
const r = handler.get(target, key, start);
|
||||
if (typeof r == "undefined") {
|
||||
return Undefined;
|
||||
}
|
||||
return r;
|
||||
} : (key, start) => {
|
||||
const r = targetScriptable.get(key, start);
|
||||
if (typeof r == "undefined") {
|
||||
return Undefined;
|
||||
}
|
||||
return r;
|
||||
},
|
||||
getClassName: () => `Proxy<${targetScriptable.getClassName()}>`,
|
||||
getDefaultValue: OriginCall("getDefaultValue"),
|
||||
getIds: handler.ownKeys ? () => {
|
||||
const keys = handler.ownKeys(target);
|
||||
const arr = java.lang.reflect.Array.newInstance(java.lang.Object, keys.length);
|
||||
for (let i = 0; i < keys.length; i++) {
|
||||
if (typeof keys[i] == "number") {
|
||||
arr[i] = new java.lang.Integer(keys[i]);
|
||||
} else {
|
||||
arr[i] = keys[i];
|
||||
}
|
||||
}
|
||||
return arr;
|
||||
} : OriginCall("getIds"),
|
||||
getParentScope: OriginCall("getParentScope"),
|
||||
getPrototype: handler.getPrototypeOf ? () => {
|
||||
return handler.getPrototypeOf(target);
|
||||
} : OriginCall("getPrototype"),
|
||||
has: handler.has ? (key, start) => {
|
||||
return handler.has(target, key, start);
|
||||
} : OriginCall("has"),
|
||||
hasInstance: OriginCall("hasInstance"),
|
||||
put: handler.set ? (key, start, value) => {
|
||||
handler.set(target, key, value, start);
|
||||
} : (key, start, value) => {
|
||||
targetScriptable.put(key, target, value);
|
||||
},
|
||||
setParentScope: OriginCall("setParentScope"),
|
||||
setPrototype: handler.setPrototypeOf ? (proto) => {
|
||||
return handler.setPrototypeOf(target, proto);
|
||||
} : OriginCall("setPrototype")
|
||||
});
|
||||
return cx.toObject(scriptable, topScope);
|
||||
},
|
||||
|
||||
ensureNamespace(storeName) {
|
||||
const version = this.getStoreVersion(storeName);
|
||||
if (version < 1) {
|
||||
this.createStore(storeName, {
|
||||
id: { type: "integer", primaryKey: true, autoIncrement: true }, // rowid
|
||||
parent: "integer",
|
||||
key: null,
|
||||
type: "integer",
|
||||
value: null
|
||||
});
|
||||
this.setStoreVersion(storeName, 1);
|
||||
}
|
||||
},
|
||||
allocateRefId(storeName) {
|
||||
const query = this.queryItems({
|
||||
store: storeName,
|
||||
fields: { "max": "max(value)" },
|
||||
selection: "type = 3 or type = 4"
|
||||
});
|
||||
const ret = this.readCursorOnce(query);
|
||||
return new java.lang.Long(ret.max == null ? 1 : ret.max + 1);
|
||||
},
|
||||
convertToJSValue(storeName, dbTypeId, dbValue) {
|
||||
switch(Number(dbTypeId)) {
|
||||
case 0: // primitive: number / string / byte[] / null
|
||||
return dbValue;
|
||||
case 1: // boolean
|
||||
return dbValue != 0;
|
||||
case 2: // Date
|
||||
return new Date(dbValue);
|
||||
case 3: // object
|
||||
return this.getNamespaceProxy(storeName, dbValue, "object");
|
||||
case 4: // array
|
||||
return this.getNamespaceProxy(storeName, dbValue, "array");
|
||||
}
|
||||
},
|
||||
convertToDBValue(storeName, jsValue) {
|
||||
const type = typeof jsValue;
|
||||
if (type == "number" || type == "string") {
|
||||
return { type: 0, value: jsValue };
|
||||
}
|
||||
if (type == "boolean") {
|
||||
return { type: 1, value: jsValue ? 1 : 0 };
|
||||
}
|
||||
if (type == "object") {
|
||||
if (jsValue == null || jsValue instanceof this.BlobType || jsValue instanceof java.lang.Long) {
|
||||
return { type: 0, value: jsValue };
|
||||
}
|
||||
if (jsValue instanceof Date) {
|
||||
return { type: 2, value: jsValue.getTime() };
|
||||
}
|
||||
const isArray = jsValue instanceof Array;
|
||||
if (jsValue.__id__) {
|
||||
return {
|
||||
type: isArray ? 4 : 3,
|
||||
value: jsValue.__id__
|
||||
};
|
||||
}
|
||||
const refId = this.allocateRefId(storeName);
|
||||
const proxy = this.getNamespaceProxy(storeName, refId, isArray ? "array" : "object");
|
||||
return {
|
||||
type: isArray ? 4 : 3,
|
||||
value: refId,
|
||||
proxy: proxy,
|
||||
afterStored: () => {
|
||||
Object.entries(jsValue).forEach((entry) => {
|
||||
proxy[entry[0]] = entry[1];
|
||||
});
|
||||
}
|
||||
};
|
||||
}
|
||||
},
|
||||
getNamespaceProxy(storeName, startId, startType) {
|
||||
const base = startType == "array" ? [] : {};
|
||||
const idMap = {};
|
||||
const cursor = this.queryItems({
|
||||
store: storeName,
|
||||
selection: ["parent = ?", startId]
|
||||
});
|
||||
Object.defineProperty(base, "__id__", { value: startId });
|
||||
this.forEachColumn(cursor, (entry) => {
|
||||
base[entry.key] = this.convertToJSValue(storeName, entry.type, entry.value);
|
||||
idMap[entry.key] = entry.id;
|
||||
});
|
||||
const proxy = this.createProxy(base, {
|
||||
set: (target, key, value) => {
|
||||
const converted = this.convertToDBValue(storeName, value);
|
||||
if (!converted) throw new Error(`Cannot set ${key} to ${value}`);
|
||||
const item = {
|
||||
parent: startId,
|
||||
key: typeof key == "number" ? new java.lang.Long(key) : key,
|
||||
type: converted.type,
|
||||
value: converted.value
|
||||
};
|
||||
if (key in idMap) {
|
||||
item.id = idMap[key];
|
||||
}
|
||||
idMap[key] = this.setItem({
|
||||
store: storeName,
|
||||
item: item
|
||||
});
|
||||
target[key] = converted.proxy || value;
|
||||
if (converted.afterStored) {
|
||||
converted.afterStored();
|
||||
}
|
||||
return true;
|
||||
},
|
||||
deleteProperty: (target, key) => {
|
||||
const id = idMap[key];
|
||||
delete target[key];
|
||||
delete idMap[key];
|
||||
this.deleteItems({
|
||||
store: storeName,
|
||||
selection: ["id = ?", id]
|
||||
});
|
||||
}
|
||||
});
|
||||
return proxy;
|
||||
},
|
||||
doNamespaceGC(storeName) {
|
||||
const cursor = this.queryItems({
|
||||
store: storeName,
|
||||
});
|
||||
const entries = this.readCursorAll(cursor);
|
||||
const visit = (parentRef, parent) => {
|
||||
const children = entries.filter((e) => e.parent == parentRef);
|
||||
children.forEach((child) => {
|
||||
if (child.visited && parent) {
|
||||
parent.circular = true;
|
||||
}
|
||||
child.visited = true;
|
||||
if (child.type == 3 || child.type == 4) {
|
||||
visit(child.value, child.id);
|
||||
}
|
||||
});
|
||||
};
|
||||
visit(0, null);
|
||||
this.transaction(() => {
|
||||
entries.forEach((e) => {
|
||||
if (!e.visited || e.circular) {
|
||||
this.deleteItems({
|
||||
store: storeName,
|
||||
selection: ["id=?", e.id]
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
},
|
||||
getNamespace(storeName) {
|
||||
this.ensureNamespace(storeName);
|
||||
this.doNamespaceGC(storeName);
|
||||
return this.getNamespaceProxy(storeName, 0, "object");
|
||||
}
|
||||
});
|
||||
|
||||
MapScript.loadModule("Settings", DBSettings.getNamespace("settings"));
|
@ -573,7 +573,8 @@ MapScript.loadModule("ExternalStorage", {
|
||||
return false;
|
||||
},
|
||||
importFile(uri, hint) {
|
||||
const importFile = this.createImportFile(hint.replace("**", this.uriToName(uri)));
|
||||
if (hint) hint = hint.replace("**", this.uriToName(uri));
|
||||
const importFile = this.createImportFile(hint);
|
||||
const input = this.openInputStream(uri);
|
||||
importFile.getParentFile().mkdirs();
|
||||
const output = new java.io.FileOutputStream(importFile);
|
||||
|
294
modules/utils/JSONHelper.js
Normal file
294
modules/utils/JSONHelper.js
Normal file
@ -0,0 +1,294 @@
|
||||
MapScript.loadModule("JSONHelper", {
|
||||
Context: function(str, onToken, options) {
|
||||
this.p = 0;
|
||||
this.s = str;
|
||||
this.onToken = onToken || (() => void 0);
|
||||
this.eof = () => this.p >= this.s.length;
|
||||
this.rest = () => this.s.slice(this.p);
|
||||
this.peek = (n) => {
|
||||
if (this.eof()) this.reportError("Unexpected EOF");
|
||||
return n ? this.s.slice(this.p, this.p + n) : this.s.charAt(this.p);
|
||||
};
|
||||
this.expect = (ch) => {
|
||||
if (this.peek() == ch) {
|
||||
this.p++;
|
||||
return ch;
|
||||
} else {
|
||||
this.reportError("Expected " + ch);
|
||||
}
|
||||
}
|
||||
this.consume = (n) => {
|
||||
if (n) this.p += n - 1;
|
||||
if (this.eof()) this.reportError("Unexpected EOF");
|
||||
this.p++;
|
||||
return n ? this.s.slice(this.p - n, this.p) : this.s.charAt(this.p - 1);
|
||||
}
|
||||
this.token = (type, f) => {
|
||||
const start = this.p;
|
||||
const value = f();
|
||||
this.onToken(start, this.p, type, value);
|
||||
return value;
|
||||
}
|
||||
this.reportError = (msg) => {
|
||||
const err = new Error(msg);
|
||||
err.position = this.p;
|
||||
throw err;
|
||||
};
|
||||
Object.assign(this, options);
|
||||
},
|
||||
JSON: {},
|
||||
JSONC: {
|
||||
allowComments: true
|
||||
},
|
||||
JSON5: {
|
||||
allowComments: true,
|
||||
allowTrailingComma: true,
|
||||
allowSingleQuote: true,
|
||||
allowLatinEscape: true,
|
||||
allowEscapeAny: true,
|
||||
allowIdentiferAsName: true,
|
||||
whitespaces: " \t\r\n",
|
||||
identifierRegExp: /^[^\s"'\\:]+/
|
||||
},
|
||||
scan(str, onToken, options) {
|
||||
let cx = new this.Context(str, onToken, options);
|
||||
const ret = this.scanNext(cx);
|
||||
this.skipWhitespace(cx);
|
||||
if (!cx.eof()) {
|
||||
cx.reportError("Unexpected JSON end");
|
||||
}
|
||||
return ret;
|
||||
},
|
||||
scanNext(cx) {
|
||||
this.skipWhitespace(cx);
|
||||
const ch = cx.peek();
|
||||
if (ch == "{") {
|
||||
return this.scanObject(cx);
|
||||
}
|
||||
if (ch == "[") {
|
||||
return this.scanArray(cx);
|
||||
}
|
||||
if (ch == "\"" || ch == "'") {
|
||||
return cx.token("literal", () => this.scanString(cx));
|
||||
}
|
||||
if (ch == "-" || ch == "+" || ch >= "0" && ch <= "9" || ch == "N") {
|
||||
return cx.token("literal", () => this.scanNumber(cx));
|
||||
}
|
||||
return cx.token("literal", () => this.scanLiteral(cx));
|
||||
},
|
||||
scanObject(cx) {
|
||||
cx.token("objectBegin", () => cx.expect("{"));
|
||||
let expectComma = false, afterComma = false;
|
||||
const object = {};
|
||||
this.skipWhitespace(cx);
|
||||
let name, value;
|
||||
for (;;) {
|
||||
if (cx.peek() == "}") {
|
||||
if (afterComma && !cx.allowTrailingComma) {
|
||||
cx.reportError("Trailing comma not allowed");
|
||||
}
|
||||
cx.token("objectEnd", () => cx.consume());
|
||||
break;
|
||||
}
|
||||
if (expectComma) {
|
||||
cx.token("objectSeparator", () => cx.expect(","));
|
||||
this.skipWhitespace(cx);
|
||||
expectComma = false;
|
||||
afterComma = true;
|
||||
continue;
|
||||
}
|
||||
name = cx.token("propertyName", () => this.scanIdentifier(cx));
|
||||
this.skipWhitespace(cx);
|
||||
cx.token("propertySeparator", () => cx.expect(":"));
|
||||
value = this.scanNext(cx);
|
||||
object[name] = value;
|
||||
this.skipWhitespace(cx);
|
||||
expectComma = true;
|
||||
afterComma = false;
|
||||
}
|
||||
return object;
|
||||
},
|
||||
scanArray(cx) {
|
||||
cx.token("arrayBegin", () => cx.expect("["));
|
||||
let expectComma = false, afterComma = false;
|
||||
const array = [];
|
||||
this.skipWhitespace(cx);
|
||||
let value;
|
||||
for (;;) {
|
||||
if (cx.peek() == "]") {
|
||||
if (afterComma && !cx.allowTrailingComma) {
|
||||
cx.reportError("Trailing comma not allowed");
|
||||
}
|
||||
cx.token("arrayEnd", () => cx.consume());
|
||||
break;
|
||||
}
|
||||
if (expectComma) {
|
||||
cx.token("arraySeparator", () => cx.expect(","));
|
||||
this.skipWhitespace(cx);
|
||||
expectComma = false;
|
||||
afterComma = true;
|
||||
continue;
|
||||
}
|
||||
value = this.scanNext(cx);
|
||||
array.push(value);
|
||||
this.skipWhitespace(cx);
|
||||
expectComma = true;
|
||||
afterComma = false;
|
||||
}
|
||||
return array;
|
||||
},
|
||||
Literals: {
|
||||
"true": true,
|
||||
"false": false,
|
||||
"null": null
|
||||
},
|
||||
scanLiteral(cx) {
|
||||
let key;
|
||||
const literals = cx.literals || this.Literals;
|
||||
for (key in literals) {
|
||||
if (cx.peek(key.length) == key) {
|
||||
cx.consume(key.length);
|
||||
return literals[key];
|
||||
}
|
||||
}
|
||||
cx.reportError("Unknown literal");
|
||||
},
|
||||
scanIdentifier(cx) {
|
||||
if (cx.identifierRegExp) {
|
||||
const match = cx.rest().match(cx.identifierRegExp);
|
||||
if (match) {
|
||||
cx.consume(match[0].length);
|
||||
return match[0];
|
||||
}
|
||||
}
|
||||
return this.scanString(cx);
|
||||
},
|
||||
StringEscapes: {
|
||||
"\"": "\"",
|
||||
"\\": "\\",
|
||||
"/": "/",
|
||||
"b": "\b",
|
||||
"f": "\f",
|
||||
"n": "\n",
|
||||
"r": "\r",
|
||||
"t": "\t"
|
||||
},
|
||||
scanString(cx) {
|
||||
let quote;
|
||||
if (cx.allowSingleQuote && cx.peek() == "'") {
|
||||
quote = cx.consume();
|
||||
} else {
|
||||
quote = cx.expect("\"");
|
||||
}
|
||||
const escapeMap = cx.escapes || this.StringEscapes;
|
||||
const characters = [];
|
||||
let ch, esc, hex;
|
||||
for (;;) {
|
||||
ch = cx.peek();
|
||||
if (ch == quote) {
|
||||
cx.consume();
|
||||
break;
|
||||
}
|
||||
if (ch == "\\") {
|
||||
cx.consume();
|
||||
esc = cx.peek();
|
||||
if (esc == "u") {
|
||||
cx.consume();
|
||||
hex = cx.peek(4);
|
||||
if (hex.match(/[0-9a-fA-F]{4}/)) {
|
||||
cx.consume(4);
|
||||
characters.push(String.fromCharCode(parseInt(hex, 16)));
|
||||
} else {
|
||||
cx.reportError("Illegal unicode codepoint");
|
||||
}
|
||||
} else if (cx.allowLatinEscape && esc == "x") {
|
||||
cx.consume();
|
||||
hex = cx.peek(2);
|
||||
if (hex.match(/[0-9a-fA-F]{2}/)) {
|
||||
cx.consume(2);
|
||||
characters.push(String.fromCharCode(parseInt(hex, 16)));
|
||||
} else {
|
||||
cx.reportError("Illegal latin codepoint");
|
||||
}
|
||||
} else if (esc in escapeMap) {
|
||||
cx.consume();
|
||||
characters.push(escapeMap[esc]);
|
||||
} else if (cx.allowSingleQuote && esc == "'") {
|
||||
cx.consume();
|
||||
characters.push("'");
|
||||
} else {
|
||||
if (cx.allowEscapeAny) {
|
||||
characters.push(ch);
|
||||
} else {
|
||||
cx.reportError("Illegal string escape \\" + esc);
|
||||
}
|
||||
}
|
||||
} else if (ch.charCodeAt(0) >= 0x20) {
|
||||
cx.consume();
|
||||
characters.push(ch);
|
||||
} else {
|
||||
cx.reportError("Illegal string character " + ch);
|
||||
}
|
||||
}
|
||||
return characters.join("");
|
||||
},
|
||||
NumberRegExp: /-?(?:0|[1-9]\d*)(?:\.\d+)?(?:[eE][+-]?\d+)?/,
|
||||
scanNumber(cx) {
|
||||
const numberRegExp = cx.numberRegExp || this.NumberRegExp;
|
||||
const match = cx.rest().match(numberRegExp);
|
||||
if (match) {
|
||||
cx.consume(match[0].length);
|
||||
return Number(match[0]);
|
||||
} else {
|
||||
cx.reportError("Illegal number format");
|
||||
}
|
||||
},
|
||||
Whitespaces: " \t\r\n",
|
||||
skipWhitespace(cx) {
|
||||
const whitespaces = cx.whitespaces || this.Whitespaces;
|
||||
let ch, ch2;
|
||||
while (!cx.eof()) {
|
||||
ch2 = cx.peek(2);
|
||||
if (cx.allowComments) {
|
||||
let commentContent = [];
|
||||
if (ch2 == "//") {
|
||||
cx.token("lineComment", () => {
|
||||
cx.consume(2);
|
||||
for (;;) {
|
||||
if (cx.eof()) break;
|
||||
ch = cx.peek();
|
||||
if (ch == "\r" || ch == "\n") break;
|
||||
commentContent.push(ch);
|
||||
cx.consume(1);
|
||||
}
|
||||
return commentContent.join("");
|
||||
});
|
||||
continue;
|
||||
}
|
||||
if (ch2 == "/*") {
|
||||
cx.token("blockComment", () => {
|
||||
cx.consume(2);
|
||||
for (;;) {
|
||||
if (cx.eof()) break;
|
||||
ch2 = cx.peek(2);
|
||||
if (ch2 == "*/") {
|
||||
cx.consume(2);
|
||||
break;
|
||||
};
|
||||
commentContent.push(ch2.charAt(0));
|
||||
cx.consume(1);
|
||||
}
|
||||
return commentContent.join("");
|
||||
});
|
||||
continue;
|
||||
}
|
||||
}
|
||||
ch = ch2.charAt(0);
|
||||
if (whitespaces.indexOf(ch) >= 0) {
|
||||
cx.consume();
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
});
|
Loading…
Reference in New Issue
Block a user