From 58f7e36c3bfab689ef093c1647591c04e279ff09 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Thu, 28 Dec 2017 11:50:25 +0800 Subject: [PATCH 001/102] Update main.js MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 可以选择不监听事件,给GUI调用提供可能性 --- index.html | 1 + main.js | 9 +++++++-- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/index.html b/index.html index 44c759a0..fa25ac90 100644 --- a/index.html +++ b/index.html @@ -113,5 +113,6 @@ 此浏览器不支持HTML5 + \ No newline at end of file diff --git a/main.js b/main.js index fe644e79..b9891a99 100644 --- a/main.js +++ b/main.js @@ -195,8 +195,9 @@ main.prototype.setMainTipsText = function (text) { main.dom.mainTips.innerHTML = text; } -var main = new main(); -main.init(); + + +main.prototype.listen = function () { window.onresize = function () { try { @@ -366,3 +367,7 @@ main.dom.normalLevel.onclick = function () { main.dom.hardLevel.onclick = function () { core.events.startGame('Hard'); } + +}//listen end + +var main = new main(); \ No newline at end of file From 8873991004740c3fe9e9adc47dbecfa5fa116cc0 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Thu, 28 Dec 2017 16:19:38 +0800 Subject: [PATCH 002/102] =?UTF-8?q?=E6=95=B0=E6=8D=AEjson=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- drawMapGUI.html | 3 +- libs/data.js | 166 +------------------------------ libs/enemys.js | 64 +----------- libs/floors/data.js | 175 +++++++++++++++++++++++++++++++++ libs/floors/enemys.js | 63 ++++++++++++ libs/floors/icons.js | 215 ++++++++++++++++++++++++++++++++++++++++ libs/floors/items.js | 113 +++++++++++++++++++++ libs/floors/maps.js | 194 ++++++++++++++++++++++++++++++++++++ libs/floors/sample0.js | 2 +- libs/floors/sample1.js | 4 +- libs/icons.js | 216 +---------------------------------------- libs/items.js | 111 ++------------------- libs/maps.js | 197 +------------------------------------ main.js | 54 +++++++---- 14 files changed, 817 insertions(+), 760 deletions(-) create mode 100644 libs/floors/data.js create mode 100644 libs/floors/enemys.js create mode 100644 libs/floors/icons.js create mode 100644 libs/floors/items.js create mode 100644 libs/floors/maps.js diff --git a/drawMapGUI.html b/drawMapGUI.html index 663d824e..7b2fcad2 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -420,7 +420,7 @@ editor.prototype.init = function() { editor.prototype.loadMod = function (callback) { main={'instance':{}}; var loadedNum=0; - ['libs/icons.js','libs/maps.js'].forEach( function (value,ii,aa) { + ['libs/floors/icons.js','libs/floors/maps.js','libs/icons.js','libs/maps.js'].forEach( function (value,ii,aa) { var script = document.createElement('script'); script.src = value + '?' + editor.version; document.body.appendChild(script); @@ -435,6 +435,7 @@ editor.prototype.loadMod = function (callback) { editor.prototype.afterLoadMod = function (callback) { main.instance.icons.init(); + main.instance.maps.init(); var icons=main.instance.icons.getIcons(); editor.ids = []; diff --git a/libs/data.js b/libs/data.js index d8ad6961..1e68480b 100644 --- a/libs/data.js +++ b/libs/data.js @@ -3,168 +3,10 @@ function data() { } data.prototype.init = function() { - this.firstData = { - "title": "魔塔样板", // 游戏名,将显示在标题页面以及切换楼层的界面中 - "name": "template", // 游戏的唯一英文标识符。由英文、数字、下划线组成,不能超过20个字符。 - "version": "Ver 1.0.0 (Beta)", // 当前游戏版本;版本不一致的存档不能通用。 - "floorId": "sample0", // 初始楼层ID - "hero": { // 勇士初始数据 - "name": "阳光", // 勇士名;可以改成喜欢的 - 'lv': 1, // 初始等级,该项必须为正整数 - "hp": 1000, // 初始生命值 - "atk": 100, // 初始攻击 - "def": 100, // 初始防御 - "mdef": 100, // 初始魔防 - "money": 100, // 初始金币 - "experience": 0, // 初始经验 - "items": { // 初始道具个数 - "keys": { - "yellowKey": 0, - "blueKey": 0, - "redKey": 0 - }, - "constants": {}, - "tools": {} - }, - "flyRange": [], // 初始可飞的楼层;一般留空数组即可 - "loc": {"direction": "up", "x": 6, "y": 10}, // 勇士初始位置 - "flags": { // 游戏过程中的变量或flags - "poison": false, // 毒 - "weak": false, // 衰 - "curse": false, // 咒 - } - }, - "startText": [ // 游戏开始前剧情。如果无剧情直接留一个空数组即可。 - "Hi,欢迎来到 HTML5 魔塔样板!\n\n本样板由艾之葵制作,可以让你在不会写任何代码\n的情况下也能做出属于自己的H5魔塔!", - "这里游戏开始时的剧情。\n定义在data.js的startText处。\n\n你可以在这里写上自己的内容。", - "赶快来试一试吧!" - ], - "shops": { // 定义全局商店(即快捷商店) - "moneyShop1": { // 商店唯一ID - "name": "贪婪之神", // 商店名称(标题) - "icon": "blueShop", // 商店图标,blueShop为蓝色商店,pinkShop为粉色商店 - "textInList": "1F金币商店", // 在快捷商店栏中显示的名称 - "use": "money", // 商店所要使用的。只能是"money"或"experience"。 - "need": "20+10*times*(times+1)", // 商店需要的金币/经验数值;可以是一个表达式,以times作为参数计算。 - // 这里用到的times为该商店的已经的访问次数。首次访问该商店时times的值为0。 - // 上面的例子是50层商店的计算公式。你也可以写任意其他的计算公式,只要以times作为参数即可。 - // 例如: "need": "25" 就是恒定需要25金币的商店; "need": "20+2*times" 就是第一次访问要20金币,以后每次递增2金币的商店。 - // 如果是对于每个选项有不同的计算公式,写 "need": "-1" 即可。可参见下面的经验商店。 - "text": "勇敢的武士啊,给我${need}金币就可以:", // 显示的文字,需手动加换行符。可以使用${need}表示上面的need值。 - "choices": [ // 商店的选项 - {"text": "生命+800", "effect": "status:hp+=800"}, - // 如果有多个effect以分号分开,参见下面的经验商店 - {"text": "攻击+4", "effect": "status:atk+=4"}, - {"text": "防御+4", "effect": "status:def+=4"}, - {"text": "魔防+10", "effect": "status:mdef+=10"} - // effect只能对status和item进行操作,不能修改flag值。 - // 必须是X+=Y的形式,其中Y可以是一个表达式,以status:xxx或item:xxx为参数 - // 其他effect样例: - // "item:yellowKey+=1" 黄钥匙+1 - // "item:pickaxe+=3" 破墙镐+3 - // "status:hp+=2*(status:atk+status:def)" 将生命提升攻防和的数值的两倍 - ] - }, - "expShop1": { // 商店唯一ID - "name": "经验之神", - "icon": "pinkShop", - "textInList": "1F经验商店", - "use": "experience", // 该商店使用的是经验进行计算 - "need": "-1", // 如果是对于每个选项所需要的数值不同,这里直接写-1,然后下面选项里给定具体数值 - "text": "勇敢的武士啊,给我若干经验就可以:", - "choices": [ - // 在choices中写need,可以针对每个选项都有不同的需求。 - // 这里的need同样可以以times作为参数,比如 "need": "100+20*times" - {"text": "等级+1", "need": "100", "effect": "status:lv+=1;status:hp+=1000;status:atk+=7;status:def+=7"}, - // 多个effect直接以分号分开即可。如上面的意思是生命+1000,攻击+7,防御+7。 - {"text": "攻击+5", "need": "30", "effect": "status:atk+=5"}, - {"text": "防御+5", "need": "30", "effect": "status:def+=5"}, - ] - }, - }, - "levelUp": [ // 经验升级所需要的数值,是一个数组 - {}, // 第一项为初始等级,可以简单留空,也可以写name - - // 每一个里面可以含有三个参数 name, need, effect - // need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 - // name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 - // effect为本次升级所执行的操作,可由若干项组成,由分号分开 - // 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 - {"need": 20, "name": "第二级", "effect": "status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10"}, // 先将生命提升攻防和的2倍;再将攻击+10,防御+10 - - // effect也允许写一个function,代表本次升级将会执行的操作 - {"need": 40, "effect": function () { - core.drawText("恭喜升级!"); - core.status.hero.hp *= 2; - core.status.hero.atk += 100; - core.status.hero.def += 100; - }}, - - // 依次往下写需要的数值即可 - ] - } - // 各种数值;一些数值可以在这里设置 - this.values = { - /****** 角色相关 ******/ - "HPMAX": 999999, // HP上限;-1则无上限 - "lavaDamage": 100, // 经过血网受到的伤害 - "poisonDamage": 10, // 中毒后每步受到的伤害 - "weakValue": 20, // 衰弱状态下攻防减少的数值 - /****** 道具相关 ******/ - "redJewel": 3, // 红宝石加攻击的数值 - "blueJewel": 3, // 蓝宝石加防御的数值 - "greenJewel": 5, // 绿宝石加魔防的数值 - "redPotion": 100, // 红血瓶加血数值 - "bluePotion": 250, // 蓝血瓶加血数值 - "yellowPotion": 500, // 黄血瓶加血数值 - "greenPotion": 800, // 绿血瓶加血数值 - "sword1": 10, // 铁剑加攻数值 - "shield1": 10, // 铁盾加防数值 - "sword2": 20, // 银剑加攻数值 - "shield2": 20, // 银盾加防数值 - "sword3": 40, // 骑士剑加攻数值 - "shield3": 40, // 骑士盾加防数值 - "sword4": 80, // 圣剑加攻数值 - "shield4": 80, // 圣盾加防数值 - "sword5": 160, // 神圣剑加攻数值 - "shield5": 160, // 神圣盾加防数值 - "moneyPocket": 500, // 金钱袋加金币的数值 - /****** 怪物相关 ******/ - 'breakArmor': 0.9, // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) - 'counterAttack': 0.1, // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) - 'purify': 3, // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) - 'hatred': 2, // 仇恨属性中,每杀死一个怪物获得的仇恨值 - /****** 系统相关 ******/ - 'animateSpeed': 500, // 动画时间 - } - // 系统FLAG,在游戏运行中中请不要修改它。 - this.flags = { - /****** 角色状态相关 ******/ - "enableNegativeDamage": true, // 是否支持负伤害(回血) - "enableFloor": false, // 是否在状态栏显示当前楼层 - "enableLv": true, // 是否在状态栏显示当前等级 - "enableMDef": true, // 是否在状态栏及战斗界面显示魔防(护盾) - "enableMoney": true, // 是否在状态栏、怪物手册及战斗界面显示金币 - "enableExperience": true, // 是否在状态栏、怪物手册及战斗界面显示经验 - "enableLevelUp": false, // 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false - "enableDebuff": true, // 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff - ////// 上述的几个开关将直接影响状态栏的显示效果 ////// - /****** 道具相关 ******/ - "flyNearStair": true, // 是否需要在楼梯边使用传送器 - "pickaxeFourDirections": true, // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 - "bombFourDirections": true, // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) - "bigKeyIsBox": false, // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 - /****** 系统相关 ******/ - "startDirectly": false, // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 - "canOpenBattleAnimate": true, // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false - "showBattleAnimateConfirm": true, // 是否在游戏开始时提供“是否开启战斗动画”的选项 - "battleAnimate": true, // 是否默认显示战斗动画;用户可以手动在菜单栏中开关 - "displayEnemyDamage": true, // 是否地图怪物显伤;用户可以手动在菜单栏中开关 - "displayExtraDamage": false, // 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 - "enableGentleClick": true, // 是否允许轻触(获得面前物品) - "portalWithoutTrigger": true, // 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 - "potionWhileRouting": false, // 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 - } + this.firstData = data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d.firstData; + this.values = data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d.values; + this.flags = data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d.flags; + delete(data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d); } data.prototype.getFirstData = function() { diff --git a/libs/enemys.js b/libs/enemys.js index f236d68d..56b4de1c 100644 --- a/libs/enemys.js +++ b/libs/enemys.js @@ -4,68 +4,8 @@ function enemys() { enemys.prototype.init = function () { // 怪物属性初始化定义: - this.enemys = { - 'greenSlime': {'name': '绿头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 1, 'experience': 1, 'special': 0}, - 'redSlime': {'name': '红头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'blackSlime': {'name': '青头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'slimelord': {'name': '怪王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'special': 9}, - 'bat': {'name': '小蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 2, 'experience': 0, 'special': 1}, - 'bigBat': {'name': '大蝙蝠', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redBat': {'name': '红蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 5, 'experience': 0, 'special': 4}, - 'vampire': {'name': '冥灵魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeleton': {'name': '骷髅人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonSoilder': {'name': '骷髅士兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonCaptain': {'name': '骷髅队长', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'ghostSkeleton': {'name': '冥队长', 'hp': 100, 'atk': 120, 'def': 0, 'money': 8, 'experience': 0, 'special': 7}, - 'zombie': {'name': '兽人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'zombieKnight': {'name': '兽人武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'rock': {'name': '石头人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 4, 'experience': 0, 'special': 3}, - 'slimeMan': {'name': '影子战士', 'hp': 100, 'atk': 0, 'def': 0, 'money': 11, 'experience': 0, 'special': 10}, // 模仿怪的攻防设为0就好 - 'bluePriest': {'name': '初级法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 3, 'experience': 0, 'special': 2}, - 'redPriest': {'name': '高级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'brownWizard': {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100}, // 领域怪需要加value表示领域伤害的数值 - 'redWizard': {'name': '高级巫师', 'hp': 1000, 'atk': 1200, 'def': 0, 'money': 160, 'experience': 0, 'special': 15, 'value': 200}, - 'yellowGuard': {'name': '初级卫兵', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'special': 0}, - 'blueGuard': {'name': '中级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redGuard': {'name': '高级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'swordsman': {'name': '双手剑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 6, 'experience': 0, 'special': 5}, - 'soldier': {'name': '冥战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'yellowKnight': {'name': '金骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redKnight': {'name': '红骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'darkKnight': {'name': '黑骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'blackKing': {'name': '黑衣魔王', 'hp': 1000, 'atk': 500, 'def': 0, 'money': 1000, 'experience': 1000, 'special': 0, 'bomb': false}, // 加入 'bomb': false 代表该怪物不可被炸弹或圣锤炸掉 - 'yellowKing': {'name': '黄衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'greenKing': {'name': '青衣武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'blueKnight': {'name': '蓝骑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 9, 'experience': 0, 'special': 8}, - 'goldSlime': {'name': '黄头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'poisonSkeleton': {'name': '紫骷髅', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'poisonBat': {'name': '紫蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 14, 'experience': 0, 'special': 13}, - 'steelRock': {'name': '铁面人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonPriest': {'name': '骷髅法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonKing': {'name': '骷髅王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonWizard': {'name': '骷髅巫师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redSkeletonCaption': {'name': '骷髅武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'special': 0}, - 'badHero': {'name': '迷失勇者', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'demon': {'name': '魔神武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'demonPriest': {'name': '魔神法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'goldHornSlime': {'name': '金角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redKing': {'name': '红衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'whiteKing': {'name': '白衣武士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 17, 'experience': 0, 'special': 16}, - 'blackMagician': {'name': '黑暗大法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 12, 'experience': 0, 'special': 11, 'value': 1/3, 'bomb': false}, // 吸血怪需要在后面添加value代表吸血比例 - 'silverSlime': {'name': '银头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 15, 'experience': 0, 'special': 14}, - 'swordEmperor': {'name': '剑圣', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'whiteHornSlime': {'name': '尖角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'badPrincess': {'name': '痛苦魔女', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'badFairy': {'name': '黑暗仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'grayPriest': {'name': '中级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redSwordsman': {'name': '剑王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 7, 'experience': 0, 'special': 6}, - 'whiteGhost': {'name': '水银战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'poisonZombie': {'name': '绿兽人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 13, 'experience': 0, 'special': 12}, - 'magicDragon': {'name': '魔龙', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'octopus': {'name': '血影', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'darkFairy': {'name': '仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'greenKnight': {'name': '强盾骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - } + this.enemys = enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80; + delete(enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80); } enemys.prototype.getEnemys = function (enemyId) { diff --git a/libs/floors/data.js b/libs/floors/data.js new file mode 100644 index 00000000..5a943f27 --- /dev/null +++ b/libs/floors/data.js @@ -0,0 +1,175 @@ +data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = +{ + "main" : { + "useCompress" : false, // 是否使用压缩文件 + // 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 + // 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 + // 如果要进行剧本的修改请务必将其改成false。 + + "floorIds" : [ // 在这里按顺序放所有的楼层;其顺序直接影响到楼层传送器的顺序和上楼器/下楼器的顺序 + "sample0", "sample1", "sample2", "test" + ] + }, + "firstData" : { + "title": "魔塔样板", // 游戏名,将显示在标题页面以及切换楼层的界面中 + "name": "template", // 游戏的唯一英文标识符。由英文、数字、下划线组成,不能超过20个字符。 + "version": "Ver 1.0.0 (Beta)", // 当前游戏版本;版本不一致的存档不能通用。 + "floorId": "sample0", // 初始楼层ID + "hero": { // 勇士初始数据 + "name": "阳光", // 勇士名;可以改成喜欢的 + "lv": 1, // 初始等级,该项必须为正整数 + "hp": 2000, // 初始生命值 + "atk": 100, // 初始攻击 + "def": 100, // 初始防御 + "mdef": 100, // 初始魔防 + "money": 100, // 初始金币 + "experience": 0, // 初始经验 + "items": { // 初始道具个数 + "keys": { + "yellowKey": 0, + "blueKey": 0, + "redKey": 0 + }, + "constants": {}, + "tools": {} + }, + "flyRange": [], // 初始可飞的楼层;一般留空数组即可 + "loc": {"direction": "up", "x": 6, "y": 10}, // 勇士初始位置 + "flags": { // 游戏过程中的变量或flags + "poison": false, // 毒 + "weak": false, // 衰 + "curse": false, // 咒 + } + }, + "startText": [ // 游戏开始前剧情。如果无剧情直接留一个空数组即可。 + "Hi,欢迎来到 HTML5 魔塔样板!\n\n本样板由艾之葵制作,可以让你在不会写任何代码\n的情况下也能做出属于自己的H5魔塔!", + "这里游戏开始时的剧情。\n定义在data.js的startText处。\n\n你可以在这里写上自己的内容。", + "赶快来试一试吧!" + ], + "shops": { // 定义全局商店(即快捷商店) + "moneyShop1": { // 商店唯一ID + "name": "贪婪之神", // 商店名称(标题) + "icon": "blueShop", // 商店图标,blueShop为蓝色商店,pinkShop为粉色商店 + "textInList": "1F金币商店", // 在快捷商店栏中显示的名称 + "use": "money", // 商店所要使用的。只能是"money"或"experience"。 + "need": "20+10*times*(times+1)", // 商店需要的金币/经验数值;可以是一个表达式,以times作为参数计算。 + // 这里用到的times为该商店的已经的访问次数。首次访问该商店时times的值为0。 + // 上面的例子是50层商店的计算公式。你也可以写任意其他的计算公式,只要以times作为参数即可。 + // 例如: "need": "25" 就是恒定需要25金币的商店; "need": "20+2*times" 就是第一次访问要20金币,以后每次递增2金币的商店。 + // 如果是对于每个选项有不同的计算公式,写 "need": "-1" 即可。可参见下面的经验商店。 + "text": "勇敢的武士啊,给我${need}金币就可以:", // 显示的文字,需手动加换行符。可以使用${need}表示上面的need值。 + "choices": [ // 商店的选项 + {"text": "生命+800", "effect": "status:hp+=800"}, + // 如果有多个effect以分号分开,参见下面的经验商店 + {"text": "攻击+4", "effect": "status:atk+=4"}, + {"text": "防御+4", "effect": "status:def+=4"}, + {"text": "魔防+10", "effect": "status:mdef+=10"} + // effect只能对status和item进行操作,不能修改flag值。 + // 必须是X+=Y的形式,其中Y可以是一个表达式,以status:xxx或item:xxx为参数 + // 其他effect样例: + // "item:yellowKey+=1" 黄钥匙+1 + // "item:pickaxe+=3" 破墙镐+3 + // "status:hp+=2*(status:atk+status:def)" 将生命提升攻防和的数值的两倍 + ] + }, + "expShop1": { // 商店唯一ID + "name": "经验之神", + "icon": "pinkShop", + "textInList": "1F经验商店", + "use": "experience", // 该商店使用的是经验进行计算 + "need": "-1", // 如果是对于每个选项所需要的数值不同,这里直接写-1,然后下面选项里给定具体数值 + "text": "勇敢的武士啊,给我若干经验就可以:", + "choices": [ + // 在choices中写need,可以针对每个选项都有不同的需求。 + // 这里的need同样可以以times作为参数,比如 "need": "100+20*times" + {"text": "等级+1", "need": "100", "effect": "status:lv+=1;status:hp+=1000;status:atk+=7;status:def+=7"}, + // 多个effect直接以分号分开即可。如上面的意思是生命+1000,攻击+7,防御+7。 + {"text": "攻击+5", "need": "30", "effect": "status:atk+=5"}, + {"text": "防御+5", "need": "30", "effect": "status:def+=5"}, + ] + }, + }, + "levelUp": [ // 经验升级所需要的数值,是一个数组 + {}, // 第一项为初始等级,可以简单留空,也可以写name + + // 每一个里面可以含有三个参数 name, need, effect + // need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 + // name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 + // effect为本次升级所执行的操作,可由若干项组成,由分号分开 + // 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 + {"need": 20, "name": "第二级", "effect": "status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10"}, // 先将生命提升攻防和的2倍;再将攻击+10,防御+10 + + // effect也允许写一个function,代表本次升级将会执行的操作 + {"need": 40, "effect": function () { + core.drawText("恭喜升级!"); + core.status.hero.hp *= 2; + core.status.hero.atk += 100; + core.status.hero.def += 100; + }}, + + // 依次往下写需要的数值即可 + ] + }, + // 各种数值;一些数值可以在这里设置 + "values" : { + /****** 角色相关 ******/ + "HPMAX": 999999, // HP上限;-1则无上限 + "lavaDamage": 100, // 经过血网受到的伤害 + "poisonDamage": 10, // 中毒后每步受到的伤害 + "weakValue": 20, // 衰弱状态下攻防减少的数值 + /****** 道具相关 ******/ + "redJewel": 3, // 红宝石加攻击的数值 + "blueJewel": 3, // 蓝宝石加防御的数值 + "greenJewel": 5, // 绿宝石加魔防的数值 + "redPotion": 100, // 红血瓶加血数值 + "bluePotion": 250, // 蓝血瓶加血数值 + "yellowPotion": 500, // 黄血瓶加血数值 + "greenPotion": 800, // 绿血瓶加血数值 + "sword1": 10, // 铁剑加攻数值 + "shield1": 10, // 铁盾加防数值 + "sword2": 20, // 银剑加攻数值 + "shield2": 20, // 银盾加防数值 + "sword3": 40, // 骑士剑加攻数值 + "shield3": 40, // 骑士盾加防数值 + "sword4": 80, // 圣剑加攻数值 + "shield4": 80, // 圣盾加防数值 + "sword5": 160, // 神圣剑加攻数值 + "shield5": 160, // 神圣盾加防数值 + "moneyPocket": 500, // 金钱袋加金币的数值 + /****** 怪物相关 ******/ + "breakArmor": 0.9, // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) + "counterAttack": 0.1, // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) + "purify": 3, // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) + "hatred": 2, // 仇恨属性中,每杀死一个怪物获得的仇恨值 + /****** 系统相关 ******/ + "animateSpeed": 500, // 动画时间 + }, + // 系统FLAG,在游戏运行中中请不要修改它。 + "flags" : { + /****** 角色状态相关 ******/ + "enableNegativeDamage": true, // 是否支持负伤害(回血) + "enableFloor": false, // 是否在状态栏显示当前楼层 + "enableLv": true, // 是否在状态栏显示当前等级 + "enableMDef": true, // 是否在状态栏及战斗界面显示魔防(护盾) + "enableMoney": true, // 是否在状态栏、怪物手册及战斗界面显示金币 + "enableExperience": true, // 是否在状态栏、怪物手册及战斗界面显示经验 + "enableLevelUp": false, // 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false + "enableDebuff": true, // 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff + ////// 上述的几个开关将直接影响状态栏的显示效果 ////// + /****** 道具相关 ******/ + "flyNearStair": true, // 是否需要在楼梯边使用传送器 + "pickaxeFourDirections": true, // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 + "bombFourDirections": true, // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) + "bigKeyIsBox": false, // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 + /****** 系统相关 ******/ + "startDirectly": false, // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 + "canOpenBattleAnimate": true, // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false + "showBattleAnimateConfirm": true, // 是否在游戏开始时提供“是否开启战斗动画”的选项 + "battleAnimate": true, // 是否默认显示战斗动画;用户可以手动在菜单栏中开关 + "displayEnemyDamage": true, // 是否地图怪物显伤;用户可以手动在菜单栏中开关 + "displayExtraDamage": false, // 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 + "enableGentleClick": true, // 是否允许轻触(获得面前物品) + "portalWithoutTrigger": true, // 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 + "potionWhileRouting": false, // 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 + } +} \ No newline at end of file diff --git a/libs/floors/enemys.js b/libs/floors/enemys.js new file mode 100644 index 00000000..7952ffd1 --- /dev/null +++ b/libs/floors/enemys.js @@ -0,0 +1,63 @@ +enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80 = //1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:4连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨 +{ + "greenSlime": {"name": "绿头怪", "hp": 100, "atk": 120, "def": 0, "money": 1, "experience": 1, "special": 0}, + "redSlime": {"name": "红头怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "blackSlime": {"name": "青头怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "slimelord": {"name": "怪王", "hp": 100, "atk": 120, "def": 0, "money": 10, "experience": 0, "special": 9}, + "bat": {"name": "小蝙蝠", "hp": 100, "atk": 120, "def": 0, "money": 2, "experience": 0, "special": 1}, + "bigBat": {"name": "大蝙蝠", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "redBat": {"name": "红蝙蝠", "hp": 100, "atk": 120, "def": 0, "money": 5, "experience": 0, "special": 4}, + "vampire": {"name": "冥灵魔王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "skeleton": {"name": "骷髅人", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "skeletonSoilder": {"name": "骷髅士兵", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "skeletonCaptain": {"name": "骷髅队长", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "ghostSkeleton": {"name": "冥队长", "hp": 100, "atk": 120, "def": 0, "money": 8, "experience": 0, "special": 7}, + "zombie": {"name": "兽人", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "zombieKnight": {"name": "兽人武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "rock": {"name": "石头人", "hp": 100, "atk": 120, "def": 0, "money": 4, "experience": 0, "special": 3}, + "slimeMan": {"name": "影子战士", "hp": 100, "atk": 0, "def": 0, "money": 11, "experience": 0, "special": 10}, // 模仿怪的攻防设为0就好 + "bluePriest": {"name": "初级法师", "hp": 100, "atk": 120, "def": 0, "money": 3, "experience": 0, "special": 2}, + "redPriest": {"name": "高级法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "brownWizard": {"name": "初级巫师", "hp": 100, "atk": 120, "def": 0, "money": 16, "experience": 0, "special": 15, "value": 100}, // 领域怪需要加value表示领域伤害的数值 + "redWizard": {"name": "高级巫师", "hp": 1000, "atk": 1200, "def": 0, "money": 160, "experience": 0, "special": 15, "value": 200}, + "yellowGuard": {"name": "初级卫兵", "hp": 100, "atk": 120, "def": 0, "money": 10, "experience": 0, "special": 0}, + "blueGuard": {"name": "中级卫兵", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "redGuard": {"name": "高级卫兵", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "swordsman": {"name": "双手剑士", "hp": 100, "atk": 120, "def": 0, "money": 6, "experience": 0, "special": 5}, + "soldier": {"name": "冥战士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "yellowKnight": {"name": "金骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "redKnight": {"name": "红骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "darkKnight": {"name": "黑骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "blackKing": {"name": "黑衣魔王", "hp": 1000, "atk": 500, "def": 0, "money": 1000, "experience": 1000, "special": 0, "bomb": false}, // 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉 + "yellowKing": {"name": "黄衣魔王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "greenKing": {"name": "青衣武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "blueKnight": {"name": "蓝骑士", "hp": 100, "atk": 120, "def": 0, "money": 9, "experience": 0, "special": 8}, + "goldSlime": {"name": "黄头怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "poisonSkeleton": {"name": "紫骷髅", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "poisonBat": {"name": "紫蝙蝠", "hp": 100, "atk": 120, "def": 0, "money": 14, "experience": 0, "special": 13}, + "steelRock": {"name": "铁面人", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "skeletonPriest": {"name": "骷髅法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "skeletonKing": {"name": "骷髅王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "skeletonWizard": {"name": "骷髅巫师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "redSkeletonCaption": {"name": "骷髅武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "special": 0}, + "badHero": {"name": "迷失勇者", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "demon": {"name": "魔神武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "demonPriest": {"name": "魔神法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "goldHornSlime": {"name": "金角怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "redKing": {"name": "红衣魔王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "whiteKing": {"name": "白衣武士", "hp": 100, "atk": 120, "def": 0, "money": 17, "experience": 0, "special": 16}, + "blackMagician": {"name": "黑暗大法师", "hp": 100, "atk": 120, "def": 0, "money": 12, "experience": 0, "special": 11, "value": 1/3, "bomb": false}, // 吸血怪需要在后面添加value代表吸血比例 + "silverSlime": {"name": "银头怪", "hp": 100, "atk": 120, "def": 0, "money": 15, "experience": 0, "special": 14}, + "swordEmperor": {"name": "剑圣", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "whiteHornSlime": {"name": "尖角怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "badPrincess": {"name": "痛苦魔女", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "badFairy": {"name": "黑暗仙子", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "grayPriest": {"name": "中级法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "redSwordsman": {"name": "剑王", "hp": 100, "atk": 120, "def": 0, "money": 7, "experience": 0, "special": 6}, + "whiteGhost": {"name": "水银战士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "poisonZombie": {"name": "绿兽人", "hp": 100, "atk": 120, "def": 0, "money": 13, "experience": 0, "special": 12}, + "magicDragon": {"name": "魔龙", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "octopus": {"name": "血影", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "darkFairy": {"name": "仙子", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + "greenKnight": {"name": "强盾骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, +} \ No newline at end of file diff --git a/libs/floors/icons.js b/libs/floors/icons.js new file mode 100644 index 00000000..f9a0e1b1 --- /dev/null +++ b/libs/floors/icons.js @@ -0,0 +1,215 @@ +icons_4665ee12_3a1f_44a4_bea3_0fccba634dc1 = +{ + "hero": { + "down": {"loc": 0, "stop": 0, "leftFoot": 1, "rightFoot": 3}, + "left": {"loc": 1, "stop": 0, "leftFoot": 1, "rightFoot": 3}, + "right": {"loc": 2, "stop": 0, "leftFoot": 1, "rightFoot": 3}, + "up": {"loc": 3, "stop": 0, "leftFoot": 1, "rightFoot": 3} + }, + "terrains": { + "ground": 0, + "grass": 1, + "grass2": 2, + "snowGround": 3, + "ground2": 4, + "ground3": 5, + "ground4": 6, + "sand": 7, + "ground5": 8, + "yellowWall2": 9, + "whiteWall2": 10, + "blueWall2": 11, + "blockWall": 12, + "grayWall": 13, + "white": 14, + "ground6": 15, + "soil": 16, + "yellowWall": 17, + "whiteWall": 18, + "blueWall": 19, + "star": 20, + "lava": 21, + "ice": 22, + "downFloor": 23, + "upFloor": 24, + "yellowDoor": 25, + "blueDoor": 26, + "redDoor": 27, + "greenDoor": 28, + "specialDoor": 29, + "steelDoor": 30, + "blueShop-left": 31, + "blueShop-right": 32, + "pinkShop-left": 33, + "pinkShop-right": 34, + "arrowUp": 35, + "arrowDown": 36, + "arrowLeft": 37, + "arrowRight": 38, + "light": 39, + "darkLight": 40 + }, + "animates": { + "star": 0, + "lava": 1, + "waterWall": 2, + "yellowDoor": 3, + "blueDoor": 4, + "redDoor": 5, + "greenDoor": 6, + "specialDoor": 7, + "blueWallDoor": 8, + "yellowWallDoor": 9, + "whiteWallDoor": 10, + "steelDoor": 11, + "lavaDoor": 12, + "grayLavaDoor": 13, + "starDoor": 14, + "mockBlueWallDoor": 15, + "mockYellowWallDoor": 16, + "mockWhiteWallDoor": 17, + "iceYellowWallDoor": 18, + "starPortal": 19, + "exclamation": 20, + "portal": 21, + "switch": 22, + "lavaNet": 23, + "poisonNet": 24, + "weakNet": 25, + "curseNet": 26, + "downPortal": 27, + "leftPortal": 28, + "rightPortal": 29, + "upPortal": 30, + "water": 31, + }, + "npcs": { + "man": 0, + "woman": 1, + "thief": 2, + "fairy": 3, + "magician": 4, + "womanMagician": 5, + "oldMan": 6, + "child": 7, + "wood": 8, + "pinkShop": 9, + "blueShop": 10, + "princess": 11 + }, + "enemys": { + "greenSlime": 0, + "redSlime": 1, + "blackSlime": 2, + "slimelord": 3, + "bat": 4, + "bigBat": 5, + "redBat": 6, + "vampire": 7, + "skeleton": 8, + "skeletonSoilder": 9, + "skeletonCaptain": 10, + "ghostSkeleton": 11, + "zombie": 12, + "zombieKnight": 13, + "rock": 14, + "slimeMan": 15, + "bluePriest": 16, + "redPriest": 17, + "brownWizard": 18, + "redWizard": 19, + "yellowGuard": 20, + "blueGuard": 21, + "redGuard": 22, + "swordsman": 23, + "soldier": 24, + "yellowKnight": 25, + "redKnight": 26, + "darkKnight": 27, + "blackKing": 28, + "yellowKing": 29, + "greenKing": 30, + "blueKnight": 31, + "goldSlime": 32, + "poisonSkeleton": 33, + "poisonBat": 34, + "steelRock": 35, + "skeletonPriest": 36, + "skeletonKing": 37, + "skeletonWizard": 38, + "redSkeletonCaption": 39, + "badHero": 40, + "demon": 41, + "demonPriest": 42, + "goldHornSlime": 43, + "redKing": 44, + "whiteKing": 45, + "blackMagician": 46, + "silverSlime": 47, + "swordEmperor": 48, + "whiteHornSlime": 49, + "badPrincess": 50, + "badFairy": 51, + "grayPriest": 52, + "redSwordsman": 53, + "whiteGhost": 54, + "poisonZombie": 55, + "magicDragon": 56, + "octopus": 57, + "darkFairy": 58, + "greenKnight": 59, + }, + "items": { + "yellowKey": 0, + "blueKey": 1, + "redKey": 2, + "greenKey": 3, + "steelKey": 4, + "bigKey": 6, + "redJewel": 16, + "blueJewel": 17, + "greenJewel": 18, + "yellowJewel": 19, + "redPotion": 20, + "bluePotion": 21, + "greenPotion": 22, + "yellowPotion": 23, + "sword1": 50, + "sword2": 51, + "sword3": 52, + "sword4": 53, + "sword5": 54, + "shield1": 55, + "shield2": 56, + "shield3": 57, + "shield4": 58, + "shield5": 59, + "book": 9, + "fly": 12, + "pickaxe": 45, + "icePickaxe": 44, + "bomb": 43, + "centerFly": 13, + "upFly": 15, + "downFly": 14, + "coin": 11, + "snow": 41, + "cross": 40, + "superPotion": 29, + "earthquake": 8, + "poisonWine": 24, + "weakWine": 25, + "curseWine": 27, + "superWine": 28, + "knife": 42, + "moneyPocket": 46, + "shoes": 47, + "hammer": 48 + }, + "autotile": { // 所有的Autotile列表;后面的index简单取0即可 + "autotile": 0, + "autotile1": 0, + "autotile2": 0, + "autotile3": 0, + } +} \ No newline at end of file diff --git a/libs/floors/items.js b/libs/floors/items.js new file mode 100644 index 00000000..a181532d --- /dev/null +++ b/libs/floors/items.js @@ -0,0 +1,113 @@ +items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a = +{ + +"items" : { + // 钥匙 + 'yellowKey': {'cls': 'keys', 'name': '黄钥匙'}, + 'blueKey': {'cls': 'keys', 'name': '蓝钥匙'}, + 'redKey': {'cls': 'keys', 'name': '红钥匙'}, + + // 宝石、血瓶 + 'redJewel': {'cls': 'items', 'name': '红宝石'}, + 'blueJewel': {'cls': 'items', 'name': '蓝宝石'}, + 'greenJewel': {'cls': 'items', 'name': '绿宝石'}, + 'yellowJewel': {'cls': 'items', 'name': '黄宝石'}, + 'redPotion': {'cls': 'items', 'name': '红血瓶'}, + 'bluePotion': {'cls': 'items', 'name': '蓝血瓶'}, + 'yellowPotion': {'cls': 'items', 'name': '黄血瓶'}, + 'greenPotion': {'cls': 'items', 'name': '绿血瓶'}, + 'sword1': {'cls': 'items', 'name': '铁剑'}, + 'sword2': {'cls': 'items', 'name': '银剑'}, + 'sword3': {'cls': 'items', 'name': '骑士剑'}, + 'sword4': {'cls': 'items', 'name': '圣剑'}, + 'sword5': {'cls': 'items', 'name': '神圣剑'}, + 'shield1': {'cls': 'items', 'name': '铁盾'}, + 'shield2': {'cls': 'items', 'name': '银盾'}, + 'shield3': {'cls': 'items', 'name': '骑士盾'}, + 'shield4': {'cls': 'items', 'name': '圣盾'}, + 'shield5': {'cls': 'items', 'name': '神圣盾'}, + 'superPotion': {'cls': 'items', 'name': '圣水'}, + 'moneyPocket': {'cls': 'items', 'name': '金钱袋'}, + + // 物品 + 'book': {'cls': 'constants', 'name': '怪物手册', 'text': '可以查看当前楼层各怪物属性'}, + 'fly': {'cls': 'constants', 'name': '楼层传送器', 'text': '可以自由往来去过的楼层'}, + 'coin': {'cls': 'constants', 'name': '幸运金币', 'text': '持有时打败怪物可得双倍金币'}, + 'snow': {'cls': 'constants', 'name': '冰冻徽章', 'text': '可以将四周的熔岩变成平地'}, + 'cross': {'cls': 'constants', 'name': '十字架', 'text': '该道具尚未被定义'}, + 'knife': {'cls': 'constants', 'name': '屠龙匕首', 'text': '该道具尚未被定义'}, + 'shoes': {'cls': 'constants', 'name': '绿鞋', 'text': '持有时无视负面地形'}, + + // 道具 + 'bigKey': {'cls': 'tools', 'name': '大黄门钥匙', 'text': '可以开启当前层所有黄门'}, + 'greenKey': {'cls': 'tools', 'name': '绿钥匙', 'text': '可以打开一扇绿门'}, + 'steelKey': {'cls': 'tools', 'name': '铁门钥匙', 'text': '可以打开一扇铁门'}, + 'pickaxe': {'cls': 'tools', 'name': '破墙镐', 'text': '可以破坏勇士面前的墙'}, + 'icePickaxe': {'cls': 'tools', 'name': '破冰镐', 'text': '可以破坏勇士面前的一堵冰墙'}, + 'bomb': {'cls': 'tools', 'name': '炸弹', 'text': '可以炸掉勇士面前的怪物'}, + 'centerFly': {'cls': 'tools', 'name': '中心对称飞行器', 'text': '可以飞向当前楼层中心对称的位置'}, + 'upFly': {'cls': 'tools', 'name': '上楼器', 'text': '可以飞往楼上的相同位置'}, + 'downFly': {'cls': 'tools', 'name': '下楼器', 'text': '可以飞往楼下的相同位置'}, + 'earthquake': {'cls': 'tools', 'name': '地震卷轴', 'text': '可以破坏当前层的所有墙'}, + 'poisonWine': {'cls': 'tools', 'name': '解毒药水', 'text': '可以解除中毒状态'}, + 'weakWine': {'cls': 'tools', 'name': '解衰药水', 'text': '可以解除衰弱状态'}, + 'curseWine': {'cls': 'tools', 'name': '解咒药水', 'text': '可以解除诅咒状态'}, + 'superWine': {'cls': 'tools', 'name': '万能药水', 'text': '可以解除所有不良状态'}, + 'hammer': {'cls': 'tools', 'name': '圣锤', 'text': '可以炸掉勇士面前的怪物'} +}, + + + + +"itemEffect" : { + "redJewel":"core.status.hero.atk += core.values.redJewel", + "blueJewel":"core.status.hero.def += core.values.blueJewel", + "greenJewel":"core.status.hero.mdef += core.values.greenJewel", + // 黄宝石属性:需自己定义 + "yellowJewel":"core.status.hero.hp+=1000;core.status.hero.atk+=6;core.status.hero.def+=6;core.status.hero.mdef+=10;", + "redPotion":"core.status.hero.hp += core.values.redPotion", + "bluePotion":"core.status.hero.hp += core.values.bluePotion", + "yellowPotion":"core.status.hero.hp += core.values.yellowPotion", + "greenPotion":"core.status.hero.hp += core.values.greenPotion", + "sword1":"core.status.hero.atk += core.values.sword1", + "sword2":"core.status.hero.atk += core.values.sword2", + "sword3":"core.status.hero.atk += core.values.sword3", + "sword4":"core.status.hero.atk += core.values.sword4", + "sword5":"core.status.hero.atk += core.values.sword5", + "shield1":"core.status.hero.def += core.values.shield1", + "shield2":"core.status.hero.def += core.values.shield2", + "shield3":"core.status.hero.def += core.values.shield3", + "shield4":"core.status.hero.def += core.values.shield4", + "shield5":"core.status.hero.def += core.values.shield5", + // 只有是钥匙盒才会执行这一步 + "bigKey":"core.status.hero.items.keys.yellowKey++;core.status.hero.items.keys.blueKey++;core.status.hero.items.keys.redKey++;", + "superPotion":"core.status.hero.hp *= 2", + "moneyPocket":"core.status.hero.money += core.values.moneyPocket", +}, + + +"itemEffectTip" : { + "redJewel":"',攻击+'+core.values.redJewel", + "blueJewel":"',防御+'+core.values.blueJewel", + "greenJewel":"',魔防+'+core.values.greenJewel", + "yellowJewel":"',全属性提升'", + "redPotion":"',生命+'+core.values.redPotion", + "bluePotion":"',生命+'+core.values.bluePotion", + "yellowPotion":"',生命+'+core.values.yellowPotion", + "greenPotion":"',生命+'+core.values.greenPotion", + "sword1":"',攻击+'+core.values.sword1", + "sword2":"',攻击+'+core.values.sword2", + "sword3":"',攻击+'+core.values.sword3", + "sword4":"',攻击+'+core.values.sword4", + "sword5":"',攻击+'+core.values.sword5", + "shield1":"',防御+'+core.values.shield1", + "shield2":"',防御+'+core.values.shield2", + "shield3":"',防御+'+core.values.shield3", + "shield4":"',防御+'+core.values.shield4", + "shield5":"',防御+'+core.values.shield5", + "bigKey":"',全钥匙+1'", + "superPotion":"',生命值翻倍'", + "moneyPocket":"',金币+'+core.values.moneyPocket", +} + +} \ No newline at end of file diff --git a/libs/floors/maps.js b/libs/floors/maps.js new file mode 100644 index 00000000..30ef090a --- /dev/null +++ b/libs/floors/maps.js @@ -0,0 +1,194 @@ +maps_90f36752_8815_4be8_b32b_d7fad1d0542e = +{ + ////////////////////////// 地形部分 ////////////////////////// + + // 0-20 地形 + "1":{"cls": "terrains", "id": "yellowWall"}, // 黄墙 + "2":{"cls": "terrains", "id": "whiteWall"}, // 白墙 + "3":{"cls": "terrains", "id": "blueWall"}, // 白墙 + "4":{"cls": "animates", "id": "star", "noPass": true}, // 星空 + "5":{"cls": "animates", "id": "lava", "noPass": true}, // 岩浆 + "6":{"cls": "terrains", "id": "ice"}, // 岩浆 + "7":{"cls": "terrains", "id": "blueShop-left"}, // 蓝色商店左 + "8":{"cls": "terrains", "id": "blueShop-right"}, // 蓝色商店右 + "9":{"cls": "terrains", "id": "pinkShop-left"}, // 粉色商店左 + "10":{"cls": "terrains", "id": "pinkShop-right"}, // 粉色商店左 + "11":{"cls": "animates", "id": "lavaNet", "noPass": false, "trigger": "passNet"}, // 血网 + "12":{"cls": "animates", "id": "poisonNet", "noPass": false, "trigger": "passNet"}, // 毒网 + "13":{"cls": "animates", "id": "weakNet", "noPass": false, "trigger": "passNet"}, // 衰网 + "14":{"cls": "animates", "id": "curseNet", "noPass": false, "trigger": "passNet"}, // 咒网 + "15":{"cls": "animates", "id": "water", "noPass": true}, // 水 + // 在这里添加更多地形 + // 如果空地不足,可以从180以后开始继续放,只要不和现有的数字冲突即可 + + // Autotile + "20":{"cls": "autotile", "id": "autotile", "noPass": true}, // autotile + // 更多的autotile从151到160,只要不和现有的数字冲突即可 + "151":{"cls": "autotile", "id": "autotile1", "noPass": true}, + "152":{"cls": "autotile", "id": "autotile2", "noPass": true}, + "153":{"cls": "autotile", "id": "autotile3", "noPass": true}, + + + ////////////////////////// 物品部分 ////////////////////////// + + // 21-80 物品 + "21":{"cls": "items", "id": "yellowKey"}, // 黄钥匙 + "22":{"cls": "items", "id": "blueKey"}, // 蓝钥匙 + "23":{"cls": "items", "id": "redKey"}, // 红钥匙 + "24":{"cls": "items", "id": "greenKey"}, // 绿钥匙 + "25":{"cls": "items", "id": "steelKey"}, // 铁门钥匙 + "26":{"cls": "items", "id": "bigKey"}, // 大黄门钥匙(钥匙盒) + "27":{"cls": "items", "id": "redJewel"}, // 红宝石 + "28":{"cls": "items", "id": "blueJewel"}, // 蓝宝石 + "29":{"cls": "items", "id": "greenJewel"}, // 绿宝石 + "30":{"cls": "items", "id": "yellowJewel"}, // 黄宝石 + "31":{"cls": "items", "id": "redPotion"}, // 红血瓶 + "32":{"cls": "items", "id": "bluePotion"}, // 蓝血瓶 + "33":{"cls": "items", "id": "greenPotion"}, // 绿血瓶 + "34":{"cls": "items", "id": "yellowPotion"}, // 黄血瓶 + "35":{"cls": "items", "id": "sword1"}, // 铁剑 + "36":{"cls": "items", "id": "shield1"}, // 铁盾 + "37":{"cls": "items", "id": "sword2"}, // 银剑 + "38":{"cls": "items", "id": "shield2"}, // 银盾 + "39":{"cls": "items", "id": "sword3"}, // 骑士剑 + "40":{"cls": "items", "id": "shield3"}, // 骑士盾 + "41":{"cls": "items", "id": "sword4"}, // 圣剑 + "42":{"cls": "items", "id": "shield4"}, // 圣盾 + "43":{"cls": "items", "id": "sword5"}, // 神圣剑 + "44":{"cls": "items", "id": "shield5"}, // 神圣盾 + "45":{"cls": "items", "id": "book"}, // 怪物手册 + "46":{"cls": "items", "id": "fly"}, // 楼层传送器 + "47":{"cls": "items", "id": "pickaxe"}, // 破墙镐 + "48":{"cls": "items", "id": "icePickaxe"}, // 破冰镐 + "49":{"cls": "items", "id": "bomb"}, // 炸弹 + "50":{"cls": "items", "id": "centerFly"}, // 中心对称 + "51":{"cls": "items", "id": "upFly"}, // 上楼器 + "52":{"cls": "items", "id": "downFly"}, // 下楼器 + "53":{"cls": "items", "id": "coin"}, // 幸运金币 + "54":{"cls": "items", "id": "snow"}, // 冰冻徽章 + "55":{"cls": "items", "id": "cross"}, // 十字架 + "56":{"cls": "items", "id": "superPotion"}, // 圣水 + "57":{"cls": "items", "id": "earthquake"}, // 地震卷轴 + "58":{"cls": "items", "id": "poisonWine"}, // 解毒药水 + "59":{"cls": "items", "id": "weakWine"}, // 解衰药水 + "60":{"cls": "items", "id": "curseWine"}, // 解咒药水 + "61":{"cls": "items", "id": "superWine"}, // 万能药水 + "62":{"cls": "items", "id": "knife"}, // 屠龙匕首 + "63":{"cls": "items", "id": "moneyPocket"}, // 金钱袋 + "64":{"cls": "items", "id": "shoes"}, // 绿鞋 + "65":{"cls": "items", "id": "hammer"}, // 圣锤 + + + ////////////////////////// 门、楼梯、传送点部分 ////////////////////////// + + // 81-100 门 + "81":{"cls": "terrains", "id": "yellowDoor", "trigger": "openDoor"}, // 黄门 + "82":{"cls": "terrains", "id": "blueDoor", "trigger": "openDoor"}, // 蓝门 + "83":{"cls": "terrains", "id": "redDoor", "trigger": "openDoor"}, // 红门 + "84":{"cls": "terrains", "id": "greenDoor", "trigger": "openDoor"}, // 绿门 + "85":{"cls": "terrains", "id": "specialDoor", "trigger": "openDoor"}, // 机关门左 + "86":{"cls": "terrains", "id": "steelDoor", "trigger": "openDoor"}, // 铁门 + "87":{"cls": "terrains", "id": "upFloor", "noPass": false}, // 上楼梯 + "88":{"cls": "terrains", "id": "downFloor", "noPass": false}, // 下楼梯 + "89":{"cls": "animates", "id": "portal", "noPass": false}, // 传送门 + "90":{"cls": "animates", "id": "starPortal", "noPass": false}, // 星空传送门 + "91":{"cls": "animates", "id": "upPortal", "noPass": false}, // 上箭头 + "92":{"cls": "animates", "id": "leftPortal", "noPass": false}, // 左箭头 + "93":{"cls": "animates", "id": "downPortal", "noPass": false}, // 下箭头 + "94":{"cls": "animates", "id": "rightPortal", "noPass": false}, // 右箭头 + + + ////////////////////////// NPC部分 ////////////////////////// + + // 121-150 NPC + "121":{"cls": "npcs", "id": "man"}, + "122":{"cls": "npcs", "id": "woman"}, + "123":{"cls": "npcs", "id": "thief"}, + "124":{"cls": "npcs", "id": "fairy"}, + "125":{"cls": "npcs", "id": "magician"}, + "126":{"cls": "npcs", "id": "womanMagician"}, + "127":{"cls": "npcs", "id": "oldMan"}, + "128":{"cls": "npcs", "id": "child"}, + "129":{"cls": "npcs", "id": "wood"}, + "130":{"cls": "npcs", "id": "pinkShop"}, + "131":{"cls": "npcs", "id": "blueShop"}, + "132":{"cls": "npcs", "id": "princess"}, + + ////////////////////////// 其他部分 ////////////////////////// + + // 161-200 其他(单向箭头、灯、箱子等等) + "161":{"cls": "terrains", "id": "arrowUp", "noPass": false}, // 单向上箭头 + "162":{"cls": "terrains", "id": "arrowDown", "noPass": false}, // 单向下箭头 + "163":{"cls": "terrains", "id": "arrowLeft", "noPass": false}, // 单向左箭头 + "164":{"cls": "terrains", "id": "arrowRight", "noPass": false}, // 单向右箭头 + "165":{"cls": "terrains", "id": "light", "trigger": "changeLight", "noPass": false}, // 灯 + "166":{"cls": "terrains", "id": "darkLight", "noPass": true}, // 暗灯 + + + ////////////////////////// 怪物部分 ////////////////////////// + + // 201-300 怪物 + "201":{"cls": "enemys", "id": "greenSlime"}, + "202":{"cls": "enemys", "id": "redSlime"}, + "203":{"cls": "enemys", "id": "blackSlime"}, + "204":{"cls": "enemys", "id": "slimelord"}, + "205":{"cls": "enemys", "id": "bat"}, + "206":{"cls": "enemys", "id": "bigBat"}, + "207":{"cls": "enemys", "id": "redBat"}, + "208":{"cls": "enemys", "id": "vampire"}, + "209":{"cls": "enemys", "id": "skeleton"}, + "210":{"cls": "enemys", "id": "skeletonSoilder"}, + "211":{"cls": "enemys", "id": "skeletonCaptain"}, + "212":{"cls": "enemys", "id": "ghostSkeleton"}, + "213":{"cls": "enemys", "id": "zombie"}, + "214":{"cls": "enemys", "id": "zombieKnight"}, + "215":{"cls": "enemys", "id": "rock"}, + "216":{"cls": "enemys", "id": "slimeMan"}, + "217":{"cls": "enemys", "id": "bluePriest"}, + "218":{"cls": "enemys", "id": "redPriest"}, + "219":{"cls": "enemys", "id": "brownWizard"}, + "220":{"cls": "enemys", "id": "redWizard"}, + "221":{"cls": "enemys", "id": "yellowGuard"}, + "222":{"cls": "enemys", "id": "blueGuard"}, + "223":{"cls": "enemys", "id": "redGuard"}, + "224":{"cls": "enemys", "id": "swordsman"}, + "225":{"cls": "enemys", "id": "soldier"}, + "226":{"cls": "enemys", "id": "yellowKnight"}, + "227":{"cls": "enemys", "id": "redKnight"}, + "228":{"cls": "enemys", "id": "darkKnight"}, + "229":{"cls": "enemys", "id": "blackKing"}, + "230":{"cls": "enemys", "id": "yellowKing"}, + "231":{"cls": "enemys", "id": "greenKing"}, + "232":{"cls": "enemys", "id": "blueKnight"}, + "233":{"cls": "enemys", "id": "goldSlime"}, + "234":{"cls": "enemys", "id": "poisonSkeleton"}, + "235":{"cls": "enemys", "id": "poisonBat"}, + "236":{"cls": "enemys", "id": "steelRock"}, + "237":{"cls": "enemys", "id": "skeletonPriest"}, + "238":{"cls": "enemys", "id": "skeletonKing"}, + "239":{"cls": "enemys", "id": "skeletonWizard"}, + "240":{"cls": "enemys", "id": "redSkeletonCaption"}, + "241":{"cls": "enemys", "id": "badHero"}, + "242":{"cls": "enemys", "id": "demon"}, + "243":{"cls": "enemys", "id": "demonPriest"}, + "244":{"cls": "enemys", "id": "goldHornSlime"}, + "245":{"cls": "enemys", "id": "redKing"}, + "246":{"cls": "enemys", "id": "whiteKing"}, + "247":{"cls": "enemys", "id": "blackMagician"}, + "248":{"cls": "enemys", "id": "silverSlime"}, + "249":{"cls": "enemys", "id": "swordEmperor"}, + "250":{"cls": "enemys", "id": "whiteHornSlime"}, + "251":{"cls": "enemys", "id": "badPrincess"}, + "252":{"cls": "enemys", "id": "badFairy"}, + "253":{"cls": "enemys", "id": "grayPriest"}, + "254":{"cls": "enemys", "id": "redSwordsman"}, + "255":{"cls": "enemys", "id": "whiteGhost"}, + "256":{"cls": "enemys", "id": "poisonZombie"}, + "257":{"cls": "enemys", "id": "magicDragon"}, + "258":{"cls": "enemys", "id": "octopus"}, + "259":{"cls": "enemys", "id": "darkFairy"}, + "260":{"cls": "enemys", "id": "greenKnight"}, + + ////////////////////////// 待定... ////////////////////////// + // 目前ID暂时不要超过400 +} \ No newline at end of file diff --git a/libs/floors/sample0.js b/libs/floors/sample0.js index a32e0d7d..4535039c 100644 --- a/libs/floors/sample0.js +++ b/libs/floors/sample0.js @@ -41,7 +41,7 @@ main.floors.sample0 = { "10,11": [ // 守着门的老人 "\t[老人,woman]这些是门,需要对应的钥匙打开。\n机关门必须使用特殊的开法。", "\t[老人,woman]开门后可触发 afterOpenDoor 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。", - {'type': 'hide', "time": 500} + {"type": "hide", "time": 500} ], "2,10": [ // 守着楼梯、传送门、路障的老人 "\t[老人,womanMagician]这些是路障、楼梯、传送门。", diff --git a/libs/floors/sample1.js b/libs/floors/sample1.js index b28c41d1..c9d53d4b 100644 --- a/libs/floors/sample1.js +++ b/libs/floors/sample1.js @@ -61,9 +61,9 @@ main.floors.sample1 = { {"type": "hide", "loc": [1,8]}, {"type": "hide", "loc": [1,5], "time": 500}, // 隐藏红衣魔王,动画500ms {"type": "hide"}, // 隐藏本事件 - {"type": "setFg", "color": [0,0,0], 'time': 1250}, // 渐变为白色 + {"type": "setFg", "color": [0,0,0], "time": 1250}, // 渐变为白色 {"type": "sleep", "time": 700}, - {"type": "changeFloor", "floorId": "sample1", "loc": [1,11], 'direction': 'right', 'time': 1000}, // 楼层切换。changeFloor必须指定floorId和loc。 + {"type": "changeFloor", "floorId": "sample1", "loc": [1,11], "direction": "right", "time": 1000}, // 楼层切换。changeFloor必须指定floorId和loc。 // 备注:这里也可以下面的这种写法: // {"type": "changePos", "loc": [1,11]} // 使用这种写法将不会有“楼层切换动画”,而是直接让勇士到达本层的loc位置。 diff --git a/libs/icons.js b/libs/icons.js index 4aced479..a614cded 100644 --- a/libs/icons.js +++ b/libs/icons.js @@ -3,220 +3,8 @@ function icons() { } icons.prototype.init = function () { - this.icons = { - 'hero': { - 'down': {'loc': 0, 'stop': 0, 'leftFoot': 1, 'rightFoot': 3}, - 'left': {'loc': 1, 'stop': 0, 'leftFoot': 1, 'rightFoot': 3}, - 'right': {'loc': 2, 'stop': 0, 'leftFoot': 1, 'rightFoot': 3}, - 'up': {'loc': 3, 'stop': 0, 'leftFoot': 1, 'rightFoot': 3} - }, - 'terrains': { - 'ground': 0, - 'grass': 1, - 'grass2': 2, - 'snowGround': 3, - 'ground2': 4, - 'ground3': 5, - 'ground4': 6, - 'sand': 7, - 'ground5': 8, - 'yellowWall2': 9, - 'whiteWall2': 10, - 'blueWall2': 11, - 'blockWall': 12, - 'grayWall': 13, - 'white': 14, - 'ground6': 15, - 'soil': 16, - 'yellowWall': 17, - 'whiteWall': 18, - 'blueWall': 19, - 'star': 20, - 'lava': 21, - 'ice': 22, - 'downFloor': 23, - 'upFloor': 24, - 'yellowDoor': 25, - 'blueDoor': 26, - 'redDoor': 27, - 'greenDoor': 28, - 'specialDoor': 29, - 'steelDoor': 30, - 'blueShop-left': 31, - 'blueShop-right': 32, - 'pinkShop-left': 33, - 'pinkShop-right': 34, - 'arrowUp': 35, - 'arrowDown': 36, - 'arrowLeft': 37, - 'arrowRight': 38, - 'light': 39, - 'darkLight': 40 - }, - 'animates': { - 'star': 0, - 'lava': 1, - 'waterWall': 2, - 'yellowDoor': 3, - 'blueDoor': 4, - 'redDoor': 5, - 'greenDoor': 6, - 'specialDoor': 7, - 'blueWallDoor': 8, - 'yellowWallDoor': 9, - 'whiteWallDoor': 10, - 'steelDoor': 11, - 'lavaDoor': 12, - 'grayLavaDoor': 13, - 'starDoor': 14, - 'mockBlueWallDoor': 15, - 'mockYellowWallDoor': 16, - 'mockWhiteWallDoor': 17, - 'iceYellowWallDoor': 18, - 'starPortal': 19, - 'exclamation': 20, - 'portal': 21, - 'switch': 22, - 'lavaNet': 23, - 'poisonNet': 24, - 'weakNet': 25, - 'curseNet': 26, - 'downPortal': 27, - 'leftPortal': 28, - 'rightPortal': 29, - 'upPortal': 30, - 'water': 31, - }, - 'npcs': { - 'man': 0, - 'woman': 1, - 'thief': 2, - 'fairy': 3, - 'magician': 4, - 'womanMagician': 5, - 'oldMan': 6, - 'child': 7, - 'wood': 8, - 'pinkShop': 9, - 'blueShop': 10, - 'princess': 11 - }, - 'enemys': { - 'greenSlime': 0, - 'redSlime': 1, - 'blackSlime': 2, - 'slimelord': 3, - 'bat': 4, - 'bigBat': 5, - 'redBat': 6, - 'vampire': 7, - 'skeleton': 8, - 'skeletonSoilder': 9, - 'skeletonCaptain': 10, - 'ghostSkeleton': 11, - 'zombie': 12, - 'zombieKnight': 13, - 'rock': 14, - 'slimeMan': 15, - 'bluePriest': 16, - 'redPriest': 17, - 'brownWizard': 18, - 'redWizard': 19, - 'yellowGuard': 20, - 'blueGuard': 21, - 'redGuard': 22, - 'swordsman': 23, - 'soldier': 24, - 'yellowKnight': 25, - 'redKnight': 26, - 'darkKnight': 27, - 'blackKing': 28, - 'yellowKing': 29, - 'greenKing': 30, - 'blueKnight': 31, - 'goldSlime': 32, - 'poisonSkeleton': 33, - 'poisonBat': 34, - 'steelRock': 35, - 'skeletonPriest': 36, - 'skeletonKing': 37, - 'skeletonWizard': 38, - 'redSkeletonCaption': 39, - 'badHero': 40, - 'demon': 41, - 'demonPriest': 42, - 'goldHornSlime': 43, - 'redKing': 44, - 'whiteKing': 45, - 'blackMagician': 46, - 'silverSlime': 47, - 'swordEmperor': 48, - 'whiteHornSlime': 49, - 'badPrincess': 50, - 'badFairy': 51, - 'grayPriest': 52, - 'redSwordsman': 53, - 'whiteGhost': 54, - 'poisonZombie': 55, - 'magicDragon': 56, - 'octopus': 57, - 'darkFairy': 58, - 'greenKnight': 59, - }, - 'items': { - 'yellowKey': 0, - 'blueKey': 1, - 'redKey': 2, - 'greenKey': 3, - 'steelKey': 4, - 'bigKey': 6, - 'redJewel': 16, - 'blueJewel': 17, - 'greenJewel': 18, - 'yellowJewel': 19, - 'redPotion': 20, - 'bluePotion': 21, - 'greenPotion': 22, - 'yellowPotion': 23, - 'sword1': 50, - 'sword2': 51, - 'sword3': 52, - 'sword4': 53, - 'sword5': 54, - 'shield1': 55, - 'shield2': 56, - 'shield3': 57, - 'shield4': 58, - 'shield5': 59, - 'book': 9, - 'fly': 12, - 'pickaxe': 45, - 'icePickaxe': 44, - 'bomb': 43, - 'centerFly': 13, - 'upFly': 15, - 'downFly': 14, - 'coin': 11, - 'snow': 41, - 'cross': 40, - 'superPotion': 29, - 'earthquake': 8, - 'poisonWine': 24, - 'weakWine': 25, - 'curseWine': 27, - 'superWine': 28, - 'knife': 42, - 'moneyPocket': 46, - 'shoes': 47, - 'hammer': 48 - }, - 'autotile': { // 所有的Autotile列表;后面的index简单取0即可 - 'autotile': 0, - 'autotile1': 0, - 'autotile2': 0, - 'autotile3': 0, - } - } + this.icons = icons_4665ee12_3a1f_44a4_bea3_0fccba634dc1; + delete(icons_4665ee12_3a1f_44a4_bea3_0fccba634dc1); } icons.prototype.getIcons = function () { diff --git a/libs/items.js b/libs/items.js index e2a36c8a..1d6a0201 100644 --- a/libs/items.js +++ b/libs/items.js @@ -3,60 +3,10 @@ function items() { } items.prototype.init = function () { - this.items = { - // 钥匙 - 'yellowKey': {'cls': 'keys', 'name': '黄钥匙'}, - 'blueKey': {'cls': 'keys', 'name': '蓝钥匙'}, - 'redKey': {'cls': 'keys', 'name': '红钥匙'}, - - // 宝石、血瓶 - 'redJewel': {'cls': 'items', 'name': '红宝石'}, - 'blueJewel': {'cls': 'items', 'name': '蓝宝石'}, - 'greenJewel': {'cls': 'items', 'name': '绿宝石'}, - 'yellowJewel': {'cls': 'items', 'name': '黄宝石'}, - 'redPotion': {'cls': 'items', 'name': '红血瓶'}, - 'bluePotion': {'cls': 'items', 'name': '蓝血瓶'}, - 'yellowPotion': {'cls': 'items', 'name': '黄血瓶'}, - 'greenPotion': {'cls': 'items', 'name': '绿血瓶'}, - 'sword1': {'cls': 'items', 'name': '铁剑'}, - 'sword2': {'cls': 'items', 'name': '银剑'}, - 'sword3': {'cls': 'items', 'name': '骑士剑'}, - 'sword4': {'cls': 'items', 'name': '圣剑'}, - 'sword5': {'cls': 'items', 'name': '神圣剑'}, - 'shield1': {'cls': 'items', 'name': '铁盾'}, - 'shield2': {'cls': 'items', 'name': '银盾'}, - 'shield3': {'cls': 'items', 'name': '骑士盾'}, - 'shield4': {'cls': 'items', 'name': '圣盾'}, - 'shield5': {'cls': 'items', 'name': '神圣盾'}, - 'superPotion': {'cls': 'items', 'name': '圣水'}, - 'moneyPocket': {'cls': 'items', 'name': '金钱袋'}, - - // 物品 - 'book': {'cls': 'constants', 'name': '怪物手册', 'text': '可以查看当前楼层各怪物属性'}, - 'fly': {'cls': 'constants', 'name': '楼层传送器', 'text': '可以自由往来去过的楼层'}, - 'coin': {'cls': 'constants', 'name': '幸运金币', 'text': '持有时打败怪物可得双倍金币'}, - 'snow': {'cls': 'constants', 'name': '冰冻徽章', 'text': '可以将四周的熔岩变成平地'}, - 'cross': {'cls': 'constants', 'name': '十字架', 'text': '该道具尚未被定义'}, - 'knife': {'cls': 'constants', 'name': '屠龙匕首', 'text': '该道具尚未被定义'}, - 'shoes': {'cls': 'constants', 'name': '绿鞋', 'text': '持有时无视负面地形'}, - - // 道具 - 'bigKey': {'cls': 'tools', 'name': '大黄门钥匙', 'text': '可以开启当前层所有黄门'}, - 'greenKey': {'cls': 'tools', 'name': '绿钥匙', 'text': '可以打开一扇绿门'}, - 'steelKey': {'cls': 'tools', 'name': '铁门钥匙', 'text': '可以打开一扇铁门'}, - 'pickaxe': {'cls': 'tools', 'name': '破墙镐', 'text': '可以破坏勇士面前的墙'}, - 'icePickaxe': {'cls': 'tools', 'name': '破冰镐', 'text': '可以破坏勇士面前的一堵冰墙'}, - 'bomb': {'cls': 'tools', 'name': '炸弹', 'text': '可以炸掉勇士面前的怪物'}, - 'centerFly': {'cls': 'tools', 'name': '中心对称飞行器', 'text': '可以飞向当前楼层中心对称的位置'}, - 'upFly': {'cls': 'tools', 'name': '上楼器', 'text': '可以飞往楼上的相同位置'}, - 'downFly': {'cls': 'tools', 'name': '下楼器', 'text': '可以飞往楼下的相同位置'}, - 'earthquake': {'cls': 'tools', 'name': '地震卷轴', 'text': '可以破坏当前层的所有墙'}, - 'poisonWine': {'cls': 'tools', 'name': '解毒药水', 'text': '可以解除中毒状态'}, - 'weakWine': {'cls': 'tools', 'name': '解衰药水', 'text': '可以解除衰弱状态'}, - 'curseWine': {'cls': 'tools', 'name': '解咒药水', 'text': '可以解除诅咒状态'}, - 'superWine': {'cls': 'tools', 'name': '万能药水', 'text': '可以解除所有不良状态'}, - 'hammer': {'cls': 'tools', 'name': '圣锤', 'text': '可以炸掉勇士面前的怪物'} - } + this.items = items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a.items; + this.itemEffect = items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a.itemEffect; + this.itemEffectTip = items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a.itemEffectTip; + delete(items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a); } // 初始化道具 @@ -79,36 +29,7 @@ items.prototype.getItemEffect = function(itemId, itemNum) { var itemCls = core.material.items[itemId].cls; // 消耗品 if (itemCls === 'items') { - if (itemId === 'redJewel') core.status.hero.atk += core.values.redJewel; - if (itemId === 'blueJewel') core.status.hero.def += core.values.blueJewel; - if (itemId === 'greenJewel') core.status.hero.mdef += core.values.greenJewel; - if (itemId == 'yellowJewel') { // 黄宝石属性:需自己定义 - core.status.hero.hp+=1000; - core.status.hero.atk+=6; - core.status.hero.def+=6; - core.status.hero.mdef+=10; - } - if (itemId === 'redPotion') core.status.hero.hp += core.values.redPotion; - if (itemId === 'bluePotion') core.status.hero.hp += core.values.bluePotion; - if (itemId === 'yellowPotion') core.status.hero.hp += core.values.yellowPotion; - if (itemId === 'greenPotion') core.status.hero.hp += core.values.greenPotion; - if (itemId === 'sword1') core.status.hero.atk += core.values.sword1; - if (itemId === 'sword2') core.status.hero.atk += core.values.sword2; - if (itemId == 'sword3') core.status.hero.atk += core.values.sword3; - if (itemId == 'sword4') core.status.hero.atk += core.values.sword4; - if (itemId === 'sword5') core.status.hero.atk += core.values.sword5; - if (itemId === 'shield1') core.status.hero.def += core.values.shield1; - if (itemId === 'shield2') core.status.hero.def += core.values.shield2; - if (itemId === 'shield3') core.status.hero.def += core.values.shield3; - if (itemId === 'shield4') core.status.hero.def += core.values.shield4; - if (itemId === 'shield5') core.status.hero.def += core.values.shield5; - if (itemId === 'bigKey') { // 只有是钥匙盒才会执行这一步 - core.status.hero.items.keys.yellowKey++; - core.status.hero.items.keys.blueKey++; - core.status.hero.items.keys.redKey++; - } - if (itemId == 'superPotion') core.status.hero.hp *= 2; - if (itemId == 'moneyPocket') core.status.hero.money += core.values.moneyPocket; + if (itemId in this.itemEffect)eval(this.itemEffect[itemId]); } else { core.addItem(itemId, itemNum); @@ -116,27 +37,7 @@ items.prototype.getItemEffect = function(itemId, itemNum) { } items.prototype.getItemEffectTip = function(itemId) { - if (itemId === 'redJewel') return ",攻击+"+core.values.redJewel; - if (itemId === 'blueJewel') return ",防御+"+core.values.blueJewel; - if (itemId === 'greenJewel') return ",魔防+"+core.values.greenJewel; - if (itemId == 'yellowJewel') return ",全属性提升"; - if (itemId === 'redPotion') return ",生命+"+core.values.redPotion; - if (itemId === 'bluePotion') return ",生命+"+core.values.bluePotion; - if (itemId === 'yellowPotion') return ",生命+"+core.values.yellowPotion; - if (itemId === 'greenPotion') return ",生命+"+core.values.greenPotion; - if (itemId === 'sword1') return ",攻击+"+core.values.sword1; - if (itemId === 'sword2') return ",攻击+"+core.values.sword2; - if (itemId === 'sword3') return ",攻击+"+core.values.sword3; - if (itemId === 'sword4') return ",攻击+"+core.values.sword4; - if (itemId === 'sword5') return ",攻击+"+core.values.sword5; - if (itemId === 'shield1') return ",防御+"+core.values.shield1; - if (itemId === 'shield2') return ",防御+"+core.values.shield2; - if (itemId === 'shield3') return ",防御+"+core.values.shield3; - if (itemId === 'shield4') return ",防御+"+core.values.shield4; - if (itemId === 'shield5') return ",防御+"+core.values.shield5; - if (itemId === 'bigKey') return ",全钥匙+1"; - if (itemId === 'superPotion') return ",生命值翻倍"; - if (itemId == 'moneyPocket') return ",金币+"+core.values.moneyPocket; + if (itemId in this.itemEffectTip)return eval(this.itemEffectTip[itemId]); return ""; } diff --git a/libs/maps.js b/libs/maps.js index 0557f07a..7704e7a3 100644 --- a/libs/maps.js +++ b/libs/maps.js @@ -1,5 +1,8 @@ function maps() {} -maps.prototype.init = function() {} +maps.prototype.init = function() { + this.blocksInfo = maps_90f36752_8815_4be8_b32b_d7fad1d0542e; + delete(maps_90f36752_8815_4be8_b32b_d7fad1d0542e); +} maps.prototype.loadFloor = function (floorId, map) { var floor = core.floors[floorId]; @@ -61,197 +64,7 @@ maps.prototype.getBlock = function (x, y, id) { var tmp = {'x': x, 'y': y, 'id': id}; if (enable!=null) tmp.enable = enable; - ////////////////////////// 地形部分 ////////////////////////// - - // 0-20 地形 - if (id == 1) tmp.event = {'cls': 'terrains', 'id': 'yellowWall'}; // 黄墙 - if (id == 2) tmp.event = {'cls': 'terrains', 'id': 'whiteWall'}; // 白墙 - if (id == 3) tmp.event = {'cls': 'terrains', 'id': 'blueWall'}; // 白墙 - if (id == 4) tmp.event = {'cls': 'animates', 'id': 'star', 'noPass': true}; // 星空 - if (id == 5) tmp.event = {'cls': 'animates', 'id': 'lava', 'noPass': true}; // 岩浆 - if (id == 6) tmp.event = {'cls': 'terrains', 'id': 'ice'}; // 岩浆 - if (id == 7) tmp.event = {'cls': 'terrains', 'id': 'blueShop-left'}; // 蓝色商店左 - if (id == 8) tmp.event = {'cls': 'terrains', 'id': 'blueShop-right'}; // 蓝色商店右 - if (id == 9) tmp.event = {'cls': 'terrains', 'id': 'pinkShop-left'}; // 粉色商店左 - if (id == 10) tmp.event = {'cls': 'terrains', 'id': 'pinkShop-right'}; // 粉色商店左 - if (id == 11) tmp.event = {'cls': 'animates', 'id': 'lavaNet', 'noPass': false, 'trigger': 'passNet'}; // 血网 - if (id == 12) tmp.event = {'cls': 'animates', 'id': 'poisonNet', 'noPass': false, 'trigger': 'passNet'}; // 毒网 - if (id == 13) tmp.event = {'cls': 'animates', 'id': 'weakNet', 'noPass': false, 'trigger': 'passNet'}; // 衰网 - if (id == 14) tmp.event = {'cls': 'animates', 'id': 'curseNet', 'noPass': false, 'trigger': 'passNet'}; // 咒网 - if (id == 15) tmp.event = {'cls': 'animates', 'id': 'water', 'noPass': true}; // 水 - // 在这里添加更多地形 - // 如果空地不足,可以从180以后开始继续放,只要不和现有的数字冲突即可 - - // Autotile - if (id == 20) tmp.event = {'cls': 'autotile', 'id': 'autotile', 'noPass': true}; // autotile - // 更多的autotile从151到160,只要不和现有的数字冲突即可 - if (id == 151) tmp.event = {'cls': 'autotile', 'id': 'autotile1', 'noPass': true}; - if (id == 152) tmp.event = {'cls': 'autotile', 'id': 'autotile2', 'noPass': true}; - if (id == 153) tmp.event = {'cls': 'autotile', 'id': 'autotile3', 'noPass': true}; - - - ////////////////////////// 物品部分 ////////////////////////// - - // 21-80 物品 - if (id == 21) tmp.event = {'cls': 'items', 'id': 'yellowKey'}; // 黄钥匙 - if (id == 22) tmp.event = {'cls': 'items', 'id': 'blueKey'}; // 蓝钥匙 - if (id == 23) tmp.event = {'cls': 'items', 'id': 'redKey'}; // 红钥匙 - if (id == 24) tmp.event = {'cls': 'items', 'id': 'greenKey'}; // 绿钥匙 - if (id == 25) tmp.event = {'cls': 'items', 'id': 'steelKey'}; // 铁门钥匙 - if (id == 26) tmp.event = {'cls': 'items', 'id': 'bigKey'}; // 大黄门钥匙(钥匙盒) - if (id == 27) tmp.event = {'cls': 'items', 'id': 'redJewel'}; // 红宝石 - if (id == 28) tmp.event = {'cls': 'items', 'id': 'blueJewel'}; // 蓝宝石 - if (id == 29) tmp.event = {'cls': 'items', 'id': 'greenJewel'}; // 绿宝石 - if (id == 30) tmp.event = {'cls': 'items', 'id': 'yellowJewel'}; // 黄宝石 - if (id == 31) tmp.event = {'cls': 'items', 'id': 'redPotion'}; // 红血瓶 - if (id == 32) tmp.event = {'cls': 'items', 'id': 'bluePotion'}; // 蓝血瓶 - if (id == 33) tmp.event = {'cls': 'items', 'id': 'greenPotion'}; // 绿血瓶 - if (id == 34) tmp.event = {'cls': 'items', 'id': 'yellowPotion'}; // 黄血瓶 - if (id == 35) tmp.event = {'cls': 'items', 'id': 'sword1'}; // 铁剑 - if (id == 36) tmp.event = {'cls': 'items', 'id': 'shield1'}; // 铁盾 - if (id == 37) tmp.event = {'cls': 'items', 'id': 'sword2'}; // 银剑 - if (id == 38) tmp.event = {'cls': 'items', 'id': 'shield2'}; // 银盾 - if (id == 39) tmp.event = {'cls': 'items', 'id': 'sword3'}; // 骑士剑 - if (id == 40) tmp.event = {'cls': 'items', 'id': 'shield3'}; // 骑士盾 - if (id == 41) tmp.event = {'cls': 'items', 'id': 'sword4'}; // 圣剑 - if (id == 42) tmp.event = {'cls': 'items', 'id': 'shield4'}; // 圣盾 - if (id == 43) tmp.event = {'cls': 'items', 'id': 'sword5'}; // 神圣剑 - if (id == 44) tmp.event = {'cls': 'items', 'id': 'shield5'}; // 神圣盾 - if (id == 45) tmp.event = {'cls': 'items', 'id': 'book'}; // 怪物手册 - if (id == 46) tmp.event = {'cls': 'items', 'id': 'fly'}; // 楼层传送器 - if (id == 47) tmp.event = {'cls': 'items', 'id': 'pickaxe'}; // 破墙镐 - if (id == 48) tmp.event = {'cls': 'items', 'id': 'icePickaxe'}; // 破冰镐 - if (id == 49) tmp.event = {'cls': 'items', 'id': 'bomb'}; // 炸弹 - if (id == 50) tmp.event = {'cls': 'items', 'id': 'centerFly'}; // 中心对称 - if (id == 51) tmp.event = {'cls': 'items', 'id': 'upFly'}; // 上楼器 - if (id == 52) tmp.event = {'cls': 'items', 'id': 'downFly'}; // 下楼器 - if (id == 53) tmp.event = {'cls': 'items', 'id': 'coin'}; // 幸运金币 - if (id == 54) tmp.event = {'cls': 'items', 'id': 'snow'}; // 冰冻徽章 - if (id == 55) tmp.event = {'cls': 'items', 'id': 'cross'}; // 十字架 - if (id == 56) tmp.event = {'cls': 'items', 'id': 'superPotion'}; // 圣水 - if (id == 57) tmp.event = {'cls': 'items', 'id': 'earthquake'} // 地震卷轴 - if (id == 58) tmp.event = {'cls': 'items', 'id': 'poisonWine'} // 解毒药水 - if (id == 59) tmp.event = {'cls': 'items', 'id': 'weakWine'} // 解衰药水 - if (id == 60) tmp.event = {'cls': 'items', 'id': 'curseWine'} // 解咒药水 - if (id == 61) tmp.event = {'cls': 'items', 'id': 'superWine'} // 万能药水 - if (id == 62) tmp.event = {'cls': 'items', 'id': 'knife'} // 屠龙匕首 - if (id == 63) tmp.event = {'cls': 'items', 'id': 'moneyPocket'} // 金钱袋 - if (id == 64) tmp.event = {'cls': 'items', 'id': 'shoes'} // 绿鞋 - if (id == 65) tmp.event = {'cls': 'items', 'id': 'hammer'} // 圣锤 - - - ////////////////////////// 门、楼梯、传送点部分 ////////////////////////// - - // 81-100 门 - if (id == 81) tmp.event = {'cls': 'terrains', 'id': 'yellowDoor', 'trigger': 'openDoor'}; // 黄门 - if (id == 82) tmp.event = {'cls': 'terrains', 'id': 'blueDoor', 'trigger': 'openDoor'}; // 蓝门 - if (id == 83) tmp.event = {'cls': 'terrains', 'id': 'redDoor', 'trigger': 'openDoor'}; // 红门 - if (id == 84) tmp.event = {'cls': 'terrains', 'id': 'greenDoor', 'trigger': 'openDoor'}; // 绿门 - if (id == 85) tmp.event = {'cls': 'terrains', 'id': 'specialDoor', 'trigger': 'openDoor'}; // 机关门左 - if (id == 86) tmp.event = {'cls': 'terrains', 'id': 'steelDoor', 'trigger': 'openDoor'}; // 铁门 - if (id == 87) tmp.event = {'cls': 'terrains', 'id': 'upFloor', 'noPass': false}; // 上楼梯 - if (id == 88) tmp.event = {'cls': 'terrains', 'id': 'downFloor', 'noPass': false}; // 下楼梯 - if (id == 89) tmp.event = {'cls': 'animates', 'id': 'portal', 'noPass': false}; // 传送门 - if (id == 90) tmp.event = {'cls': 'animates', 'id': 'starPortal', 'noPass': false}; // 星空传送门 - if (id == 91) tmp.event = {'cls': 'animates', 'id': 'upPortal', 'noPass': false}; // 上箭头 - if (id == 92) tmp.event = {'cls': 'animates', 'id': 'leftPortal', 'noPass': false}; // 左箭头 - if (id == 93) tmp.event = {'cls': 'animates', 'id': 'downPortal', 'noPass': false}; // 下箭头 - if (id == 94) tmp.event = {'cls': 'animates', 'id': 'rightPortal', 'noPass': false}; // 右箭头 - - - ////////////////////////// NPC部分 ////////////////////////// - - // 121-150 NPC - if (id == 121) tmp.event = {'cls': 'npcs', 'id': 'man'}; - if (id == 122) tmp.event = {'cls': 'npcs', 'id': 'woman'}; - if (id == 123) tmp.event = {'cls': 'npcs', 'id': 'thief'}; - if (id == 124) tmp.event = {'cls': 'npcs', 'id': 'fairy'}; - if (id == 125) tmp.event = {'cls': 'npcs', 'id': 'magician'}; - if (id == 126) tmp.event = {'cls': 'npcs', 'id': 'womanMagician'}; - if (id == 127) tmp.event = {'cls': 'npcs', 'id': 'oldMan'}; - if (id == 128) tmp.event = {'cls': 'npcs', 'id': 'child'}; - if (id == 129) tmp.event = {'cls': 'npcs', 'id': 'wood'}; - if (id == 130) tmp.event = {'cls': 'npcs', 'id': 'pinkShop'}; - if (id == 131) tmp.event = {'cls': 'npcs', 'id': 'blueShop'}; - if (id == 132) tmp.event = {'cls': 'npcs', 'id': 'princess'}; - - ////////////////////////// 其他部分 ////////////////////////// - - // 161-200 其他(单向箭头、灯、箱子等等) - if (id == 161) tmp.event = {'cls': 'terrains', 'id': 'arrowUp', 'noPass': false}; // 单向上箭头 - if (id == 162) tmp.event = {'cls': 'terrains', 'id': 'arrowDown', 'noPass': false}; // 单向下箭头 - if (id == 163) tmp.event = {'cls': 'terrains', 'id': 'arrowLeft', 'noPass': false}; // 单向左箭头 - if (id == 164) tmp.event = {'cls': 'terrains', 'id': 'arrowRight', 'noPass': false}; // 单向右箭头 - if (id == 165) tmp.event = {'cls': 'terrains', 'id': 'light', 'trigger': 'changeLight', 'noPass': false}; // 灯 - if (id == 166) tmp.event = {'cls': 'terrains', 'id': 'darkLight', 'noPass': true}; // 暗灯 - - - ////////////////////////// 怪物部分 ////////////////////////// - - // 201-300 怪物 - if (id == 201) tmp.event = {'cls': 'enemys', 'id': 'greenSlime'}; - if (id == 202) tmp.event = {'cls': 'enemys', 'id': 'redSlime'}; - if (id == 203) tmp.event = {'cls': 'enemys', 'id': 'blackSlime'}; - if (id == 204) tmp.event = {'cls': 'enemys', 'id': 'slimelord'}; - if (id == 205) tmp.event = {'cls': 'enemys', 'id': 'bat'}; - if (id == 206) tmp.event = {'cls': 'enemys', 'id': 'bigBat'}; - if (id == 207) tmp.event = {'cls': 'enemys', 'id': 'redBat'}; - if (id == 208) tmp.event = {'cls': 'enemys', 'id': 'vampire'}; - if (id == 209) tmp.event = {'cls': 'enemys', 'id': 'skeleton'}; - if (id == 210) tmp.event = {'cls': 'enemys', 'id': 'skeletonSoilder'}; - if (id == 211) tmp.event = {'cls': 'enemys', 'id': 'skeletonCaptain'}; - if (id == 212) tmp.event = {'cls': 'enemys', 'id': 'ghostSkeleton'}; - if (id == 213) tmp.event = {'cls': 'enemys', 'id': 'zombie'}; - if (id == 214) tmp.event = {'cls': 'enemys', 'id': 'zombieKnight'}; - if (id == 215) tmp.event = {'cls': 'enemys', 'id': 'rock'}; - if (id == 216) tmp.event = {'cls': 'enemys', 'id': 'slimeMan'}; - if (id == 217) tmp.event = {'cls': 'enemys', 'id': 'bluePriest'}; - if (id == 218) tmp.event = {'cls': 'enemys', 'id': 'redPriest'}; - if (id == 219) tmp.event = {'cls': 'enemys', 'id': 'brownWizard'}; - if (id == 220) tmp.event = {'cls': 'enemys', 'id': 'redWizard'}; - if (id == 221) tmp.event = {'cls': 'enemys', 'id': 'yellowGuard'}; - if (id == 222) tmp.event = {'cls': 'enemys', 'id': 'blueGuard'}; - if (id == 223) tmp.event = {'cls': 'enemys', 'id': 'redGuard'}; - if (id == 224) tmp.event = {'cls': 'enemys', 'id': 'swordsman'}; - if (id == 225) tmp.event = {'cls': 'enemys', 'id': 'soldier'}; - if (id == 226) tmp.event = {'cls': 'enemys', 'id': 'yellowKnight'}; - if (id == 227) tmp.event = {'cls': 'enemys', 'id': 'redKnight'}; - if (id == 228) tmp.event = {'cls': 'enemys', 'id': 'darkKnight'}; - if (id == 229) tmp.event = {'cls': 'enemys', 'id': 'blackKing'}; - if (id == 230) tmp.event = {'cls': 'enemys', 'id': 'yellowKing'}; - if (id == 231) tmp.event = {'cls': 'enemys', 'id': 'greenKing'}; - if (id == 232) tmp.event = {'cls': 'enemys', 'id': 'blueKnight'}; - if (id == 233) tmp.event = {'cls': 'enemys', 'id': 'goldSlime'}; - if (id == 234) tmp.event = {'cls': 'enemys', 'id': 'poisonSkeleton'}; - if (id == 235) tmp.event = {'cls': 'enemys', 'id': 'poisonBat'}; - if (id == 236) tmp.event = {'cls': 'enemys', 'id': 'steelRock'}; - if (id == 237) tmp.event = {'cls': 'enemys', 'id': 'skeletonPriest'}; - if (id == 238) tmp.event = {'cls': 'enemys', 'id': 'skeletonKing'}; - if (id == 239) tmp.event = {'cls': 'enemys', 'id': 'skeletonWizard'}; - if (id == 240) tmp.event = {'cls': 'enemys', 'id': 'redSkeletonCaption'}; - if (id == 241) tmp.event = {'cls': 'enemys', 'id': 'badHero'}; - if (id == 242) tmp.event = {'cls': 'enemys', 'id': 'demon'}; - if (id == 243) tmp.event = {'cls': 'enemys', 'id': 'demonPriest'}; - if (id == 244) tmp.event = {'cls': 'enemys', 'id': 'goldHornSlime'}; - if (id == 245) tmp.event = {'cls': 'enemys', 'id': 'redKing'}; - if (id == 246) tmp.event = {'cls': 'enemys', 'id': 'whiteKing'}; - if (id == 247) tmp.event = {'cls': 'enemys', 'id': 'blackMagician'}; - if (id == 248) tmp.event = {'cls': 'enemys', 'id': 'silverSlime'}; - if (id == 249) tmp.event = {'cls': 'enemys', 'id': 'swordEmperor'}; - if (id == 250) tmp.event = {'cls': 'enemys', 'id': 'whiteHornSlime'}; - if (id == 251) tmp.event = {'cls': 'enemys', 'id': 'badPrincess'}; - if (id == 252) tmp.event = {'cls': 'enemys', 'id': 'badFairy'}; - if (id == 253) tmp.event = {'cls': 'enemys', 'id': 'grayPriest'}; - if (id == 254) tmp.event = {'cls': 'enemys', 'id': 'redSwordsman'}; - if (id == 255) tmp.event = {'cls': 'enemys', 'id': 'whiteGhost'}; - if (id == 256) tmp.event = {'cls': 'enemys', 'id': 'poisonZombie'}; - if (id == 257) tmp.event = {'cls': 'enemys', 'id': 'magicDragon'}; - if (id == 258) tmp.event = {'cls': 'enemys', 'id': 'octopus'}; - if (id == 259) tmp.event = {'cls': 'enemys', 'id': 'darkFairy'}; - if (id == 260) tmp.event = {'cls': 'enemys', 'id': 'greenKnight'}; - - ////////////////////////// 待定... ////////////////////////// - // 目前ID暂时不要超过400 + if (id in this.blocksInfo) tmp.event = JSON.parse(JSON.stringify(this.blocksInfo[id])); return tmp; } diff --git a/main.js b/main.js index b9891a99..0e07327f 100644 --- a/main.js +++ b/main.js @@ -43,6 +43,9 @@ function main() { this.loadList = [ 'items', 'icons', 'maps', 'enemys', 'events', 'data', 'ui', 'core' ]; + this.pureData = [ + "data","enemys","icons","maps","items" + ]; this.images = [ 'animates', 'enemys', 'hero', 'items', 'npcs', 'terrains' // Autotile 动态添加 @@ -90,15 +93,6 @@ function main() { //------------------------ 用户修改内容 ------------------------// this.version = "0.1"; // 游戏版本号;如果更改了游戏内容建议修改此version以免造成缓存问题。 - - this.useCompress = false; // 是否使用压缩文件 - // 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 - // 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 - // 如果要进行剧本的修改请务必将其改成false。 - - this.floorIds = [ // 在这里按顺序放所有的楼层;其顺序直接影响到楼层传送器的顺序和上楼器/下楼器的顺序 - "sample0", "sample1", "sample2", "test" - ] //------------------------ 用户修改内容 END ------------------------// this.floors = {} @@ -110,18 +104,22 @@ main.prototype.init = function () { for (var i = 0; i < main.dom.gameCanvas.length; i++) { main.canvas[main.dom.gameCanvas[i].id] = main.dom.gameCanvas[i].getContext('2d'); } - main.loaderJs(function () { - var coreData = {}; - for (i = 0; i < main.loadList.length; i++) { - var name = main.loadList[i]; - if (name === 'core') continue; - main[name].init(main.dom); - coreData[name] = main[name]; - } - main.loaderFloors(function() { - main.core.init(main.dom, main.statusBar, main.canvas, main.images, main.sounds, main.floorIds, main.floors, coreData); - main.core.resize(main.dom.body.clientWidth, main.dom.body.clientHeight); - }) + main.loadPureData(function(){ + main.useCompress=data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d.main.useCompress; + main.floorIds=data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d.main.floorIds; + main.loaderJs(function () { + var coreData = {}; + for (i = 0; i < main.loadList.length; i++) { + var name = main.loadList[i]; + if (name === 'core') continue; + main[name].init(main.dom); + coreData[name] = main[name]; + } + main.loaderFloors(function() { + main.core.init(main.dom, main.statusBar, main.canvas, main.images, main.sounds, main.floorIds, main.floors, coreData); + main.core.resize(main.dom.body.clientWidth, main.dom.body.clientHeight); + }); + }); }); } @@ -191,6 +189,20 @@ main.prototype.loadFloor = function(floorId, callback) { } } +main.prototype.loadPureData = function(callback) { + var loadedNum = 0; + main.pureData.forEach(function(name){ + var script = document.createElement('script'); + script.src = 'libs/floors/' + name +'.js?' + this.version; + main.dom.body.appendChild(script); + script.onload = function () { + loadedNum++; + if (loadedNum == main.pureData.length)callback(); + } + }); + +} + main.prototype.setMainTipsText = function (text) { main.dom.mainTips.innerHTML = text; } From d8ea628f111d6e3d636a9bcf9766fabb36b6838b Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Thu, 28 Dec 2017 17:15:45 +0800 Subject: [PATCH 003/102] =?UTF-8?q?=E9=87=8D=E5=91=BD=E5=90=8D=E7=9B=AE?= =?UTF-8?q?=E5=BD=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- libs/{floors => project}/data.js | 0 libs/{floors => project}/enemys.js | 0 libs/{ => project}/floors/MT0.js | 0 libs/{ => project}/floors/sample0.js | 0 libs/{ => project}/floors/sample1.js | 0 libs/{ => project}/floors/sample2.js | 0 libs/{ => project}/floors/test.js | 0 libs/{floors => project}/icons.js | 0 libs/{floors => project}/items.js | 0 libs/{floors => project}/maps.js | 0 main.js | 6 +++--- 11 files changed, 3 insertions(+), 3 deletions(-) rename libs/{floors => project}/data.js (100%) rename libs/{floors => project}/enemys.js (100%) rename libs/{ => project}/floors/MT0.js (100%) rename libs/{ => project}/floors/sample0.js (100%) rename libs/{ => project}/floors/sample1.js (100%) rename libs/{ => project}/floors/sample2.js (100%) rename libs/{ => project}/floors/test.js (100%) rename libs/{floors => project}/icons.js (100%) rename libs/{floors => project}/items.js (100%) rename libs/{floors => project}/maps.js (100%) diff --git a/libs/floors/data.js b/libs/project/data.js similarity index 100% rename from libs/floors/data.js rename to libs/project/data.js diff --git a/libs/floors/enemys.js b/libs/project/enemys.js similarity index 100% rename from libs/floors/enemys.js rename to libs/project/enemys.js diff --git a/libs/floors/MT0.js b/libs/project/floors/MT0.js similarity index 100% rename from libs/floors/MT0.js rename to libs/project/floors/MT0.js diff --git a/libs/floors/sample0.js b/libs/project/floors/sample0.js similarity index 100% rename from libs/floors/sample0.js rename to libs/project/floors/sample0.js diff --git a/libs/floors/sample1.js b/libs/project/floors/sample1.js similarity index 100% rename from libs/floors/sample1.js rename to libs/project/floors/sample1.js diff --git a/libs/floors/sample2.js b/libs/project/floors/sample2.js similarity index 100% rename from libs/floors/sample2.js rename to libs/project/floors/sample2.js diff --git a/libs/floors/test.js b/libs/project/floors/test.js similarity index 100% rename from libs/floors/test.js rename to libs/project/floors/test.js diff --git a/libs/floors/icons.js b/libs/project/icons.js similarity index 100% rename from libs/floors/icons.js rename to libs/project/icons.js diff --git a/libs/floors/items.js b/libs/project/items.js similarity index 100% rename from libs/floors/items.js rename to libs/project/items.js diff --git a/libs/floors/maps.js b/libs/project/maps.js similarity index 100% rename from libs/floors/maps.js rename to libs/project/maps.js diff --git a/main.js b/main.js index 0e07327f..7653d2cf 100644 --- a/main.js +++ b/main.js @@ -149,7 +149,7 @@ main.prototype.loaderFloors = function (callback) { main.setMainTipsText('正在加载楼层文件...') if (this.useCompress) { // 读取压缩文件 var script = document.createElement('script'); - script.src = 'libs/floors.min.js?' + this.version; + script.src = 'libs/project/floors.min.js?' + this.version; main.dom.body.appendChild(script); script.onload = function () { main.dom.mainTips.style.display = 'none'; @@ -182,7 +182,7 @@ main.prototype.loadMod = function (modName, callback) { main.prototype.loadFloor = function(floorId, callback) { var script = document.createElement('script'); - script.src = 'libs/floors/' + floorId +'.js?' + this.version; + script.src = 'libs/project/floors/' + floorId +'.js?' + this.version; main.dom.body.appendChild(script); script.onload = function () { callback(floorId); @@ -193,7 +193,7 @@ main.prototype.loadPureData = function(callback) { var loadedNum = 0; main.pureData.forEach(function(name){ var script = document.createElement('script'); - script.src = 'libs/floors/' + name +'.js?' + this.version; + script.src = 'libs/project/' + name +'.js?' + this.version; main.dom.body.appendChild(script); script.onload = function () { loadedNum++; From f92124e16238482a222d511bb8dca4dd54865dee Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 30 Dec 2017 12:02:19 +0800 Subject: [PATCH 004/102] editor.file demo --- _server/editor_file.js | 89 ++++++++++++++++++++++++++++++++++++++++++ drawMapGUI.html | 5 +++ 2 files changed, 94 insertions(+) create mode 100644 _server/editor_file.js diff --git a/_server/editor_file.js b/_server/editor_file.js new file mode 100644 index 00000000..f245b77a --- /dev/null +++ b/_server/editor_file.js @@ -0,0 +1,89 @@ +(function(){ + + editor_file = {}; + + editor_file.getFloorFileList = function(editor,callback){ + if (isset(callback)) callback(['simple0.js','simple1.js','simple2.js'],null); + } + //callback(Array,err:String) + editor_file.loadFloorFile = function(editor,filename,callback){ + if (isset(callback)) callback('',null); + } + //callback(String,err:String) + editor_file.saveFloorFile = function(editor,callback){ + if (isset(callback)) callback(null); + } + //callback(err:String) + editor_file.saveFloorFile = function(editor,saveAsFilename,callback){ + if (isset(callback)) callback(null); + } + //callback(err:String) + + //////////////////////////////////////////////////////////////////// + + editor_file.changeIdAndIdnum = function(editor,id,idnum,callback){ + if (isset(callback)) callback(null); + } + //callback(err:String) + editor_file.editItem = function(editor,id,obj,callback){ + //obj形式同callback的obj,为null或undefined时只查询不修改 + if (isset(callback)) callback( + {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"}, + {'items':'','itemEffect':'','itemEffectTip':''}, + null); + //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items + } + //callback(obj,commentObj,err:String) + editor_file.editEnemy = function(editor,id,obj,callback){ + //obj形式同callback的obj,为null或undefined时只查询不修改 + if (isset(callback)) callback( + {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, "bomb": false}, + {'name': '名称', 'hp': '生命值', 'atk': '攻击力', 'def': '防御力', 'money': '金币', 'experience': '经验', 'special': '特殊属性\n1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:4连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨\n多个属性例如用010411表示先攻2连击吸血\n模仿怪的攻防设为0就好\n', 'value': '特殊属性的数值\n领域怪需要加value表示领域伤害的数值\n吸血怪需要在后面添加value代表吸血比例', 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉'}, + null); + } + //callback(obj,commentObj,err:String) + + //////////////////////////////////////////////////////////////////// + + editor_file.editLoc = function(editor,x,y,obj,callback){ + //obj形式同callback的obj,为null或undefined时只查询不修改 + if (isset(callback)) callback( + {"events":['\t[老人,man]这些是本样板支持的所有的道具。\n\n道具分为三类:items, constants, tools。\nitems 为即捡即用类道具,例如宝石、血瓶、剑盾等。\nconstants 为永久道具,例如怪物手册、楼层传送器、幸运金币等。\ntools 为消耗类道具,例如破墙镐、炸弹、中心对称飞行器等。\n\n后两类道具在工具栏中可以看到并使用。', '\t[老人,man]有关道具效果,定义在items.js中。\n目前大多数道具已有默认行为,如有自定义的需求则需在items.js中修改代码。', '\t[老人,man]constants 和 tools 各最多只允许12种,多了会导致图标溢出。', '\t[老人,man]拾取道具结束后可触发 afterGetItem 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。', {'type': 'hide', 'time': 500}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, + {"events":['', '', '', '', {'type': '', 'time': ' // 消失 \n // 守着门的老人 '}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, + null); + } + //callback(obj,commentObj,err:String) + + //////////////////////////////////////////////////////////////////// + + editor_file.editFloor = function(editor,obj,callback){ + //obj形式同callback的obj,为null或undefined时只查询不修改 + if (isset(callback)) callback( + {'floorId': 'sample0', 'title': '样板 0 层', 'name': '0', 'canFlyTo': True, 'canUseQuickShop': True, 'defaultGround': 'ground', 'firstArrive': ['\t[样板提示]首次到达某层可以触发 firstArrive 事件,该事件可类似于RMXP中的“自动执行脚本”。\n\n本事件支持一切的事件类型,常常用来触发对话,例如:', '\t[hero]我是谁?我从哪来?我又要到哪去?', '\t[仙子,fairy]你问我...?我也不知道啊...', '本层主要对道具、门、怪物等进行介绍,有关事件的各种信息在下一层会有更为详细的说明。']}, + {'floorId': '// 这里需要改楼层名,请和文件名及下面的floorId保持完全一致 // 楼层唯一标识符仅能由字母、数字、下划线组成,且不能由数字开头 // 推荐用法:第20层就用MT20,第38层就用MT38,地下6层就用MT_6(用下划线代替负号),隐藏3层用MT3h(h表示隐藏),等等 \n // 楼层唯一标识符,需要和名字完全一致 ', 'title': ' // 楼层中文名 ', 'name': ' // 显示在状态栏中的层数 ', 'canFlyTo': ' // 该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) ', 'canUseQuickShop': ' // 该层是否允许使用快捷商店 ', 'defaultGround': ' // 默认地面的图块ID(terrains中) \n // 地图数据,需要是13x13,建议使用地图生成器来生成 ', 'firstArrive': ['', '', '', ' // 该楼的所有可能事件列表 \n // 守着道具的老人 ']}, + null); + } + //callback(obj,commentObj,err:String) + + //////////////////////////////////////////////////////////////////// + + + + editor_file.editTower = function(editor,obj,callback){ + //obj形式同callback的obj,为null或undefined时只查询不修改 + if (isset(callback)) callback( + {'main': {'useCompress': False, 'floorIds': ['sample0', 'sample1', 'sample2', 'test']}, 'firstData': {'title': '魔塔样板', 'name': 'template', 'version': 'Ver 1.0.0 (Beta)', 'floorId': 'sample0', 'hero': {'name': '阳光', 'lv': 1, 'hp': 2000, 'atk': 100, 'def': 100, 'mdef': 100, 'money': 100, 'experience': 0, 'items': {'keys': {'yellowKey': 0, 'blueKey': 0, 'redKey': 0}, 'constants': {}, 'tools': {}}, 'flyRange': [], 'loc': {'direction': 'up', 'x': 6, 'y': 10}, 'flags': {'poison': False, 'weak': False, 'curse': False}}, 'startText': ['Hi,欢迎来到 HTML5 魔塔样板!\n\n本样板由艾之葵制作,可以让你在不会写任何代码\n的情况下也能做出属于自己的H5魔塔!', '这里游戏开始时的剧情。\n定义在data.js的startText处。\n\n你可以在这里写上自己的内容。', '赶快来试一试吧!'], 'shops': {'moneyShop1': {'name': '贪婪之神', 'icon': 'blueShop', 'textInList': '1F金币商店', 'use': 'money', 'need': '20+10*times*(times+1)', 'text': '勇敢的武士啊,给我${need}金币就可以:', 'choices': [{'text': '生命+800', 'effect': 'status:hp+=800'}, {'text': '攻击+4', 'effect': 'status:atk+=4'}, {'text': '防御+4', 'effect': 'status:def+=4'}, {'text': '魔防+10', 'effect': 'status:mdef+=10'}]}, 'expShop1': {'name': '经验之神', 'icon': 'pinkShop', 'textInList': '1F经验商店', 'use': 'experience', 'need': '-1', 'text': '勇敢的武士啊,给我若干经验就可以:', 'choices': [{'text': '等级+1', 'need': '100', 'effect': 'status:lv+=1;status:hp+=1000;status:atk+=7;status:def+=7'}, {'text': '攻击+5', 'need': '30', 'effect': 'status:atk+=5'}, {'text': '防御+5', 'need': '30', 'effect': 'status:def+=5'}]}}, 'levelUp': [{}, {'need': 20, 'name': '第二级', 'effect': 'status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10'}, {'need': 40, 'effect': 'function () {\n core.drawText("恭喜升级!");\n core.status.hero.hp *= 2;\n core.status.hero.atk += 100;\n core.status.hero.def += 100;\n }'}]}, 'values': {'HPMAX': 999999, 'lavaDamage': 100, 'poisonDamage': 10, 'weakValue': 20, 'redJewel': 3, 'blueJewel': 3, 'greenJewel': 5, 'redPotion': 100, 'bluePotion': 250, 'yellowPotion': 500, 'greenPotion': 800, 'sword1': 10, 'shield1': 10, 'sword2': 20, 'shield2': 20, 'sword3': 40, 'shield3': 40, 'sword4': 80, 'shield4': 80, 'sword5': 160, 'shield5': 160, 'moneyPocket': 500, 'breakArmor': 0.9, 'counterAttack': 0.1, 'purify': 3, 'hatred': 2, 'animateSpeed': 500}, 'flags': {'enableNegativeDamage': True, 'enableFloor': False, 'enableLv': True, 'enableMDef': True, 'enableMoney': True, 'enableExperience': True, 'enableLevelUp': False, 'enableDebuff': True, 'flyNearStair': True, 'pickaxeFourDirections': True, 'bombFourDirections': True, 'bigKeyIsBox': False, 'startDirectly': False, 'canOpenBattleAnimate': True, 'showBattleAnimateConfirm': True, 'battleAnimate': True, 'displayEnemyDamage': True, 'displayExtraDamage': False, 'enableGentleClick': True, 'portalWithoutTrigger': True, 'potionWhileRouting': False}}, + {'main': {'useCompress': ' // 是否使用压缩文件 // 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 // 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 // 如果要进行剧本的修改请务必将其改成false。 \n // 在这里按顺序放所有的楼层;其顺序直接影响到楼层传送器的顺序和上楼器/下楼器的顺序 ', 'floorIds': ['', '', '', '']}, 'firstData': {'title': ' // 游戏名,将显示在标题页面以及切换楼层的界面中 ', 'name': ' // 游戏的唯一英文标识符。由英文、数字、下划线组成,不能超过20个字符。 ', 'version': ' // 当前游戏版本;版本不一致的存档不能通用。 ', 'floorId': ' // 初始楼层ID \n // 勇士初始数据 ', 'hero': {'name': ' // 勇士名;可以改成喜欢的 ', 'lv': ' // 初始等级,该项必须为正整数 ', 'hp': ' // 初始生命值 ', 'atk': ' // 初始攻击 ', 'def': ' // 初始防御 ', 'mdef': ' // 初始魔防 ', 'money': ' // 初始金币 ', 'experience': ' // 初始经验 \n // 初始道具个数 ', 'items': {'keys': {'yellowKey': '', 'blueKey': '', 'redKey': ''}, 'constants': '', 'tools': ''}, 'flyRange': ' // 初始可飞的楼层;一般留空数组即可 ', 'loc': {'direction': '', 'x': '', 'y': ' // 勇士初始位置 \n // 游戏过程中的变量或flags '}, 'flags': {'poison': ' // 毒 ', 'weak': ' // 衰 ', 'curse': ' // 咒 \n // 游戏开始前剧情。如果无剧情直接留一个空数组即可。 '}}, 'startText': ['', '', ' // 定义全局商店(即快捷商店) \n // 商店唯一ID '], 'shops': {'moneyShop1': {'name': ' // 商店名称(标题) ', 'icon': ' // 商店图标,blueShop为蓝色商店,pinkShop为粉色商店 ', 'textInList': ' // 在快捷商店栏中显示的名称 ', 'use': ' // 商店所要使用的。只能是"money"或"experience"。 ', 'need': ' // 商店需要的金币/经验数值;可以是一个表达式,以times作为参数计算。 // 这里用到的times为该商店的已经的访问次数。首次访问该商店时times的值为0。 // 上面的例子是50层商店的计算公式。你也可以写任意其他的计算公式,只要以times作为参数即可。 // 例如: "need": "25" 就是恒定需要25金币的商店; "need": "20+2*times" 就是第一次访问要20金币,以后每次递增2金币的商店。 // 如果是对于每个选项有不同的计算公式,写 "need": "-1" 即可。可参见下面的经验商店。 ', 'text': ' // 显示的文字,需手动加换行符。可以使用${need}表示上面的need值。 \n // 商店的选项 ', 'choices': [{'text': '', 'effect': ' // 如果有多个effect以分号分开,参见下面的经验商店 '}, {'text': '', 'effect': ''}, {'text': '', 'effect': ''}, {'text': '', 'effect': ' // effect只能对status和item进行操作,不能修改flag值。 // 必须是X+=Y的形式,其中Y可以是一个表达式,以status:xxx或item:xxx为参数 // 其他effect样例: // "item:yellowKey+=1" 黄钥匙+1 // "item:pickaxe+=3" 破墙镐+3 // "status:hp+=2*(status:atk+status:def)" 将生命提升攻防和的数值的两倍 \n // 商店唯一ID '}]}, 'expShop1': {'name': '', 'icon': '', 'textInList': '', 'use': ' // 该商店使用的是经验进行计算 ', 'need': ' // 如果是对于每个选项所需要的数值不同,这里直接写-1,然后下面选项里给定具体数值 ', 'text': ' // 在choices中写need,可以针对每个选项都有不同的需求。 // 这里的need同样可以以times作为参数,比如 "need": "100+20*times" ', 'choices': [{'text': '', 'need': '', 'effect': ' // 多个effect直接以分号分开即可。如上面的意思是生命+1000,攻击+7,防御+7。 '}, {'text': '', 'need': '', 'effect': ''}, {'text': '', 'need': '', 'effect': ' // 经验升级所需要的数值,是一个数组 '}]}}, 'levelUp': [' // 第一项为初始等级,可以简单留空,也可以写name // 每一个里面可以含有三个参数 name, need, effect // need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 // name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 // effect为本次升级所执行的操作,可由若干项组成,由分号分开 // 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 ', {'need': '', 'name': '', 'effect': ' // 先将生命提升攻防和的2倍;再将攻击+10,防御+10 // effect也允许写一个function,代表本次升级将会执行的操作 '}, {'need': '', 'effect': ' // 依次往下写需要的数值即可 \n // 各种数值;一些数值可以在这里设置 \n /****** 角色相关 ******/ '}]}, 'values': {'HPMAX': ' // HP上限;-1则无上限 ', 'lavaDamage': ' // 经过血网受到的伤害 ', 'poisonDamage': ' // 中毒后每步受到的伤害 ', 'weakValue': ' // 衰弱状态下攻防减少的数值 /****** 道具相关 ******/ ', 'redJewel': ' // 红宝石加攻击的数值 ', 'blueJewel': ' // 蓝宝石加防御的数值 ', 'greenJewel': ' // 绿宝石加魔防的数值 ', 'redPotion': ' // 红血瓶加血数值 ', 'bluePotion': ' // 蓝血瓶加血数值 ', 'yellowPotion': ' // 黄血瓶加血数值 ', 'greenPotion': ' // 绿血瓶加血数值 ', 'sword1': ' // 铁剑加攻数值 ', 'shield1': ' // 铁盾加防数值 ', 'sword2': ' // 银剑加攻数值 ', 'shield2': ' // 银盾加防数值 ', 'sword3': ' // 骑士剑加攻数值 ', 'shield3': ' // 骑士盾加防数值 ', 'sword4': ' // 圣剑加攻数值 ', 'shield4': ' // 圣盾加防数值 ', 'sword5': ' // 神圣剑加攻数值 ', 'shield5': ' // 神圣盾加防数值 ', 'moneyPocket': ' // 金钱袋加金币的数值 /****** 怪物相关 ******/ ', 'breakArmor': ' // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) ', 'counterAttack': ' // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) ', 'purify': ' // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) ', 'hatred': ' // 仇恨属性中,每杀死一个怪物获得的仇恨值 /****** 系统相关 ******/ ', 'animateSpeed': ' // 动画时间 \n // 系统FLAG,在游戏运行中中请不要修改它。 \n /****** 角色状态相关 ******/ '}, 'flags': {'enableNegativeDamage': ' // 是否支持负伤害(回血) ', 'enableFloor': ' // 是否在状态栏显示当前楼层 ', 'enableLv': ' // 是否在状态栏显示当前等级 ', 'enableMDef': ' // 是否在状态栏及战斗界面显示魔防(护盾) ', 'enableMoney': ' // 是否在状态栏、怪物手册及战斗界面显示金币 ', 'enableExperience': ' // 是否在状态栏、怪物手册及战斗界面显示经验 ', 'enableLevelUp': ' // 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false ', 'enableDebuff': ' // 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff ////// 上述的几个开关将直接影响状态栏的显示效果 ////// /****** 道具相关 ******/ ', 'flyNearStair': ' // 是否需要在楼梯边使用传送器 ', 'pickaxeFourDirections': ' // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 ', 'bombFourDirections': ' // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) ', 'bigKeyIsBox': ' // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 /****** 系统相关 ******/ ', 'startDirectly': ' // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 ', 'canOpenBattleAnimate': ' // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false ', 'showBattleAnimateConfirm': ' // 是否在游戏开始时提供“是否开启战斗动画”的选项 ', 'battleAnimate': ' // 是否默认显示战斗动画;用户可以手动在菜单栏中开关 ', 'displayEnemyDamage': ' // 是否地图怪物显伤;用户可以手动在菜单栏中开关 ', 'displayExtraDamage': ' // 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 ', 'enableGentleClick': ' // 是否允许轻触(获得面前物品) ', 'portalWithoutTrigger': ' // 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 ', 'potionWhileRouting': ' // 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 '}}, + null); + } + //callback(obj,commentObj,err:String) + + //////////////////////////////////////////////////////////////////// + + var isset = function (val) { + if (val == undefined || val == null) { + return false; + } + return true + } +})(); \ No newline at end of file diff --git a/drawMapGUI.html b/drawMapGUI.html index 7b2fcad2..c49a6b66 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -373,6 +373,7 @@ + + + + + \ No newline at end of file From fd8a03a90de04f3240de946b466cc6c7afaa5368 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sun, 31 Dec 2017 10:49:57 +0800 Subject: [PATCH 007/102] merge 1.3 into 2.0 merge data --- libs/project/data.js | 26 ++-- libs/project/enemys.js | 120 ++++++++-------- libs/project/items.js | 2 +- libs/project/maps.js | 317 ++++++++++++++++++++--------------------- 4 files changed, 233 insertions(+), 232 deletions(-) diff --git a/libs/project/data.js b/libs/project/data.js index 1bbe4e26..9ea2276b 100644 --- a/libs/project/data.js +++ b/libs/project/data.js @@ -17,8 +17,8 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "floorId": "sample0", // 初始楼层ID "hero": { // 勇士初始数据 "name": "阳光", // 勇士名;可以改成喜欢的 - "lv": 1, // 初始等级,该项必须为正整数 - "hp": 2000, // 初始生命值 + 'lv': 1, // 初始等级,该项必须为正整数 + "hp": 1000, // 初始生命值 "atk": 100, // 初始攻击 "def": 100, // 初始防御 "mdef": 100, // 初始魔防 @@ -92,7 +92,7 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "levelUp": [ // 经验升级所需要的数值,是一个数组 {}, // 第一项为初始等级,可以简单留空,也可以写name - // 每一个里面可以含有三个参数 name, need, effect + // 每一个里面可以含有三个参数 need, name, effect // need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 // name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 // effect为本次升级所执行的操作,可由若干项组成,由分号分开 @@ -137,19 +137,18 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "shield5": 160, // 神圣盾加防数值 "moneyPocket": 500, // 金钱袋加金币的数值 /****** 怪物相关 ******/ - "breakArmor": 0.9, // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) - "counterAttack": 0.1, // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) - "purify": 3, // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) - "hatred": 2, // 仇恨属性中,每杀死一个怪物获得的仇恨值 + 'breakArmor': 0.9, // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) + 'counterAttack': 0.1, // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) + 'purify': 3, // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) + 'hatred': 2, // 仇恨属性中,每杀死一个怪物获得的仇恨值 /****** 系统相关 ******/ - "animateSpeed": 500, // 动画时间 + 'animateSpeed': 500, // 动画时间 }, // 系统FLAG,在游戏运行中中请不要修改它。 "flags" : { - /****** 角色状态相关 ******/ - "enableNegativeDamage": true, // 是否支持负伤害(回血) - "enableFloor": false, // 是否在状态栏显示当前楼层 - "enableLv": true, // 是否在状态栏显示当前等级 + /****** 状态栏相关 ******/ + "enableFloor": true, // 是否在状态栏显示当前楼层 + "enableLv": false, // 是否在状态栏显示当前等级 "enableMDef": true, // 是否在状态栏及战斗界面显示魔防(护盾) "enableMoney": true, // 是否在状态栏、怪物手册及战斗界面显示金币 "enableExperience": true, // 是否在状态栏、怪物手册及战斗界面显示经验 @@ -161,6 +160,9 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "pickaxeFourDirections": true, // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 "bombFourDirections": true, // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) "bigKeyIsBox": false, // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 + /****** 怪物相关 ******/ + "enableNegativeDamage": true, // 是否支持负伤害(回血) + "zoneSquare": false, // 领域类型。如果此项为true则为九宫格伤害,为false则为十字伤害 /****** 系统相关 ******/ "startDirectly": false, // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 "canOpenBattleAnimate": true, // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false diff --git a/libs/project/enemys.js b/libs/project/enemys.js index 7952ffd1..dd9cdae5 100644 --- a/libs/project/enemys.js +++ b/libs/project/enemys.js @@ -1,63 +1,63 @@ enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80 = //1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:4连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨 { - "greenSlime": {"name": "绿头怪", "hp": 100, "atk": 120, "def": 0, "money": 1, "experience": 1, "special": 0}, - "redSlime": {"name": "红头怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "blackSlime": {"name": "青头怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "slimelord": {"name": "怪王", "hp": 100, "atk": 120, "def": 0, "money": 10, "experience": 0, "special": 9}, - "bat": {"name": "小蝙蝠", "hp": 100, "atk": 120, "def": 0, "money": 2, "experience": 0, "special": 1}, - "bigBat": {"name": "大蝙蝠", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "redBat": {"name": "红蝙蝠", "hp": 100, "atk": 120, "def": 0, "money": 5, "experience": 0, "special": 4}, - "vampire": {"name": "冥灵魔王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "skeleton": {"name": "骷髅人", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "skeletonSoilder": {"name": "骷髅士兵", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "skeletonCaptain": {"name": "骷髅队长", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "ghostSkeleton": {"name": "冥队长", "hp": 100, "atk": 120, "def": 0, "money": 8, "experience": 0, "special": 7}, - "zombie": {"name": "兽人", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "zombieKnight": {"name": "兽人武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "rock": {"name": "石头人", "hp": 100, "atk": 120, "def": 0, "money": 4, "experience": 0, "special": 3}, - "slimeMan": {"name": "影子战士", "hp": 100, "atk": 0, "def": 0, "money": 11, "experience": 0, "special": 10}, // 模仿怪的攻防设为0就好 - "bluePriest": {"name": "初级法师", "hp": 100, "atk": 120, "def": 0, "money": 3, "experience": 0, "special": 2}, - "redPriest": {"name": "高级法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "brownWizard": {"name": "初级巫师", "hp": 100, "atk": 120, "def": 0, "money": 16, "experience": 0, "special": 15, "value": 100}, // 领域怪需要加value表示领域伤害的数值 - "redWizard": {"name": "高级巫师", "hp": 1000, "atk": 1200, "def": 0, "money": 160, "experience": 0, "special": 15, "value": 200}, - "yellowGuard": {"name": "初级卫兵", "hp": 100, "atk": 120, "def": 0, "money": 10, "experience": 0, "special": 0}, - "blueGuard": {"name": "中级卫兵", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "redGuard": {"name": "高级卫兵", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "swordsman": {"name": "双手剑士", "hp": 100, "atk": 120, "def": 0, "money": 6, "experience": 0, "special": 5}, - "soldier": {"name": "冥战士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "yellowKnight": {"name": "金骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "redKnight": {"name": "红骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "darkKnight": {"name": "黑骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "blackKing": {"name": "黑衣魔王", "hp": 1000, "atk": 500, "def": 0, "money": 1000, "experience": 1000, "special": 0, "bomb": false}, // 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉 - "yellowKing": {"name": "黄衣魔王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "greenKing": {"name": "青衣武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "blueKnight": {"name": "蓝骑士", "hp": 100, "atk": 120, "def": 0, "money": 9, "experience": 0, "special": 8}, - "goldSlime": {"name": "黄头怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "poisonSkeleton": {"name": "紫骷髅", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "poisonBat": {"name": "紫蝙蝠", "hp": 100, "atk": 120, "def": 0, "money": 14, "experience": 0, "special": 13}, - "steelRock": {"name": "铁面人", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "skeletonPriest": {"name": "骷髅法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "skeletonKing": {"name": "骷髅王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "skeletonWizard": {"name": "骷髅巫师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "redSkeletonCaption": {"name": "骷髅武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "special": 0}, - "badHero": {"name": "迷失勇者", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "demon": {"name": "魔神武士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "demonPriest": {"name": "魔神法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "goldHornSlime": {"name": "金角怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "redKing": {"name": "红衣魔王", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "whiteKing": {"name": "白衣武士", "hp": 100, "atk": 120, "def": 0, "money": 17, "experience": 0, "special": 16}, - "blackMagician": {"name": "黑暗大法师", "hp": 100, "atk": 120, "def": 0, "money": 12, "experience": 0, "special": 11, "value": 1/3, "bomb": false}, // 吸血怪需要在后面添加value代表吸血比例 - "silverSlime": {"name": "银头怪", "hp": 100, "atk": 120, "def": 0, "money": 15, "experience": 0, "special": 14}, - "swordEmperor": {"name": "剑圣", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "whiteHornSlime": {"name": "尖角怪", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "badPrincess": {"name": "痛苦魔女", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "badFairy": {"name": "黑暗仙子", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "grayPriest": {"name": "中级法师", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "redSwordsman": {"name": "剑王", "hp": 100, "atk": 120, "def": 0, "money": 7, "experience": 0, "special": 6}, - "whiteGhost": {"name": "水银战士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "poisonZombie": {"name": "绿兽人", "hp": 100, "atk": 120, "def": 0, "money": 13, "experience": 0, "special": 12}, - "magicDragon": {"name": "魔龙", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "octopus": {"name": "血影", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "darkFairy": {"name": "仙子", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, - "greenKnight": {"name": "强盾骑士", "hp": 0, "atk": 0, "def": 0, "money": 0, "experience": 0, "special": 0}, + 'greenSlime': {'name': '绿头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 1, 'experience': 1, 'special': [1,5,7,8]}, + 'redSlime': {'name': '红头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'blackSlime': {'name': '青头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'slimelord': {'name': '怪王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'special': [1,9]}, + 'bat': {'name': '小蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 2, 'experience': 0, 'special': 1}, + 'bigBat': {'name': '大蝙蝠', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'redBat': {'name': '红蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 5, 'experience': 0, 'special': 4}, + 'vampire': {'name': '冥灵魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'skeleton': {'name': '骷髅人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'skeletonSoilder': {'name': '骷髅士兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'skeletonCaptain': {'name': '骷髅队长', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'ghostSkeleton': {'name': '冥队长', 'hp': 100, 'atk': 120, 'def': 0, 'money': 8, 'experience': 0, 'special': 7}, + 'zombie': {'name': '兽人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'zombieKnight': {'name': '兽人武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'rock': {'name': '石头人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 4, 'experience': 0, 'special': 3}, + 'slimeMan': {'name': '影子战士', 'hp': 100, 'atk': 0, 'def': 0, 'money': 11, 'experience': 0, 'special': 10}, // 模仿怪的攻防设为0就好 + 'bluePriest': {'name': '初级法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 3, 'experience': 0, 'special': 2}, + 'redPriest': {'name': '高级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'brownWizard': {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, 'zoneSquare': true}, // 领域怪需要加value表示领域伤害的数值;zoneSquare代表是否九宫格伤害 + 'redWizard': {'name': '高级巫师', 'hp': 1000, 'atk': 1200, 'def': 0, 'money': 160, 'experience': 0, 'special': 15, 'value': 200, 'range': 2}, // range可选,代表领域伤害的范围;不加默认为1 + 'yellowGuard': {'name': '初级卫兵', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'special': 0}, + 'blueGuard': {'name': '中级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'redGuard': {'name': '高级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'swordsman': {'name': '双手剑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 6, 'experience': 0, 'special': 5}, + 'soldier': {'name': '冥战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'yellowKnight': {'name': '金骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'redKnight': {'name': '红骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'darkKnight': {'name': '黑骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'blackKing': {'name': '黑衣魔王', 'hp': 1000, 'atk': 500, 'def': 0, 'money': 1000, 'experience': 1000, 'special': 0, 'bomb': false}, // 加入 'bomb': false 代表该怪物不可被炸弹或圣锤炸掉 + 'yellowKing': {'name': '黄衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'greenKing': {'name': '青衣武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'blueKnight': {'name': '蓝骑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 9, 'experience': 0, 'special': 8}, + 'goldSlime': {'name': '黄头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'poisonSkeleton': {'name': '紫骷髅', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'poisonBat': {'name': '紫蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 14, 'experience': 0, 'special': 13}, + 'steelRock': {'name': '铁面人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'skeletonPriest': {'name': '骷髅法师', 'hp': 100, 'atk': 100, 'def': 0, 'money': 0, 'experience': 0, 'special': 18, 'value': 20}, + 'skeletonKing': {'name': '骷髅王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'skeletonWizard': {'name': '骷髅巫师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'redSkeletonCaption': {'name': '骷髅武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'special': 0}, + 'badHero': {'name': '迷失勇者', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'demon': {'name': '魔神武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'demonPriest': {'name': '魔神法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'goldHornSlime': {'name': '金角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'redKing': {'name': '红衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'whiteKing': {'name': '白衣武士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 17, 'experience': 0, 'special': 16}, + 'blackMagician': {'name': '黑暗大法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 12, 'experience': 0, 'special': 11, 'value': 1/3, 'bomb': false}, // 吸血怪需要在后面添加value代表吸血比例 + 'silverSlime': {'name': '银头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 15, 'experience': 0, 'special': 14}, + 'swordEmperor': {'name': '剑圣', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'whiteHornSlime': {'name': '尖角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'badPrincess': {'name': '痛苦魔女', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'badFairy': {'name': '黑暗仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'grayPriest': {'name': '中级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'redSwordsman': {'name': '剑王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 7, 'experience': 0, 'special': 6, 'n': 8}, // 多连击需要在后面指定n代表是几连击 + 'whiteGhost': {'name': '水银战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'poisonZombie': {'name': '绿兽人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 13, 'experience': 0, 'special': 12}, + 'magicDragon': {'name': '魔龙', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'octopus': {'name': '血影', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'darkFairy': {'name': '仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'greenKnight': {'name': '强盾骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, } \ No newline at end of file diff --git a/libs/project/items.js b/libs/project/items.js index a181532d..c42662bd 100644 --- a/libs/project/items.js +++ b/libs/project/items.js @@ -34,7 +34,7 @@ items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a = 'fly': {'cls': 'constants', 'name': '楼层传送器', 'text': '可以自由往来去过的楼层'}, 'coin': {'cls': 'constants', 'name': '幸运金币', 'text': '持有时打败怪物可得双倍金币'}, 'snow': {'cls': 'constants', 'name': '冰冻徽章', 'text': '可以将四周的熔岩变成平地'}, - 'cross': {'cls': 'constants', 'name': '十字架', 'text': '该道具尚未被定义'}, + 'cross': {'cls': 'constants', 'name': '十字架', 'text': '持有后无视怪物的无敌属性'}, 'knife': {'cls': 'constants', 'name': '屠龙匕首', 'text': '该道具尚未被定义'}, 'shoes': {'cls': 'constants', 'name': '绿鞋', 'text': '持有时无视负面地形'}, diff --git a/libs/project/maps.js b/libs/project/maps.js index 30ef090a..0865925e 100644 --- a/libs/project/maps.js +++ b/libs/project/maps.js @@ -3,191 +3,190 @@ maps_90f36752_8815_4be8_b32b_d7fad1d0542e = ////////////////////////// 地形部分 ////////////////////////// // 0-20 地形 - "1":{"cls": "terrains", "id": "yellowWall"}, // 黄墙 - "2":{"cls": "terrains", "id": "whiteWall"}, // 白墙 - "3":{"cls": "terrains", "id": "blueWall"}, // 白墙 - "4":{"cls": "animates", "id": "star", "noPass": true}, // 星空 - "5":{"cls": "animates", "id": "lava", "noPass": true}, // 岩浆 - "6":{"cls": "terrains", "id": "ice"}, // 岩浆 - "7":{"cls": "terrains", "id": "blueShop-left"}, // 蓝色商店左 - "8":{"cls": "terrains", "id": "blueShop-right"}, // 蓝色商店右 - "9":{"cls": "terrains", "id": "pinkShop-left"}, // 粉色商店左 - "10":{"cls": "terrains", "id": "pinkShop-right"}, // 粉色商店左 - "11":{"cls": "animates", "id": "lavaNet", "noPass": false, "trigger": "passNet"}, // 血网 - "12":{"cls": "animates", "id": "poisonNet", "noPass": false, "trigger": "passNet"}, // 毒网 - "13":{"cls": "animates", "id": "weakNet", "noPass": false, "trigger": "passNet"}, // 衰网 - "14":{"cls": "animates", "id": "curseNet", "noPass": false, "trigger": "passNet"}, // 咒网 - "15":{"cls": "animates", "id": "water", "noPass": true}, // 水 + '1':{'cls': 'terrains', 'id': 'yellowWall'}, // 黄墙 + '2':{'cls': 'terrains', 'id': 'whiteWall'}, // 白墙 + '3':{'cls': 'terrains', 'id': 'blueWall'}, // 白墙 + '4':{'cls': 'animates', 'id': 'star', 'noPass': true}, // 星空 + '5':{'cls': 'animates', 'id': 'lava', 'noPass': true}, // 岩浆 + '6':{'cls': 'terrains', 'id': 'ice'}, // 岩浆 + '7':{'cls': 'terrains', 'id': 'blueShop-left'}, // 蓝色商店左 + '8':{'cls': 'terrains', 'id': 'blueShop-right'}, // 蓝色商店右 + '9':{'cls': 'terrains', 'id': 'pinkShop-left'}, // 粉色商店左 + '10':{'cls': 'terrains', 'id': 'pinkShop-right'}, // 粉色商店左 + '11':{'cls': 'animates', 'id': 'lavaNet', 'noPass': false, 'trigger': 'passNet'}, // 血网 + '12':{'cls': 'animates', 'id': 'poisonNet', 'noPass': false, 'trigger': 'passNet'}, // 毒网 + '13':{'cls': 'animates', 'id': 'weakNet', 'noPass': false, 'trigger': 'passNet'}, // 衰网 + '14':{'cls': 'animates', 'id': 'curseNet', 'noPass': false, 'trigger': 'passNet'}, // 咒网 + '15':{'cls': 'animates', 'id': 'water', 'noPass': true}, // 水 // 在这里添加更多地形 - // 如果空地不足,可以从180以后开始继续放,只要不和现有的数字冲突即可 + // 如果空位不足,可以从180以后开始继续放,只要不和现有的数字冲突即可 // Autotile - "20":{"cls": "autotile", "id": "autotile", "noPass": true}, // autotile - // 更多的autotile从151到160,只要不和现有的数字冲突即可 - "151":{"cls": "autotile", "id": "autotile1", "noPass": true}, - "152":{"cls": "autotile", "id": "autotile2", "noPass": true}, - "153":{"cls": "autotile", "id": "autotile3", "noPass": true}, - + '20':{'cls': 'autotile', 'id': 'autotile', 'noPass': true}, // autotile + // 更多的autotile从151到160等,只要不和现有的数字冲突即可 + '151':{'cls': 'autotile', 'id': 'autotile1', 'noPass': true}, + '152':{'cls': 'autotile', 'id': 'autotile2', 'noPass': true}, + '153':{'cls': 'autotile', 'id': 'autotile3', 'noPass': true}, ////////////////////////// 物品部分 ////////////////////////// // 21-80 物品 - "21":{"cls": "items", "id": "yellowKey"}, // 黄钥匙 - "22":{"cls": "items", "id": "blueKey"}, // 蓝钥匙 - "23":{"cls": "items", "id": "redKey"}, // 红钥匙 - "24":{"cls": "items", "id": "greenKey"}, // 绿钥匙 - "25":{"cls": "items", "id": "steelKey"}, // 铁门钥匙 - "26":{"cls": "items", "id": "bigKey"}, // 大黄门钥匙(钥匙盒) - "27":{"cls": "items", "id": "redJewel"}, // 红宝石 - "28":{"cls": "items", "id": "blueJewel"}, // 蓝宝石 - "29":{"cls": "items", "id": "greenJewel"}, // 绿宝石 - "30":{"cls": "items", "id": "yellowJewel"}, // 黄宝石 - "31":{"cls": "items", "id": "redPotion"}, // 红血瓶 - "32":{"cls": "items", "id": "bluePotion"}, // 蓝血瓶 - "33":{"cls": "items", "id": "greenPotion"}, // 绿血瓶 - "34":{"cls": "items", "id": "yellowPotion"}, // 黄血瓶 - "35":{"cls": "items", "id": "sword1"}, // 铁剑 - "36":{"cls": "items", "id": "shield1"}, // 铁盾 - "37":{"cls": "items", "id": "sword2"}, // 银剑 - "38":{"cls": "items", "id": "shield2"}, // 银盾 - "39":{"cls": "items", "id": "sword3"}, // 骑士剑 - "40":{"cls": "items", "id": "shield3"}, // 骑士盾 - "41":{"cls": "items", "id": "sword4"}, // 圣剑 - "42":{"cls": "items", "id": "shield4"}, // 圣盾 - "43":{"cls": "items", "id": "sword5"}, // 神圣剑 - "44":{"cls": "items", "id": "shield5"}, // 神圣盾 - "45":{"cls": "items", "id": "book"}, // 怪物手册 - "46":{"cls": "items", "id": "fly"}, // 楼层传送器 - "47":{"cls": "items", "id": "pickaxe"}, // 破墙镐 - "48":{"cls": "items", "id": "icePickaxe"}, // 破冰镐 - "49":{"cls": "items", "id": "bomb"}, // 炸弹 - "50":{"cls": "items", "id": "centerFly"}, // 中心对称 - "51":{"cls": "items", "id": "upFly"}, // 上楼器 - "52":{"cls": "items", "id": "downFly"}, // 下楼器 - "53":{"cls": "items", "id": "coin"}, // 幸运金币 - "54":{"cls": "items", "id": "snow"}, // 冰冻徽章 - "55":{"cls": "items", "id": "cross"}, // 十字架 - "56":{"cls": "items", "id": "superPotion"}, // 圣水 - "57":{"cls": "items", "id": "earthquake"}, // 地震卷轴 - "58":{"cls": "items", "id": "poisonWine"}, // 解毒药水 - "59":{"cls": "items", "id": "weakWine"}, // 解衰药水 - "60":{"cls": "items", "id": "curseWine"}, // 解咒药水 - "61":{"cls": "items", "id": "superWine"}, // 万能药水 - "62":{"cls": "items", "id": "knife"}, // 屠龙匕首 - "63":{"cls": "items", "id": "moneyPocket"}, // 金钱袋 - "64":{"cls": "items", "id": "shoes"}, // 绿鞋 - "65":{"cls": "items", "id": "hammer"}, // 圣锤 + '21':{'cls': 'items', 'id': 'yellowKey'}, // 黄钥匙 + '22':{'cls': 'items', 'id': 'blueKey'}, // 蓝钥匙 + '23':{'cls': 'items', 'id': 'redKey'}, // 红钥匙 + '24':{'cls': 'items', 'id': 'greenKey'}, // 绿钥匙 + '25':{'cls': 'items', 'id': 'steelKey'}, // 铁门钥匙 + '26':{'cls': 'items', 'id': 'bigKey'}, // 大黄门钥匙(钥匙盒) + '27':{'cls': 'items', 'id': 'redJewel'}, // 红宝石 + '28':{'cls': 'items', 'id': 'blueJewel'}, // 蓝宝石 + '29':{'cls': 'items', 'id': 'greenJewel'}, // 绿宝石 + '30':{'cls': 'items', 'id': 'yellowJewel'}, // 黄宝石 + '31':{'cls': 'items', 'id': 'redPotion'}, // 红血瓶 + '32':{'cls': 'items', 'id': 'bluePotion'}, // 蓝血瓶 + '33':{'cls': 'items', 'id': 'greenPotion'}, // 绿血瓶 + '34':{'cls': 'items', 'id': 'yellowPotion'}, // 黄血瓶 + '35':{'cls': 'items', 'id': 'sword1'}, // 铁剑 + '36':{'cls': 'items', 'id': 'shield1'}, // 铁盾 + '37':{'cls': 'items', 'id': 'sword2'}, // 银剑 + '38':{'cls': 'items', 'id': 'shield2'}, // 银盾 + '39':{'cls': 'items', 'id': 'sword3'}, // 骑士剑 + '40':{'cls': 'items', 'id': 'shield3'}, // 骑士盾 + '41':{'cls': 'items', 'id': 'sword4'}, // 圣剑 + '42':{'cls': 'items', 'id': 'shield4'}, // 圣盾 + '43':{'cls': 'items', 'id': 'sword5'}, // 神圣剑 + '44':{'cls': 'items', 'id': 'shield5'}, // 神圣盾 + '45':{'cls': 'items', 'id': 'book'}, // 怪物手册 + '46':{'cls': 'items', 'id': 'fly'}, // 楼层传送器 + '47':{'cls': 'items', 'id': 'pickaxe'}, // 破墙镐 + '48':{'cls': 'items', 'id': 'icePickaxe'}, // 破冰镐 + '49':{'cls': 'items', 'id': 'bomb'}, // 炸弹 + '50':{'cls': 'items', 'id': 'centerFly'}, // 中心对称 + '51':{'cls': 'items', 'id': 'upFly'}, // 上楼器 + '52':{'cls': 'items', 'id': 'downFly'}, // 下楼器 + '53':{'cls': 'items', 'id': 'coin'}, // 幸运金币 + '54':{'cls': 'items', 'id': 'snow'}, // 冰冻徽章 + '55':{'cls': 'items', 'id': 'cross'}, // 十字架 + '56':{'cls': 'items', 'id': 'superPotion'}, // 圣水 + '57':{'cls': 'items', 'id': 'earthquake'}, // 地震卷轴 + '58':{'cls': 'items', 'id': 'poisonWine'}, // 解毒药水 + '59':{'cls': 'items', 'id': 'weakWine'}, // 解衰药水 + '60':{'cls': 'items', 'id': 'curseWine'}, // 解咒药水 + '61':{'cls': 'items', 'id': 'superWine'}, // 万能药水 + '62':{'cls': 'items', 'id': 'knife'}, // 屠龙匕首 + '63':{'cls': 'items', 'id': 'moneyPocket'}, // 金钱袋 + '64':{'cls': 'items', 'id': 'shoes'}, // 绿鞋 + '65':{'cls': 'items', 'id': 'hammer'}, // 圣锤 ////////////////////////// 门、楼梯、传送点部分 ////////////////////////// // 81-100 门 - "81":{"cls": "terrains", "id": "yellowDoor", "trigger": "openDoor"}, // 黄门 - "82":{"cls": "terrains", "id": "blueDoor", "trigger": "openDoor"}, // 蓝门 - "83":{"cls": "terrains", "id": "redDoor", "trigger": "openDoor"}, // 红门 - "84":{"cls": "terrains", "id": "greenDoor", "trigger": "openDoor"}, // 绿门 - "85":{"cls": "terrains", "id": "specialDoor", "trigger": "openDoor"}, // 机关门左 - "86":{"cls": "terrains", "id": "steelDoor", "trigger": "openDoor"}, // 铁门 - "87":{"cls": "terrains", "id": "upFloor", "noPass": false}, // 上楼梯 - "88":{"cls": "terrains", "id": "downFloor", "noPass": false}, // 下楼梯 - "89":{"cls": "animates", "id": "portal", "noPass": false}, // 传送门 - "90":{"cls": "animates", "id": "starPortal", "noPass": false}, // 星空传送门 - "91":{"cls": "animates", "id": "upPortal", "noPass": false}, // 上箭头 - "92":{"cls": "animates", "id": "leftPortal", "noPass": false}, // 左箭头 - "93":{"cls": "animates", "id": "downPortal", "noPass": false}, // 下箭头 - "94":{"cls": "animates", "id": "rightPortal", "noPass": false}, // 右箭头 + '81':{'cls': 'terrains', 'id': 'yellowDoor', 'trigger': 'openDoor'}, // 黄门 + '82':{'cls': 'terrains', 'id': 'blueDoor', 'trigger': 'openDoor'}, // 蓝门 + '83':{'cls': 'terrains', 'id': 'redDoor', 'trigger': 'openDoor'}, // 红门 + '84':{'cls': 'terrains', 'id': 'greenDoor', 'trigger': 'openDoor'}, // 绿门 + '85':{'cls': 'terrains', 'id': 'specialDoor', 'trigger': 'openDoor'}, // 机关门左 + '86':{'cls': 'terrains', 'id': 'steelDoor', 'trigger': 'openDoor'}, // 铁门 + '87':{'cls': 'terrains', 'id': 'upFloor', 'noPass': false}, // 上楼梯 + '88':{'cls': 'terrains', 'id': 'downFloor', 'noPass': false}, // 下楼梯 + '89':{'cls': 'animates', 'id': 'portal', 'noPass': false}, // 传送门 + '90':{'cls': 'animates', 'id': 'starPortal', 'noPass': false}, // 星空传送门 + '91':{'cls': 'animates', 'id': 'upPortal', 'noPass': false}, // 上箭头 + '92':{'cls': 'animates', 'id': 'leftPortal', 'noPass': false}, // 左箭头 + '93':{'cls': 'animates', 'id': 'downPortal', 'noPass': false}, // 下箭头 + '94':{'cls': 'animates', 'id': 'rightPortal', 'noPass': false}, // 右箭头 ////////////////////////// NPC部分 ////////////////////////// // 121-150 NPC - "121":{"cls": "npcs", "id": "man"}, - "122":{"cls": "npcs", "id": "woman"}, - "123":{"cls": "npcs", "id": "thief"}, - "124":{"cls": "npcs", "id": "fairy"}, - "125":{"cls": "npcs", "id": "magician"}, - "126":{"cls": "npcs", "id": "womanMagician"}, - "127":{"cls": "npcs", "id": "oldMan"}, - "128":{"cls": "npcs", "id": "child"}, - "129":{"cls": "npcs", "id": "wood"}, - "130":{"cls": "npcs", "id": "pinkShop"}, - "131":{"cls": "npcs", "id": "blueShop"}, - "132":{"cls": "npcs", "id": "princess"}, + '121':{'cls': 'npcs', 'id': 'man'}, + '122':{'cls': 'npcs', 'id': 'woman'}, + '123':{'cls': 'npcs', 'id': 'thief'}, + '124':{'cls': 'npcs', 'id': 'fairy'}, + '125':{'cls': 'npcs', 'id': 'magician'}, + '126':{'cls': 'npcs', 'id': 'womanMagician'}, + '127':{'cls': 'npcs', 'id': 'oldMan'}, + '128':{'cls': 'npcs', 'id': 'child'}, + '129':{'cls': 'npcs', 'id': 'wood'}, + '130':{'cls': 'npcs', 'id': 'pinkShop'}, + '131':{'cls': 'npcs', 'id': 'blueShop'}, + '132':{'cls': 'npcs', 'id': 'princess'}, ////////////////////////// 其他部分 ////////////////////////// // 161-200 其他(单向箭头、灯、箱子等等) - "161":{"cls": "terrains", "id": "arrowUp", "noPass": false}, // 单向上箭头 - "162":{"cls": "terrains", "id": "arrowDown", "noPass": false}, // 单向下箭头 - "163":{"cls": "terrains", "id": "arrowLeft", "noPass": false}, // 单向左箭头 - "164":{"cls": "terrains", "id": "arrowRight", "noPass": false}, // 单向右箭头 - "165":{"cls": "terrains", "id": "light", "trigger": "changeLight", "noPass": false}, // 灯 - "166":{"cls": "terrains", "id": "darkLight", "noPass": true}, // 暗灯 + '161':{'cls': 'terrains', 'id': 'arrowUp', 'noPass': false}, // 单向上箭头 + '162':{'cls': 'terrains', 'id': 'arrowDown', 'noPass': false}, // 单向下箭头 + '163':{'cls': 'terrains', 'id': 'arrowLeft', 'noPass': false}, // 单向左箭头 + '164':{'cls': 'terrains', 'id': 'arrowRight', 'noPass': false}, // 单向右箭头 + '165':{'cls': 'terrains', 'id': 'light', 'trigger': 'changeLight', 'noPass': false}, // 灯 + '166':{'cls': 'terrains', 'id': 'darkLight', 'noPass': true}, // 暗灯 ////////////////////////// 怪物部分 ////////////////////////// // 201-300 怪物 - "201":{"cls": "enemys", "id": "greenSlime"}, - "202":{"cls": "enemys", "id": "redSlime"}, - "203":{"cls": "enemys", "id": "blackSlime"}, - "204":{"cls": "enemys", "id": "slimelord"}, - "205":{"cls": "enemys", "id": "bat"}, - "206":{"cls": "enemys", "id": "bigBat"}, - "207":{"cls": "enemys", "id": "redBat"}, - "208":{"cls": "enemys", "id": "vampire"}, - "209":{"cls": "enemys", "id": "skeleton"}, - "210":{"cls": "enemys", "id": "skeletonSoilder"}, - "211":{"cls": "enemys", "id": "skeletonCaptain"}, - "212":{"cls": "enemys", "id": "ghostSkeleton"}, - "213":{"cls": "enemys", "id": "zombie"}, - "214":{"cls": "enemys", "id": "zombieKnight"}, - "215":{"cls": "enemys", "id": "rock"}, - "216":{"cls": "enemys", "id": "slimeMan"}, - "217":{"cls": "enemys", "id": "bluePriest"}, - "218":{"cls": "enemys", "id": "redPriest"}, - "219":{"cls": "enemys", "id": "brownWizard"}, - "220":{"cls": "enemys", "id": "redWizard"}, - "221":{"cls": "enemys", "id": "yellowGuard"}, - "222":{"cls": "enemys", "id": "blueGuard"}, - "223":{"cls": "enemys", "id": "redGuard"}, - "224":{"cls": "enemys", "id": "swordsman"}, - "225":{"cls": "enemys", "id": "soldier"}, - "226":{"cls": "enemys", "id": "yellowKnight"}, - "227":{"cls": "enemys", "id": "redKnight"}, - "228":{"cls": "enemys", "id": "darkKnight"}, - "229":{"cls": "enemys", "id": "blackKing"}, - "230":{"cls": "enemys", "id": "yellowKing"}, - "231":{"cls": "enemys", "id": "greenKing"}, - "232":{"cls": "enemys", "id": "blueKnight"}, - "233":{"cls": "enemys", "id": "goldSlime"}, - "234":{"cls": "enemys", "id": "poisonSkeleton"}, - "235":{"cls": "enemys", "id": "poisonBat"}, - "236":{"cls": "enemys", "id": "steelRock"}, - "237":{"cls": "enemys", "id": "skeletonPriest"}, - "238":{"cls": "enemys", "id": "skeletonKing"}, - "239":{"cls": "enemys", "id": "skeletonWizard"}, - "240":{"cls": "enemys", "id": "redSkeletonCaption"}, - "241":{"cls": "enemys", "id": "badHero"}, - "242":{"cls": "enemys", "id": "demon"}, - "243":{"cls": "enemys", "id": "demonPriest"}, - "244":{"cls": "enemys", "id": "goldHornSlime"}, - "245":{"cls": "enemys", "id": "redKing"}, - "246":{"cls": "enemys", "id": "whiteKing"}, - "247":{"cls": "enemys", "id": "blackMagician"}, - "248":{"cls": "enemys", "id": "silverSlime"}, - "249":{"cls": "enemys", "id": "swordEmperor"}, - "250":{"cls": "enemys", "id": "whiteHornSlime"}, - "251":{"cls": "enemys", "id": "badPrincess"}, - "252":{"cls": "enemys", "id": "badFairy"}, - "253":{"cls": "enemys", "id": "grayPriest"}, - "254":{"cls": "enemys", "id": "redSwordsman"}, - "255":{"cls": "enemys", "id": "whiteGhost"}, - "256":{"cls": "enemys", "id": "poisonZombie"}, - "257":{"cls": "enemys", "id": "magicDragon"}, - "258":{"cls": "enemys", "id": "octopus"}, - "259":{"cls": "enemys", "id": "darkFairy"}, - "260":{"cls": "enemys", "id": "greenKnight"}, + '201':{'cls': 'enemys', 'id': 'greenSlime'}, + '202':{'cls': 'enemys', 'id': 'redSlime'}, + '203':{'cls': 'enemys', 'id': 'blackSlime'}, + '204':{'cls': 'enemys', 'id': 'slimelord'}, + '205':{'cls': 'enemys', 'id': 'bat'}, + '206':{'cls': 'enemys', 'id': 'bigBat'}, + '207':{'cls': 'enemys', 'id': 'redBat'}, + '208':{'cls': 'enemys', 'id': 'vampire'}, + '209':{'cls': 'enemys', 'id': 'skeleton'}, + '210':{'cls': 'enemys', 'id': 'skeletonSoilder'}, + '211':{'cls': 'enemys', 'id': 'skeletonCaptain'}, + '212':{'cls': 'enemys', 'id': 'ghostSkeleton'}, + '213':{'cls': 'enemys', 'id': 'zombie'}, + '214':{'cls': 'enemys', 'id': 'zombieKnight'}, + '215':{'cls': 'enemys', 'id': 'rock'}, + '216':{'cls': 'enemys', 'id': 'slimeMan'}, + '217':{'cls': 'enemys', 'id': 'bluePriest'}, + '218':{'cls': 'enemys', 'id': 'redPriest'}, + '219':{'cls': 'enemys', 'id': 'brownWizard'}, + '220':{'cls': 'enemys', 'id': 'redWizard'}, + '221':{'cls': 'enemys', 'id': 'yellowGuard'}, + '222':{'cls': 'enemys', 'id': 'blueGuard'}, + '223':{'cls': 'enemys', 'id': 'redGuard'}, + '224':{'cls': 'enemys', 'id': 'swordsman'}, + '225':{'cls': 'enemys', 'id': 'soldier'}, + '226':{'cls': 'enemys', 'id': 'yellowKnight'}, + '227':{'cls': 'enemys', 'id': 'redKnight'}, + '228':{'cls': 'enemys', 'id': 'darkKnight'}, + '229':{'cls': 'enemys', 'id': 'blackKing'}, + '230':{'cls': 'enemys', 'id': 'yellowKing'}, + '231':{'cls': 'enemys', 'id': 'greenKing'}, + '232':{'cls': 'enemys', 'id': 'blueKnight'}, + '233':{'cls': 'enemys', 'id': 'goldSlime'}, + '234':{'cls': 'enemys', 'id': 'poisonSkeleton'}, + '235':{'cls': 'enemys', 'id': 'poisonBat'}, + '236':{'cls': 'enemys', 'id': 'steelRock'}, + '237':{'cls': 'enemys', 'id': 'skeletonPriest'}, + '238':{'cls': 'enemys', 'id': 'skeletonKing'}, + '239':{'cls': 'enemys', 'id': 'skeletonWizard'}, + '240':{'cls': 'enemys', 'id': 'redSkeletonCaption'}, + '241':{'cls': 'enemys', 'id': 'badHero'}, + '242':{'cls': 'enemys', 'id': 'demon'}, + '243':{'cls': 'enemys', 'id': 'demonPriest'}, + '244':{'cls': 'enemys', 'id': 'goldHornSlime'}, + '245':{'cls': 'enemys', 'id': 'redKing'}, + '246':{'cls': 'enemys', 'id': 'whiteKing'}, + '247':{'cls': 'enemys', 'id': 'blackMagician'}, + '248':{'cls': 'enemys', 'id': 'silverSlime'}, + '249':{'cls': 'enemys', 'id': 'swordEmperor'}, + '250':{'cls': 'enemys', 'id': 'whiteHornSlime'}, + '251':{'cls': 'enemys', 'id': 'badPrincess'}, + '252':{'cls': 'enemys', 'id': 'badFairy'}, + '253':{'cls': 'enemys', 'id': 'grayPriest'}, + '254':{'cls': 'enemys', 'id': 'redSwordsman'}, + '255':{'cls': 'enemys', 'id': 'whiteGhost'}, + '256':{'cls': 'enemys', 'id': 'poisonZombie'}, + '257':{'cls': 'enemys', 'id': 'magicDragon'}, + '258':{'cls': 'enemys', 'id': 'octopus'}, + '259':{'cls': 'enemys', 'id': 'darkFairy'}, + '260':{'cls': 'enemys', 'id': 'greenKnight'}, ////////////////////////// 待定... ////////////////////////// // 目前ID暂时不要超过400 From fb7749a67eb3c0eeced7ae1c8c52975984e1fb6c Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sun, 31 Dec 2017 10:54:11 +0800 Subject: [PATCH 008/102] fix bug --- drawMapGUI.html | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drawMapGUI.html b/drawMapGUI.html index 78373784..5505e776 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -438,8 +438,8 @@ editor.prototype.init = function(){ var p1 = editor.loadjs(mapsjsUrl).then(function(){ // 加载maps.js var maps_ = new maps(); //实例化maps - maps.init(); - return maps + maps_.init(); + return maps_ }); var p2 = editor.loadjs(iconsjsUrl) // 加载icons.js .then(function(){ // 实例化并获取icons From ba7bbbc7bec041acdc2a5b2b3a4b5306e0aaafb8 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sun, 31 Dec 2017 12:15:19 +0800 Subject: [PATCH 009/102] editor: import main.js MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 目前状态是都能工作,需要重写editor的方法 --- drawMapGUI.html | 160 +++++++++++++++++++++++++++++++++------ libs/core.js | 14 ++-- main.js | 2 +- test_main_init_mode.html | 150 ++++++++++++++++++++++++++++++++++++ 4 files changed, 294 insertions(+), 32 deletions(-) create mode 100644 test_main_init_mode.html diff --git a/drawMapGUI.html b/drawMapGUI.html index 5505e776..0f0c0ba7 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -328,8 +328,8 @@
- - + +
@@ -362,13 +362,111 @@
+ + + + + + + \ No newline at end of file From 5438001ea07cfd69e9a4703021c631476b31ff21 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sun, 31 Dec 2017 15:29:44 +0800 Subject: [PATCH 010/102] editor: import main.js MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 画图部分完美结合 --- drawMapGUI.html | 27 ++++++++++++++++------ libs/core.js | 20 ++++++++++++----- libs/maps.js | 60 ++++++++++++++++++++++++++++--------------------- 3 files changed, 68 insertions(+), 39 deletions(-) diff --git a/drawMapGUI.html b/drawMapGUI.html index 0f0c0ba7..c50086f8 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -520,7 +520,7 @@ function editor() { this.material = {}; } // 重构这一堆回调 -editor.prototype.init = function(){ +editor.prototype.init = function(callback){ var mapsdatajsUrl = 'libs/project/maps.js'; var iconsdatajsUrl = 'libs/project/icons.js'; var mapsjsUrl = 'libs/maps.js'; @@ -558,6 +558,7 @@ editor.prototype.init = function(){ editor.idsInit(maps, icons); // 初始化图片素材信息 editor.drawInitData(icons); // 初始化绘图 editor.listen(); // 开始监听事件 + if(Boolean(callback))callback(); }) }); @@ -719,6 +720,10 @@ editor.prototype.mapInit = function(){ } editor.prototype.drawMapBg = function(){ var bgc = bg.getContext('2d'); + if (editor.bgY == 0){ + editor.main.editor.drawMapBg(); + return; + } for (var ii = 0; ii < 13; ii++) for (var jj = 0; jj < 13; jj++) { @@ -728,10 +733,13 @@ editor.prototype.drawMapBg = function(){ } editor.prototype.updateMap = function(){ + var blocks = main.editor.mapIntoBlocks(editor.map.map(function(v){return v.map(function(v){return v.idnum||v||0})}),{'events':{},'changeFloor':{},'defaultGround':null}); + core.status.thisMap.blocks = blocks; + main.editor.updateMap(); var drawTile = function(ctx, x, y, tileInfo){ // 绘制一个普通块 - ctx.clearRect(x*32, y*32, 32, 32); + //ctx.clearRect(x*32, y*32, 32, 32); if(tileInfo == 0) return; if(typeof(tileInfo) == typeof([][0]) || !hasOwnProp(tileInfo, 'idnum')) {//未定义块画红块 @@ -748,9 +756,9 @@ editor.prototype.updateMap = function(){ ctx.fillText("?", x*32+16, y*32+27); return; } - ctx.drawImage(editor.material.images[tileInfo.images], 0, tileInfo.y*32, 32, 32, x*32, y*32, 32, 32); + //ctx.drawImage(editor.material.images[tileInfo.images], 0, tileInfo.y*32, 32, 32, x*32, y*32, 32, 32); } - + /* // autotile的相关处理 var indexArrs = [ //16种组合的图块索引数组; // 将autotile分割成48块16*16的小块; 数组索引即对应各个小块 // +----+----+----+----+----+----+ @@ -835,13 +843,13 @@ editor.prototype.updateMap = function(){ drawBlockByIndex(ctx, dx, dy, editor.material.images[info.images][info.id], index); } } - + */ // 绘制地图 start var eventCtx = document.getElementById('event').getContext("2d"); for(var y=0; y<13; y++) for(var x=0; x<13; x++){ var tileInfo = editor.map[y][x]; - if(isAutotile(tileInfo)){ + if(false && isAutotile(tileInfo)){ addIndexToAutotileInfo(x, y); drawAutotile(eventCtx, x, y, tileInfo); }else drawTile(eventCtx, x, y, tileInfo); @@ -1060,14 +1068,19 @@ editor = new editor(); main.init('editor'); //main.listen(); var afterMainInit = function(){ + //main.editor.mapIntoBlocks(editor.map.map(function(v){return v.map(function(v){return v.idnum||v||0})}),{'events':{},'changeFloor':{},'defaultGround':null}); //main.editor.drawMapBg(); //main.editor.updateMap(); + main.instance={}; editor.main=main; editor.core=core; editor.fs=fs; editor.file=editor_file; - editor.init(); + + main.editor.disableGlobalAnimate=false; + //core.status.maps = core.clone(core.maps.initMaps(floorIds)); + editor.init(editor.updateMap); } var startgame = function(){ var hard = 'Hard'; diff --git a/libs/core.js b/libs/core.js index 02d53cab..67fcb80b 100644 --- a/libs/core.js +++ b/libs/core.js @@ -1997,19 +1997,21 @@ core.prototype.drawMap = function (mapName, callback) { } } } - drawBg(); if (main.mode=='editor'){ main.editor.drawMapBg = function(){ core.clearMap('bg', 0, 0, 416, 416); drawBg(); } + } else { + drawBg(); } + core.status.floorId = mapName; + core.status.thisMap = core.status.maps[mapName]; var drawEvent = function(){ - var mapData = core.status.maps[mapName]; + var mapData = core.status.maps[core.status.floorId]; var mapBlocks = mapData.blocks; - core.status.floorId = mapName; - core.status.thisMap = mapData; + var autotileMaps = []; for (var b = 0; b < mapBlocks.length; b++) { // 事件启用 @@ -2030,12 +2032,16 @@ core.prototype.drawMap = function (mapName, callback) { } core.drawAutotile(mapName, 'event', autotileMaps, 0, 0, 32); } - drawEvent(); + if (main.mode=='editor'){ main.editor.updateMap = function(){ + core.removeGlobalAnimate(null, null, true); core.clearMap('event', 0, 0, 416, 416); drawEvent(); + core.setGlobalAnimate(core.values.animateSpeed); } + } else { + drawEvent(); } core.setGlobalAnimate(core.values.animateSpeed); @@ -2467,11 +2473,13 @@ core.prototype.addGlobalAnimate = function (animateMore, x, y, loc, image) { ////// 删除一个或所有全局动画 ////// core.prototype.removeGlobalAnimate = function (x, y, all) { - if (main.mode=='editor' && main.editor.disableGlobalAnimate) return; if (all == true) { core.status.twoAnimateObjs = []; core.status.fourAnimateObjs = []; } + + if (main.mode=='editor' && main.editor.disableGlobalAnimate) return; + for (var t = 0; t < core.status.twoAnimateObjs.length; t++) { if (core.status.twoAnimateObjs[t].x == x * 32 && core.status.twoAnimateObjs[t].y == y * 32) { core.status.twoAnimateObjs.splice(t, 1); diff --git a/libs/maps.js b/libs/maps.js index 79a3e07e..45ad3349 100644 --- a/libs/maps.js +++ b/libs/maps.js @@ -13,38 +13,46 @@ maps.prototype.loadFloor = function (floorId, map) { content['title'] = floor.title; content['canFlyTo'] = floor.canFlyTo; if (!core.isset(map)) map=floor.map; - var blocks = []; - for (var i = 0; i < 13; i++) { - for (var j = 0; j < 13; j++) { - var block = this.getBlock(j, i, map[i][j]); - if (block.event != undefined) { - if (block.event.cls == 'enemys' && block.event.trigger==undefined) { - block.event.trigger = 'battle'; - } - if (block.event.cls == 'items' && block.event.trigger==undefined) { - block.event.trigger = 'getItem'; - } - if (block.event.noPass == undefined) { - if (block.event.cls=='enemys' || block.event.cls=='terrains' || block.event.cls=='npcs') { - block.event.noPass = true; - } - } - if (block.event.animate == undefined) { - if (block.event.cls=='enemys' || block.event.cls=='npcs') { - block.event.animate = 2; - } - if (block.event.cls == 'animates') { - block.event.animate = 4; + var mapIntoBlocks = function(map,maps,floor){ + var blocks = []; + for (var i = 0; i < 13; i++) { + for (var j = 0; j < 13; j++) { + var block = maps.getBlock(j, i, map[i][j]); + if (block.event != undefined) { + if (block.event.cls == 'enemys' && block.event.trigger==undefined) { + block.event.trigger = 'battle'; + } + if (block.event.cls == 'items' && block.event.trigger==undefined) { + block.event.trigger = 'getItem'; + } + if (block.event.noPass == undefined) { + if (block.event.cls=='enemys' || block.event.cls=='terrains' || block.event.cls=='npcs') { + block.event.noPass = true; + } + } + if (block.event.animate == undefined) { + if (block.event.cls=='enemys' || block.event.cls=='npcs') { + block.event.animate = 2; + } + if (block.event.cls == 'animates') { + block.event.animate = 4; + } } } + maps.addEvent(block,j,i,floor.events[j+","+i],floor.defaultGround || "ground") + maps.addChangeFloor(block,j,i,floor.changeFloor[j+","+i]); + if (core.isset(block.event)) blocks.push(block); } - this.addEvent(block,j,i,floor.events[j+","+i],floor.defaultGround || "ground") - this.addChangeFloor(block,j,i,floor.changeFloor[j+","+i]); - if (core.isset(block.event)) blocks.push(block); + } + return blocks; + } + if (main.mode=='editor'){ + main.editor.mapIntoBlocks = function(map,floor){ + return mapIntoBlocks(map,core.maps,floor); } } // 事件处理 - content['blocks'] = blocks; + content['blocks'] = mapIntoBlocks(map,this,floor); return content; } From 4f6bf850f8f9fc3c095e984d88b9c14f69a27850 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sun, 31 Dec 2017 15:49:03 +0800 Subject: [PATCH 011/102] editor: import main.js MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit editor完全使用core的数据 --- drawMapGUI.html | 123 +++++------------------------------------------- 1 file changed, 11 insertions(+), 112 deletions(-) diff --git a/drawMapGUI.html b/drawMapGUI.html index c50086f8..cd84aa5a 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -519,105 +519,19 @@ function editor() { this.version = "1.2"; this.material = {}; } -// 重构这一堆回调 + editor.prototype.init = function(callback){ - var mapsdatajsUrl = 'libs/project/maps.js'; - var iconsdatajsUrl = 'libs/project/icons.js'; - var mapsjsUrl = 'libs/maps.js'; - var iconsjsUrl = 'libs/icons.js'; - - var p1_data = editor.loadjs(mapsdatajsUrl).then(function(){ // 加载maps.js的数据 - return 'complete'; - }); - var p2_data = editor.loadjs(iconsdatajsUrl).then(function(){ // 加载icons.js的数据 - return 'complete'; - }); - - Promise.all([p1_data, p2_data]).then(function([p1_data, p2_data]){ - - var p1 = editor.loadjs(mapsjsUrl).then(function(){ // 加载maps.js - var maps_ = new maps(); //实例化maps - maps_.init(); - return maps_ - }); - var p2 = editor.loadjs(iconsjsUrl) // 加载icons.js - .then(function(){ // 实例化并获取icons - var ic = new icons(); - ic.init(); - return ic.getIcons(); - }); - var p3 = p2.then(function(icons){ // 加载所有图片 - return editor.loadAllImgs(icons); - }) - .catch(function(err){ - console.log('发生错误!', err); - }); - - Promise.all([p1, p2, p3]) - .then(function([maps, icons, img]){ - editor.idsInit(maps, icons); // 初始化图片素材信息 - editor.drawInitData(icons); // 初始化绘图 - editor.listen(); // 开始监听事件 - if(Boolean(callback))callback(); - }) - - }); + editor.main=main; + editor.core=core; + editor.fs=fs; + editor.file=editor_file; + editor.material.images=core.material.images; + editor.idsInit(core.maps, core.icons.icons); // 初始化图片素材信息 + editor.drawInitData(core.icons.icons); // 初始化绘图 + editor.listen(); // 开始监听事件 + if(Boolean(callback))callback(); } -editor.prototype.loadjs = function(url){ - return new Promise(function(resolve, reject){ - var script = document.createElement('script'); - script.src = url + '?' + editor.version; - document.body.appendChild(script); - script.onload = function () { - resolve( console.log(url+"加载完成")); - } - script.onerror = function(){ - reject(new Error('Load js error at '+url)) - } - }); -} -editor.prototype.loadImg = function(url){ - return new Promise(function(resolve, reject){ - var img = new Image(); - img.src = url; - img.onload = function(){ - resolve(img); - } - img.onerror = function(){ - reject(new Error('Load image error at '+url)); - } - }) -} - -editor.prototype.loadAllImgs = function(icons){ - editor.material.images = {}; - var imgs = Object.keys(icons); - var autotiles = null; - if(hasOwnProp(icons, 'hero')){ // hero 图片不加载 - var index = imgs.indexOf('hero'); - imgs.splice(index, 1); - } - if(hasOwnProp(icons, 'autotile')){ - editor.material.images['autotile'] = {}; - var index = imgs.indexOf('autotile'); - imgs.splice(index, 1); - autotiles = Object.keys(icons.autotile); - imgs = imgs.concat(autotiles); - } - var p = imgs.map(function(im){ - var url = 'images/'+im+'.png' - return editor.loadImg(url).then(function(image){ - if(autotiles.indexOf(im) >= 0){ - editor.material.images['autotile'][im] = image; - }else editor.material.images[im] = image; - }).catch(function(err){ - console.log('发生错误!', err); - }); - }); - - return Promise.all(p); -} editor.prototype.idsInit = function(maps, icons){ editor.ids = []; editor.indexs = []; @@ -1068,15 +982,6 @@ editor = new editor(); main.init('editor'); //main.listen(); var afterMainInit = function(){ - //main.editor.mapIntoBlocks(editor.map.map(function(v){return v.map(function(v){return v.idnum||v||0})}),{'events':{},'changeFloor':{},'defaultGround':null}); - //main.editor.drawMapBg(); - //main.editor.updateMap(); - - main.instance={}; - editor.main=main; - editor.core=core; - editor.fs=fs; - editor.file=editor_file; main.editor.disableGlobalAnimate=false; //core.status.maps = core.clone(core.maps.initMaps(floorIds)); @@ -1094,12 +999,6 @@ var startgame = function(){ setTimeout(startgame, 300); - + From 62b11fc3a0ab5e87dca34bc2d8a55e209bdb9e36 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Mon, 1 Jan 2018 02:07:55 +0800 Subject: [PATCH 012/102] Update editor_file.js --- _server/editor_file.js | 88 +++++++++++++++++++++++++++++++++++------- 1 file changed, 74 insertions(+), 14 deletions(-) diff --git a/_server/editor_file.js b/_server/editor_file.js index 99bd334f..8ce40c89 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -3,8 +3,8 @@ editor_file = {}; editor_file.getFloorFileList = function(editor,callback){ + if (!isset(callback)) throw('未设置callback'); var fs = editor.fs; - if (isset(callback)) fs.readdir('libs/project/floors',function(err, data){ callback([data,err]); }); @@ -12,12 +12,12 @@ //callback([Array,err:String]) editor_file.loadFloorFile = function(editor,filename,callback){ //filename不含'/'不含'.js' + if (!isset(callback)) throw('未设置callback'); var fs = editor.fs; - if (isset(callback)) fs.readFile('libs/project/floors/'+filename+'.js','utf-8',function(err, data){ if (err!=null){callback(err);return;} - data=data.split('=') - data=[data[0],data.slice(1).join('=')] + data=data.split('='); + data=[data[0],data.slice(1).join('=')]; var varnameId = data[0].split('.').slice(-1)[0].trim(); var filenameId = filename.split('/').slice(-1)[0].split('\\').slice(-1)[0]; eval('b3917d1d_71c2_41f2_a8aa_481b215ffb99='+data[1]); @@ -35,8 +35,9 @@ } //callback(err:String) editor_file.saveFloorFile = function(editor,callback){ + if (!isset(callback)) throw('未设置callback'); if (!isset(editor.currentFloorId) || !isset(editor.currentfloorData)) { - if (isset(callback)) callback('未选中文件或无数据'); + callback('未选中文件或无数据'); } var filename = 'libs/project/floors/' + editor.currentFloorId + '.js'; var datastr = ['main.floors.' , editor.currentFloorId , '=\n{']; @@ -50,14 +51,15 @@ datastr=datastr.concat(['\n}']); datastr=datastr.join(''); fs.writeFile(filename,datastr,'utf-8',function(err, data){ - if (isset(callback)) callback(err); + callback(err); }); } //callback(err:String) editor_file.saveFloorFileAs = function(editor,saveAsFilename,callback){ //saveAsFilename不含'/'不含'.js' + if (!isset(callback)) throw('未设置callback'); if (!isset(editor.currentfloorData)) { - if (isset(callback)) callback('无数据'); + callback('无数据'); } editor.currentfloorData.floorId=saveAsFilename; editor.currentFloorId=saveAsFilename; @@ -67,22 +69,77 @@ //////////////////////////////////////////////////////////////////// - editor_file.changeIdAndIdnum = function(editor,id,idnum,callback){ - if (isset(callback)) callback('尚未实现'); + editor_file.changeIdAndIdnum = function(editor,id,idnum,info,callback){ + if (!isset(callback)) throw('未设置callback'); + //检查maps中是否有重复的idnum或id + var change = -1; + for(var ii in core.maps.blocksInfo){ + if (ii==idnum) { + if (info.idnum==idnum){change=ii;break;}//修改id + callback('idnum重复了'); + return; + } + if (core.maps.blocksInfo[ii].id==id) { + if (info.id==id){change=ii;break;}//修改idnum + callback('id重复了'); + return; + } + } + if (change!=-1 && change!=idnum){//修改idnum + core.maps.blocksInfo[idnum] = core.maps.blocksInfo[change]; + delete(core.maps.blocksInfo[change]); + } else if (change==idnum) {//修改id + var oldid = core.maps.blocksInfo[idnum].id; + core.maps.blocksInfo[idnum].id = id; + for(var ii in core.icons.icons){ + if (ii.hasOwnProperty(oldid)){ + ii[id]=ii[oldid]; + delete(ii[oldid]); + } + } + } else {//创建新的 + core.maps.blocksInfo[idnum]={'cls': info.images, 'id':id}; + core.icons.icons[info.images][id]=info.y; + } + + throw('尚未实现:save(core.maps.blocksInfo,map.js);save(core.icons.icons,icons.js);') + callback(null); } //callback(err:String) editor_file.editItem = function(editor,id,obj,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (!isset(callback)) throw('未设置callback'); + callback( {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"}, {'items':'','itemEffect':'','itemEffectTip':''}, null); //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items } + /* + << + {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"} + == + [ + ["change","['items']['name']","红宝石的新名字"], + ["add","['items']['新的和name同级的属性']",123], + ["change","['itemEffectTip']","',攻击力+'+core.values.redJewel"], + ] + >> + 'yellowKey': {'cls': 'keys' \*只能取keys items constants tools\n$range(thiseval in ['keys','items','constants','tools'])\n*\ , 'name': '黄钥匙'} + + $range((function(){typeof(thiseval)==typeof(0)||})()) + if( 注释.indexof('$range(')!= -1){ + thiseval = 新值; + evalstr = 注释.split('$range')[1].split('\n')[0]; + if(eval(evalstr) !== true)alert('不在取值范围内') + } + */ + //callback(obj,commentObj,err:String) editor_file.editEnemy = function(editor,id,obj,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (!isset(callback)) throw('未设置callback'); + callback( {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, "bomb": false}, {'name': '名称', 'hp': '生命值', 'atk': '攻击力', 'def': '防御力', 'money': '金币', 'experience': '经验', 'special': '特殊属性\n1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:4连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨\n多个属性例如用010411表示先攻2连击吸血\n模仿怪的攻防设为0就好\n', 'value': '特殊属性的数值\n领域怪需要加value表示领域伤害的数值\n吸血怪需要在后面添加value代表吸血比例', 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉'}, null); @@ -93,7 +150,8 @@ editor_file.editLoc = function(editor,x,y,obj,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (!isset(callback)) throw('未设置callback'); + callback( {"events":['\t[老人,man]这些是本样板支持的所有的道具。\n\n道具分为三类:items, constants, tools。\nitems 为即捡即用类道具,例如宝石、血瓶、剑盾等。\nconstants 为永久道具,例如怪物手册、楼层传送器、幸运金币等。\ntools 为消耗类道具,例如破墙镐、炸弹、中心对称飞行器等。\n\n后两类道具在工具栏中可以看到并使用。', '\t[老人,man]有关道具效果,定义在items.js中。\n目前大多数道具已有默认行为,如有自定义的需求则需在items.js中修改代码。', '\t[老人,man]constants 和 tools 各最多只允许12种,多了会导致图标溢出。', '\t[老人,man]拾取道具结束后可触发 afterGetItem 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。', {'type': 'hide', 'time': 500}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, {"events":['', '', '', '', {'type': '', 'time': ' // 消失 \n // 守着门的老人 '}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, null); @@ -104,7 +162,8 @@ editor_file.editFloor = function(editor,obj,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (!isset(callback)) throw('未设置callback'); + callback( {'floorId': 'sample0', 'title': '样板 0 层', 'name': '0', 'canFlyTo': True, 'canUseQuickShop': True, 'defaultGround': 'ground', 'firstArrive': ['\t[样板提示]首次到达某层可以触发 firstArrive 事件,该事件可类似于RMXP中的“自动执行脚本”。\n\n本事件支持一切的事件类型,常常用来触发对话,例如:', '\t[hero]我是谁?我从哪来?我又要到哪去?', '\t[仙子,fairy]你问我...?我也不知道啊...', '本层主要对道具、门、怪物等进行介绍,有关事件的各种信息在下一层会有更为详细的说明。']}, {'floorId': '// 这里需要改楼层名,请和文件名及下面的floorId保持完全一致 // 楼层唯一标识符仅能由字母、数字、下划线组成,且不能由数字开头 // 推荐用法:第20层就用MT20,第38层就用MT38,地下6层就用MT_6(用下划线代替负号),隐藏3层用MT3h(h表示隐藏),等等 \n // 楼层唯一标识符,需要和名字完全一致 ', 'title': ' // 楼层中文名 ', 'name': ' // 显示在状态栏中的层数 ', 'canFlyTo': ' // 该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) ', 'canUseQuickShop': ' // 该层是否允许使用快捷商店 ', 'defaultGround': ' // 默认地面的图块ID(terrains中) \n // 地图数据,需要是13x13,建议使用地图生成器来生成 ', 'firstArrive': ['', '', '', ' // 该楼的所有可能事件列表 \n // 守着道具的老人 ']}, null); @@ -117,7 +176,8 @@ editor_file.editTower = function(editor,obj,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (!isset(callback)) throw('未设置callback'); + callback( {'main': {'useCompress': False, 'floorIds': ['sample0', 'sample1', 'sample2', 'test']}, 'firstData': {'title': '魔塔样板', 'name': 'template', 'version': 'Ver 1.0.0 (Beta)', 'floorId': 'sample0', 'hero': {'name': '阳光', 'lv': 1, 'hp': 2000, 'atk': 100, 'def': 100, 'mdef': 100, 'money': 100, 'experience': 0, 'items': {'keys': {'yellowKey': 0, 'blueKey': 0, 'redKey': 0}, 'constants': {}, 'tools': {}}, 'flyRange': [], 'loc': {'direction': 'up', 'x': 6, 'y': 10}, 'flags': {'poison': False, 'weak': False, 'curse': False}}, 'startText': ['Hi,欢迎来到 HTML5 魔塔样板!\n\n本样板由艾之葵制作,可以让你在不会写任何代码\n的情况下也能做出属于自己的H5魔塔!', '这里游戏开始时的剧情。\n定义在data.js的startText处。\n\n你可以在这里写上自己的内容。', '赶快来试一试吧!'], 'shops': {'moneyShop1': {'name': '贪婪之神', 'icon': 'blueShop', 'textInList': '1F金币商店', 'use': 'money', 'need': '20+10*times*(times+1)', 'text': '勇敢的武士啊,给我${need}金币就可以:', 'choices': [{'text': '生命+800', 'effect': 'status:hp+=800'}, {'text': '攻击+4', 'effect': 'status:atk+=4'}, {'text': '防御+4', 'effect': 'status:def+=4'}, {'text': '魔防+10', 'effect': 'status:mdef+=10'}]}, 'expShop1': {'name': '经验之神', 'icon': 'pinkShop', 'textInList': '1F经验商店', 'use': 'experience', 'need': '-1', 'text': '勇敢的武士啊,给我若干经验就可以:', 'choices': [{'text': '等级+1', 'need': '100', 'effect': 'status:lv+=1;status:hp+=1000;status:atk+=7;status:def+=7'}, {'text': '攻击+5', 'need': '30', 'effect': 'status:atk+=5'}, {'text': '防御+5', 'need': '30', 'effect': 'status:def+=5'}]}}, 'levelUp': [{}, {'need': 20, 'name': '第二级', 'effect': 'status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10'}, {'need': 40, 'effect': 'function () {\n core.drawText("恭喜升级!");\n core.status.hero.hp *= 2;\n core.status.hero.atk += 100;\n core.status.hero.def += 100;\n }'}]}, 'values': {'HPMAX': 999999, 'lavaDamage': 100, 'poisonDamage': 10, 'weakValue': 20, 'redJewel': 3, 'blueJewel': 3, 'greenJewel': 5, 'redPotion': 100, 'bluePotion': 250, 'yellowPotion': 500, 'greenPotion': 800, 'sword1': 10, 'shield1': 10, 'sword2': 20, 'shield2': 20, 'sword3': 40, 'shield3': 40, 'sword4': 80, 'shield4': 80, 'sword5': 160, 'shield5': 160, 'moneyPocket': 500, 'breakArmor': 0.9, 'counterAttack': 0.1, 'purify': 3, 'hatred': 2, 'animateSpeed': 500}, 'flags': {'enableNegativeDamage': True, 'enableFloor': False, 'enableLv': True, 'enableMDef': True, 'enableMoney': True, 'enableExperience': True, 'enableLevelUp': False, 'enableDebuff': True, 'flyNearStair': True, 'pickaxeFourDirections': True, 'bombFourDirections': True, 'bigKeyIsBox': False, 'startDirectly': False, 'canOpenBattleAnimate': True, 'showBattleAnimateConfirm': True, 'battleAnimate': True, 'displayEnemyDamage': True, 'displayExtraDamage': False, 'enableGentleClick': True, 'portalWithoutTrigger': True, 'potionWhileRouting': False}}, {'main': {'useCompress': ' // 是否使用压缩文件 // 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 // 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 // 如果要进行剧本的修改请务必将其改成false。 \n // 在这里按顺序放所有的楼层;其顺序直接影响到楼层传送器的顺序和上楼器/下楼器的顺序 ', 'floorIds': ['', '', '', '']}, 'firstData': {'title': ' // 游戏名,将显示在标题页面以及切换楼层的界面中 ', 'name': ' // 游戏的唯一英文标识符。由英文、数字、下划线组成,不能超过20个字符。 ', 'version': ' // 当前游戏版本;版本不一致的存档不能通用。 ', 'floorId': ' // 初始楼层ID \n // 勇士初始数据 ', 'hero': {'name': ' // 勇士名;可以改成喜欢的 ', 'lv': ' // 初始等级,该项必须为正整数 ', 'hp': ' // 初始生命值 ', 'atk': ' // 初始攻击 ', 'def': ' // 初始防御 ', 'mdef': ' // 初始魔防 ', 'money': ' // 初始金币 ', 'experience': ' // 初始经验 \n // 初始道具个数 ', 'items': {'keys': {'yellowKey': '', 'blueKey': '', 'redKey': ''}, 'constants': '', 'tools': ''}, 'flyRange': ' // 初始可飞的楼层;一般留空数组即可 ', 'loc': {'direction': '', 'x': '', 'y': ' // 勇士初始位置 \n // 游戏过程中的变量或flags '}, 'flags': {'poison': ' // 毒 ', 'weak': ' // 衰 ', 'curse': ' // 咒 \n // 游戏开始前剧情。如果无剧情直接留一个空数组即可。 '}}, 'startText': ['', '', ' // 定义全局商店(即快捷商店) \n // 商店唯一ID '], 'shops': {'moneyShop1': {'name': ' // 商店名称(标题) ', 'icon': ' // 商店图标,blueShop为蓝色商店,pinkShop为粉色商店 ', 'textInList': ' // 在快捷商店栏中显示的名称 ', 'use': ' // 商店所要使用的。只能是"money"或"experience"。 ', 'need': ' // 商店需要的金币/经验数值;可以是一个表达式,以times作为参数计算。 // 这里用到的times为该商店的已经的访问次数。首次访问该商店时times的值为0。 // 上面的例子是50层商店的计算公式。你也可以写任意其他的计算公式,只要以times作为参数即可。 // 例如: "need": "25" 就是恒定需要25金币的商店; "need": "20+2*times" 就是第一次访问要20金币,以后每次递增2金币的商店。 // 如果是对于每个选项有不同的计算公式,写 "need": "-1" 即可。可参见下面的经验商店。 ', 'text': ' // 显示的文字,需手动加换行符。可以使用${need}表示上面的need值。 \n // 商店的选项 ', 'choices': [{'text': '', 'effect': ' // 如果有多个effect以分号分开,参见下面的经验商店 '}, {'text': '', 'effect': ''}, {'text': '', 'effect': ''}, {'text': '', 'effect': ' // effect只能对status和item进行操作,不能修改flag值。 // 必须是X+=Y的形式,其中Y可以是一个表达式,以status:xxx或item:xxx为参数 // 其他effect样例: // "item:yellowKey+=1" 黄钥匙+1 // "item:pickaxe+=3" 破墙镐+3 // "status:hp+=2*(status:atk+status:def)" 将生命提升攻防和的数值的两倍 \n // 商店唯一ID '}]}, 'expShop1': {'name': '', 'icon': '', 'textInList': '', 'use': ' // 该商店使用的是经验进行计算 ', 'need': ' // 如果是对于每个选项所需要的数值不同,这里直接写-1,然后下面选项里给定具体数值 ', 'text': ' // 在choices中写need,可以针对每个选项都有不同的需求。 // 这里的need同样可以以times作为参数,比如 "need": "100+20*times" ', 'choices': [{'text': '', 'need': '', 'effect': ' // 多个effect直接以分号分开即可。如上面的意思是生命+1000,攻击+7,防御+7。 '}, {'text': '', 'need': '', 'effect': ''}, {'text': '', 'need': '', 'effect': ' // 经验升级所需要的数值,是一个数组 '}]}}, 'levelUp': [' // 第一项为初始等级,可以简单留空,也可以写name // 每一个里面可以含有三个参数 name, need, effect // need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 // name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 // effect为本次升级所执行的操作,可由若干项组成,由分号分开 // 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 ', {'need': '', 'name': '', 'effect': ' // 先将生命提升攻防和的2倍;再将攻击+10,防御+10 // effect也允许写一个function,代表本次升级将会执行的操作 '}, {'need': '', 'effect': ' // 依次往下写需要的数值即可 \n // 各种数值;一些数值可以在这里设置 \n /****** 角色相关 ******/ '}]}, 'values': {'HPMAX': ' // HP上限;-1则无上限 ', 'lavaDamage': ' // 经过血网受到的伤害 ', 'poisonDamage': ' // 中毒后每步受到的伤害 ', 'weakValue': ' // 衰弱状态下攻防减少的数值 /****** 道具相关 ******/ ', 'redJewel': ' // 红宝石加攻击的数值 ', 'blueJewel': ' // 蓝宝石加防御的数值 ', 'greenJewel': ' // 绿宝石加魔防的数值 ', 'redPotion': ' // 红血瓶加血数值 ', 'bluePotion': ' // 蓝血瓶加血数值 ', 'yellowPotion': ' // 黄血瓶加血数值 ', 'greenPotion': ' // 绿血瓶加血数值 ', 'sword1': ' // 铁剑加攻数值 ', 'shield1': ' // 铁盾加防数值 ', 'sword2': ' // 银剑加攻数值 ', 'shield2': ' // 银盾加防数值 ', 'sword3': ' // 骑士剑加攻数值 ', 'shield3': ' // 骑士盾加防数值 ', 'sword4': ' // 圣剑加攻数值 ', 'shield4': ' // 圣盾加防数值 ', 'sword5': ' // 神圣剑加攻数值 ', 'shield5': ' // 神圣盾加防数值 ', 'moneyPocket': ' // 金钱袋加金币的数值 /****** 怪物相关 ******/ ', 'breakArmor': ' // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) ', 'counterAttack': ' // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) ', 'purify': ' // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) ', 'hatred': ' // 仇恨属性中,每杀死一个怪物获得的仇恨值 /****** 系统相关 ******/ ', 'animateSpeed': ' // 动画时间 \n // 系统FLAG,在游戏运行中中请不要修改它。 \n /****** 角色状态相关 ******/ '}, 'flags': {'enableNegativeDamage': ' // 是否支持负伤害(回血) ', 'enableFloor': ' // 是否在状态栏显示当前楼层 ', 'enableLv': ' // 是否在状态栏显示当前等级 ', 'enableMDef': ' // 是否在状态栏及战斗界面显示魔防(护盾) ', 'enableMoney': ' // 是否在状态栏、怪物手册及战斗界面显示金币 ', 'enableExperience': ' // 是否在状态栏、怪物手册及战斗界面显示经验 ', 'enableLevelUp': ' // 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false ', 'enableDebuff': ' // 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff ////// 上述的几个开关将直接影响状态栏的显示效果 ////// /****** 道具相关 ******/ ', 'flyNearStair': ' // 是否需要在楼梯边使用传送器 ', 'pickaxeFourDirections': ' // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 ', 'bombFourDirections': ' // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) ', 'bigKeyIsBox': ' // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 /****** 系统相关 ******/ ', 'startDirectly': ' // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 ', 'canOpenBattleAnimate': ' // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false ', 'showBattleAnimateConfirm': ' // 是否在游戏开始时提供“是否开启战斗动画”的选项 ', 'battleAnimate': ' // 是否默认显示战斗动画;用户可以手动在菜单栏中开关 ', 'displayEnemyDamage': ' // 是否地图怪物显伤;用户可以手动在菜单栏中开关 ', 'displayExtraDamage': ' // 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 ', 'enableGentleClick': ' // 是否允许轻触(获得面前物品) ', 'portalWithoutTrigger': ' // 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 ', 'potionWhileRouting': ' // 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 '}}, null); From a9835de64a4a6f925b1ccb59f813dd64750ec7fa Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Mon, 1 Jan 2018 19:31:32 +0800 Subject: [PATCH 013/102] editor_file & comment.js --- _server/editor_file.demo.js | 20 +++++------ _server/editor_file.js | 66 ++++++++++++++++++++++--------------- libs/project/comment.js | 27 +++++++++++++++ 3 files changed, 77 insertions(+), 36 deletions(-) create mode 100644 libs/project/comment.js diff --git a/_server/editor_file.demo.js b/_server/editor_file.demo.js index 943dc71d..7f70e19e 100644 --- a/_server/editor_file.demo.js +++ b/_server/editor_file.demo.js @@ -3,13 +3,13 @@ editor_file = {}; editor_file.getFloorFileList = function(editor,callback){ - if (isset(callback)) callback(['simple0.js','simple1.js','simple2.js'],null); + if (isset(callback)) callback([['simple0.js','simple1.js','simple2.js'],null]); } - //callback(Array,err:String) + //callback([Array,err:String]) editor_file.loadFloorFile = function(editor,filename,callback){ - if (isset(callback)) callback('',null); + if (isset(callback)) callback(null); } - //callback(String,err:String) + //callback(err:String) editor_file.saveFloorFile = function(editor,callback){ if (isset(callback)) callback(null); } @@ -25,16 +25,16 @@ if (isset(callback)) callback(null); } //callback(err:String) - editor_file.editItem = function(editor,id,obj,callback){ + editor_file.editItem = function(editor,id,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (isset(callback)) callback( {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"}, - {'items':'','itemEffect':'','itemEffectTip':''}, + {'items':{'cls': "只能取keys items constants tools\n$range(thiseval in ['keys','items','constants','tools'])$end", 'name': '', 'text': ''},'itemEffect':'','itemEffectTip':''}, null); //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items } //callback(obj,commentObj,err:String) - editor_file.editEnemy = function(editor,id,obj,callback){ + editor_file.editEnemy = function(editor,id,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (isset(callback)) callback( {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, "bomb": false}, @@ -45,7 +45,7 @@ //////////////////////////////////////////////////////////////////// - editor_file.editLoc = function(editor,x,y,obj,callback){ + editor_file.editLoc = function(editor,x,y,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (isset(callback)) callback( {"events":['\t[老人,man]这些是本样板支持的所有的道具。\n\n道具分为三类:items, constants, tools。\nitems 为即捡即用类道具,例如宝石、血瓶、剑盾等。\nconstants 为永久道具,例如怪物手册、楼层传送器、幸运金币等。\ntools 为消耗类道具,例如破墙镐、炸弹、中心对称飞行器等。\n\n后两类道具在工具栏中可以看到并使用。', '\t[老人,man]有关道具效果,定义在items.js中。\n目前大多数道具已有默认行为,如有自定义的需求则需在items.js中修改代码。', '\t[老人,man]constants 和 tools 各最多只允许12种,多了会导致图标溢出。', '\t[老人,man]拾取道具结束后可触发 afterGetItem 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。', {'type': 'hide', 'time': 500}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, @@ -56,7 +56,7 @@ //////////////////////////////////////////////////////////////////// - editor_file.editFloor = function(editor,obj,callback){ + editor_file.editFloor = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (isset(callback)) callback( {'floorId': 'sample0', 'title': '样板 0 层', 'name': '0', 'canFlyTo': True, 'canUseQuickShop': True, 'defaultGround': 'ground', 'firstArrive': ['\t[样板提示]首次到达某层可以触发 firstArrive 事件,该事件可类似于RMXP中的“自动执行脚本”。\n\n本事件支持一切的事件类型,常常用来触发对话,例如:', '\t[hero]我是谁?我从哪来?我又要到哪去?', '\t[仙子,fairy]你问我...?我也不知道啊...', '本层主要对道具、门、怪物等进行介绍,有关事件的各种信息在下一层会有更为详细的说明。']}, @@ -69,7 +69,7 @@ - editor_file.editTower = function(editor,obj,callback){ + editor_file.editTower = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (isset(callback)) callback( {'main': {'useCompress': False, 'floorIds': ['sample0', 'sample1', 'sample2', 'test']}, 'firstData': {'title': '魔塔样板', 'name': 'template', 'version': 'Ver 1.0.0 (Beta)', 'floorId': 'sample0', 'hero': {'name': '阳光', 'lv': 1, 'hp': 2000, 'atk': 100, 'def': 100, 'mdef': 100, 'money': 100, 'experience': 0, 'items': {'keys': {'yellowKey': 0, 'blueKey': 0, 'redKey': 0}, 'constants': {}, 'tools': {}}, 'flyRange': [], 'loc': {'direction': 'up', 'x': 6, 'y': 10}, 'flags': {'poison': False, 'weak': False, 'curse': False}}, 'startText': ['Hi,欢迎来到 HTML5 魔塔样板!\n\n本样板由艾之葵制作,可以让你在不会写任何代码\n的情况下也能做出属于自己的H5魔塔!', '这里游戏开始时的剧情。\n定义在data.js的startText处。\n\n你可以在这里写上自己的内容。', '赶快来试一试吧!'], 'shops': {'moneyShop1': {'name': '贪婪之神', 'icon': 'blueShop', 'textInList': '1F金币商店', 'use': 'money', 'need': '20+10*times*(times+1)', 'text': '勇敢的武士啊,给我${need}金币就可以:', 'choices': [{'text': '生命+800', 'effect': 'status:hp+=800'}, {'text': '攻击+4', 'effect': 'status:atk+=4'}, {'text': '防御+4', 'effect': 'status:def+=4'}, {'text': '魔防+10', 'effect': 'status:mdef+=10'}]}, 'expShop1': {'name': '经验之神', 'icon': 'pinkShop', 'textInList': '1F经验商店', 'use': 'experience', 'need': '-1', 'text': '勇敢的武士啊,给我若干经验就可以:', 'choices': [{'text': '等级+1', 'need': '100', 'effect': 'status:lv+=1;status:hp+=1000;status:atk+=7;status:def+=7'}, {'text': '攻击+5', 'need': '30', 'effect': 'status:atk+=5'}, {'text': '防御+5', 'need': '30', 'effect': 'status:def+=5'}]}}, 'levelUp': [{}, {'need': 20, 'name': '第二级', 'effect': 'status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10'}, {'need': 40, 'effect': 'function () {\n core.drawText("恭喜升级!");\n core.status.hero.hp *= 2;\n core.status.hero.atk += 100;\n core.status.hero.def += 100;\n }'}]}, 'values': {'HPMAX': 999999, 'lavaDamage': 100, 'poisonDamage': 10, 'weakValue': 20, 'redJewel': 3, 'blueJewel': 3, 'greenJewel': 5, 'redPotion': 100, 'bluePotion': 250, 'yellowPotion': 500, 'greenPotion': 800, 'sword1': 10, 'shield1': 10, 'sword2': 20, 'shield2': 20, 'sword3': 40, 'shield3': 40, 'sword4': 80, 'shield4': 80, 'sword5': 160, 'shield5': 160, 'moneyPocket': 500, 'breakArmor': 0.9, 'counterAttack': 0.1, 'purify': 3, 'hatred': 2, 'animateSpeed': 500}, 'flags': {'enableNegativeDamage': True, 'enableFloor': False, 'enableLv': True, 'enableMDef': True, 'enableMoney': True, 'enableExperience': True, 'enableLevelUp': False, 'enableDebuff': True, 'flyNearStair': True, 'pickaxeFourDirections': True, 'bombFourDirections': True, 'bigKeyIsBox': False, 'startDirectly': False, 'canOpenBattleAnimate': True, 'showBattleAnimateConfirm': True, 'battleAnimate': True, 'displayEnemyDamage': True, 'displayExtraDamage': False, 'enableGentleClick': True, 'portalWithoutTrigger': True, 'potionWhileRouting': False}}, diff --git a/_server/editor_file.js b/_server/editor_file.js index 8ce40c89..d458b341 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -85,6 +85,7 @@ return; } } + throw('需要改实现') if (change!=-1 && change!=idnum){//修改idnum core.maps.blocksInfo[idnum] = core.maps.blocksInfo[change]; delete(core.maps.blocksInfo[change]); @@ -106,37 +107,24 @@ callback(null); } //callback(err:String) - editor_file.editItem = function(editor,id,obj,callback){ - //obj形式同callback的obj,为null或undefined时只查询不修改 + editor_file.editItem = function(editor,id,actionList,callback){ + /*actionList:[ + ["change","['items']['name']","红宝石的新名字"], + ["add","['items']['新的和name同级的属性']",123], + ["change","['itemEffectTip']","',攻击力+'+core.values.redJewel"], + ] + 为[]时只查询不修改 + */ if (!isset(callback)) throw('未设置callback'); callback( {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"}, - {'items':'','itemEffect':'','itemEffectTip':''}, + {'items':{'cls': "/*只能取keys items constants tools\\n$range(thiseval in ['keys','items','constants','tools'])\\n*/", 'name': '', 'text': ''},'itemEffect':'','itemEffectTip':''}, null); //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items } - /* - << - {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"} - == - [ - ["change","['items']['name']","红宝石的新名字"], - ["add","['items']['新的和name同级的属性']",123], - ["change","['itemEffectTip']","',攻击力+'+core.values.redJewel"], - ] - >> - 'yellowKey': {'cls': 'keys' \*只能取keys items constants tools\n$range(thiseval in ['keys','items','constants','tools'])\n*\ , 'name': '黄钥匙'} - - $range((function(){typeof(thiseval)==typeof(0)||})()) - if( 注释.indexof('$range(')!= -1){ - thiseval = 新值; - evalstr = 注释.split('$range')[1].split('\n')[0]; - if(eval(evalstr) !== true)alert('不在取值范围内') - } - */ //callback(obj,commentObj,err:String) - editor_file.editEnemy = function(editor,id,obj,callback){ + editor_file.editEnemy = function(editor,id,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); callback( @@ -148,7 +136,7 @@ //////////////////////////////////////////////////////////////////// - editor_file.editLoc = function(editor,x,y,obj,callback){ + editor_file.editLoc = function(editor,x,y,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); callback( @@ -160,7 +148,7 @@ //////////////////////////////////////////////////////////////////// - editor_file.editFloor = function(editor,obj,callback){ + editor_file.editFloor = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); callback( @@ -174,7 +162,7 @@ - editor_file.editTower = function(editor,obj,callback){ + editor_file.editTower = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); callback( @@ -210,4 +198,30 @@ } return formatArrStr; } + + var saveSetting = function(file,actionList,callback) { + if (file=='icons') {} + if (file=='maps') {} + if (file=='items') {} + if (file=='enemys') {} + if (file=='data') {} + callback('出错了,要设置的文件名不识别'); + } + /* + [ + ["change","['items']['redJewel']['name']","红宝石的新名字"], + ["add","['items']['redJewel']['新的和name同级的属性']",123], + ["change","['itemEffectTip']['redJewel']","',攻击力+'+core.values.redJewel"], + ] + >> + 'yellowKey': {'cls': 'keys' \*只能取keys items constants tools\n$range(thiseval in ['keys','items','constants','tools'])\n*\ , 'name': '黄钥匙'} + + $range((function(){typeof(thiseval)==typeof(0)||})()) + if( 注释.indexof('$range(')!= -1){ + thiseval = 新值; + evalstr = 注释.split('$range')[1].split('$end')[0]; + if(eval(evalstr) !== true)alert('不在取值范围内') + } + */ + })(); \ No newline at end of file diff --git a/libs/project/comment.js b/libs/project/comment.js new file mode 100644 index 00000000..df355d73 --- /dev/null +++ b/libs/project/comment.js @@ -0,0 +1,27 @@ +comment = +{ + "items" : { + 'items':{ + 'cls': "只能取keys items constants tools\n$range(thiseval in ['keys','items','constants','tools'])$end", + 'name': '名称', + 'text': '道具在道具栏中显示的描述' + }, + 'itemEffect':'cls为items的即捡即用类物品的效果,执行时会对这里的字符串执行eval()', + 'itemEffectTip':'cls为items的即捡即用类物品,在获得时左上角额外显示的文字,执行时会对这里的字符串执行eval()得到字符串' + }, + "enemys" : { + 'name': '名称', + 'hp': '生命值', + 'atk': '攻击力', + 'def': '防御力', + 'money': '金币', + 'experience': '经验', + 'special': '特殊属性\n1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:n连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨,18:阻击,19:自爆,20:无敌\n多个属性例如用[1,4,11]表示先攻2连击吸血\n模仿怪的攻防设为0就好\n', + 'value': '特殊属性的数值\n领域怪需要加value表示领域伤害的数值\n吸血怪需要在后面添加value代表吸血比例', + 'zoneSquare': '领域怪zoneSquare代表是否九宫格伤害', + 'range': 'range可选,代表领域伤害的范围;不加默认为1\n$range(thiseval==~~thiseval &&thiseval>0)$end', + 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉$range(thiseval in [true,false])$end', + 'point': 'point可以在打败怪物后进行加点,详见文档说明\n$range(thiseval==~~thiseval && thiseval>0)$end', + 'n': '多连击需要在后面指定n代表是几连击\n$range(thiseval==~~thiseval &&thiseval>0)$end', + } +} \ No newline at end of file From 5671d5501e7a0b2bee1fe9ab8b12c7378a5a3e0c Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Tue, 2 Jan 2018 12:37:40 +0800 Subject: [PATCH 014/102] =?UTF-8?q?=E5=8F=96=E6=B6=88=E4=BA=86editor?= =?UTF-8?q?=E6=A8=A1=E5=BC=8F=E7=9A=84=E9=83=A8=E5=88=86=E5=8A=A8=E7=94=BB?= =?UTF-8?q?=20&=20fix=20bug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/vm.js | 1 + libs/core.js | 16 +++++++++++++--- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/_server/vm.js b/_server/vm.js index 4c1644bf..ba4e640e 100644 --- a/_server/vm.js +++ b/_server/vm.js @@ -168,6 +168,7 @@ var clear = new Vue({ methods: { clearMap: function(){ editor.mapInit(); + editor.updateMap(); clearTimeout(editArea.formatTimer); clearTimeout(tip.timer); pout.value = ''; diff --git a/libs/core.js b/libs/core.js index c659d2d6..12ac4980 100644 --- a/libs/core.js +++ b/libs/core.js @@ -3615,7 +3615,7 @@ core.prototype.isset = function (val) { ////// 播放背景音乐 ////// core.prototype.playBgm = function (bgm) { - + if (main.mode!='play')return; // 如果不允许播放 if (!core.musicStatus.bgmStatus) return; // 音频不存在 @@ -3666,7 +3666,7 @@ core.prototype.pauseBgm = function () { ////// 恢复背景音乐的播放 ////// core.prototype.resumeBgm = function () { - + if (main.mode!='play')return; // 如果不允许播放 if (!core.musicStatus.bgmStatus) return; @@ -3691,7 +3691,7 @@ core.prototype.resumeBgm = function () { ////// 播放音频 ////// core.prototype.playSound = function (sound) { - + if (main.mode!='play')return; // 如果不允许播放 if (!core.musicStatus.soundStatus) return; // 音频不存在 @@ -3730,6 +3730,11 @@ core.prototype.show = function (obj, speed, callback) { return; } obj.style.display = 'block'; + if (main.mode!='play'){ + obj.style.opacity = 1; + if (core.isset(callback)) {callback();} + return; + } obj.style.opacity = 0; var opacityVal = 0; var showAnimate = window.setInterval(function () { @@ -3750,6 +3755,11 @@ core.prototype.hide = function (obj, speed, callback) { obj.style.display = 'none'; return; } + if (main.mode!='play'){ + obj.style.display = 'none'; + if (core.isset(callback)) {callback();} + return; + } var opacityVal = 1; var hideAnimate = window.setInterval(function () { opacityVal -= 0.03; From 4659f4ddcdb69330dcdea8bd376e8bfe9b31c752 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Tue, 2 Jan 2018 13:35:27 +0800 Subject: [PATCH 015/102] editor.changeFloor --- _server/css/editor.css | 3 +++ drawMapGUI.html | 28 ++++++++++++++++++++++++---- 2 files changed, 27 insertions(+), 4 deletions(-) diff --git a/_server/css/editor.css b/_server/css/editor.css index 02b25b10..1ffb46b9 100644 --- a/_server/css/editor.css +++ b/_server/css/editor.css @@ -184,6 +184,9 @@ body{ top: 5px; overflow: auto; } +.egameCanvas { + position: absolute; +} .gameCanvas { position: absolute; } diff --git a/drawMapGUI.html b/drawMapGUI.html index e6051f11..5c983602 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -32,7 +32,7 @@
- +
@@ -70,7 +70,7 @@
- +
@@ -110,39 +110,39 @@
- +

- +

- +

- +

- +

- +

- +

- +

- +

@@ -157,13 +157,13 @@
- - - - - - - + + + + + + +

diff --git a/index.html b/index.html index d59b0e43..a8d12214 100644 --- a/index.html +++ b/index.html @@ -25,7 +25,7 @@

资源即将开始加载

- +
@@ -48,39 +48,39 @@
- +

- +

- +

- +

- +

- +

- +

- +

- +

@@ -95,13 +95,13 @@
- - - - - - - + + + + + + +

diff --git a/libs/core.js b/libs/core.js index 12ac4980..11a9bc9b 100644 --- a/libs/core.js +++ b/libs/core.js @@ -181,7 +181,7 @@ core.prototype.init = function (dom, statusBar, canvas, images, pngs, bgms, soun core.flags.displayExtraDamage = core.getLocalStorage('extraDamage', core.flags.displayExtraDamage); core.material.ground = new Image(); - core.material.ground.src = "images/ground.png"; + core.material.ground.src = "project/images/ground.png"; core.loader(function () { console.log(core.material); @@ -298,7 +298,7 @@ core.prototype.loadImage = function (imgName, callback) { if (name.indexOf(".png")<0) // 不包含"png" name=name+".png"; var image = new Image(); - image.src = 'images/' + name + "?v=" + main.version; + image.src = 'project/images/' + name + "?v=" + main.version; if (image.complete) { callback(imgName, image); return; @@ -323,7 +323,7 @@ core.prototype.loadMusic = function (callback) { if (core.musicStatus.audioContext!=null) { core.material.bgms[t] = 'loading'; var xhr = new XMLHttpRequest(); - xhr.open('GET', 'sounds/'+t, true); + xhr.open('GET', 'project/sounds/'+t, true); xhr.overrideMimeType("text/plain; charset=x-user-defined"); xhr.onload = function(e) { //下载完成 try { @@ -360,7 +360,7 @@ core.prototype.loadMusic = function (callback) { else { var music = new Audio(); music.preload = core.musicStatus.startDirectly?'auto':'none'; - music.src = 'sounds/'+t; + music.src = 'project/sounds/'+t; music.loop = 'loop'; core.material.bgms[t] = music; } @@ -370,7 +370,7 @@ core.prototype.loadMusic = function (callback) { if (core.musicStatus.audioContext != null) { var xhr = new XMLHttpRequest(); - xhr.open('GET', 'sounds/'+t, true); + xhr.open('GET', 'project/sounds/'+t, true); xhr.responseType = 'arraybuffer'; xhr.onload = function(e) { //下载完成 try { @@ -399,7 +399,7 @@ core.prototype.loadMusic = function (callback) { } else { var music = new Audio(); - music.src = 'sounds/'+t; + music.src = 'project/sounds/'+t; core.material.sounds[t] = music; } @@ -990,8 +990,8 @@ core.prototype.onmousewheel = function (direct) { // 怪物手册 if (core.status.lockControl && core.status.event.id == 'book') { - if (direct==1) core.ui.drawBook(core.status.event.data - 1); - if (direct==-1) core.ui.drawBook(core.status.event.data + 1); + if (direct==1) core.ui.drawBook(core.status.event.data - 6); + if (direct==-1) core.ui.drawBook(core.status.event.data + 6); return; } diff --git a/main.js b/main.js index 8efdf81d..1e3ff0d6 100644 --- a/main.js +++ b/main.js @@ -154,7 +154,7 @@ main.prototype.loaderFloors = function (callback) { main.setMainTipsText('正在加载楼层文件...') if (this.useCompress) { // 读取压缩文件 var script = document.createElement('script'); - script.src = 'libs/project/floors.min.js?v=' + this.version; + script.src = 'project/floors.min.js?v=' + this.version; main.dom.body.appendChild(script); script.onload = function () { main.dom.mainTips.style.display = 'none'; @@ -189,7 +189,7 @@ main.prototype.loadMod = function (modName, callback) { ////// 加载某一个楼层 ////// main.prototype.loadFloor = function(floorId, callback) { var script = document.createElement('script'); - script.src = 'libs/project/floors/' + floorId +'.js?v=' + this.version; + script.src = 'project/floors/' + floorId +'.js?v=' + this.version; main.dom.body.appendChild(script); script.onload = function () { callback(floorId); @@ -200,7 +200,7 @@ main.prototype.loadPureData = function(callback) { var loadedNum = 0; main.pureData.forEach(function(name){ var script = document.createElement('script'); - script.src = 'libs/project/' + name +'.js?v=' + this.version; + script.src = 'project/' + name +'.js?v=' + main.version; main.dom.body.appendChild(script); script.onload = function () { loadedNum++; diff --git a/libs/project/comment.js b/project/comment.js similarity index 100% rename from libs/project/comment.js rename to project/comment.js diff --git a/libs/project/data.js b/project/data.js similarity index 100% rename from libs/project/data.js rename to project/data.js diff --git a/libs/project/enemys.js b/project/enemys.js similarity index 100% rename from libs/project/enemys.js rename to project/enemys.js diff --git a/libs/project/floors/MT0.js b/project/floors/MT0.js similarity index 100% rename from libs/project/floors/MT0.js rename to project/floors/MT0.js diff --git a/libs/project/floors/sample0.js b/project/floors/sample0.js similarity index 99% rename from libs/project/floors/sample0.js rename to project/floors/sample0.js index aee78417..857473d0 100644 --- a/libs/project/floors/sample0.js +++ b/project/floors/sample0.js @@ -65,7 +65,7 @@ main.floors.sample0 = { ], "2,3": [ // 守着第三批怪物的老人 "\t[老人,magician]领域、夹击。\n请注意领域怪需要设置value为伤害数值,可参见样板中初级巫师的写法。", - "\t[老人,magician]夹击和领域同时发生时先计算领域,再夹击。\n自动寻路同样会尽量绕过你设置的这些点。\n\n另:本塔不支持阻击怪。", + "\t[老人,magician]夹击和领域同时发生时先计算领域,再夹击。\n自动寻路同样会尽量绕过你设置的这些点。", {"type": "hide", "time": 500} ], "12,10": { // 隐藏的仙子 diff --git a/libs/project/floors/sample1.js b/project/floors/sample1.js similarity index 100% rename from libs/project/floors/sample1.js rename to project/floors/sample1.js diff --git a/libs/project/floors/sample2.js b/project/floors/sample2.js similarity index 100% rename from libs/project/floors/sample2.js rename to project/floors/sample2.js diff --git a/libs/project/floors/test.js b/project/floors/test.js similarity index 100% rename from libs/project/floors/test.js rename to project/floors/test.js diff --git a/libs/project/icons.js b/project/icons.js similarity index 100% rename from libs/project/icons.js rename to project/icons.js diff --git a/images/animates.png b/project/images/animates.png similarity index 100% rename from images/animates.png rename to project/images/animates.png diff --git a/images/atk.png b/project/images/atk.png similarity index 100% rename from images/atk.png rename to project/images/atk.png diff --git a/images/autotile.png b/project/images/autotile.png similarity index 100% rename from images/autotile.png rename to project/images/autotile.png diff --git a/images/autotile1.png b/project/images/autotile1.png similarity index 100% rename from images/autotile1.png rename to project/images/autotile1.png diff --git a/images/autotile2.png b/project/images/autotile2.png similarity index 100% rename from images/autotile2.png rename to project/images/autotile2.png diff --git a/images/autotile3.png b/project/images/autotile3.png similarity index 100% rename from images/autotile3.png rename to project/images/autotile3.png diff --git a/images/bg.png b/project/images/bg.png similarity index 100% rename from images/bg.png rename to project/images/bg.png diff --git a/images/book.png b/project/images/book.png similarity index 100% rename from images/book.png rename to project/images/book.png diff --git a/images/def.png b/project/images/def.png similarity index 100% rename from images/def.png rename to project/images/def.png diff --git a/images/enemys.png b/project/images/enemys.png similarity index 100% rename from images/enemys.png rename to project/images/enemys.png diff --git a/images/experience.png b/project/images/experience.png similarity index 100% rename from images/experience.png rename to project/images/experience.png diff --git a/images/floor.png b/project/images/floor.png similarity index 100% rename from images/floor.png rename to project/images/floor.png diff --git a/images/fly.png b/project/images/fly.png similarity index 100% rename from images/fly.png rename to project/images/fly.png diff --git a/images/ground.png b/project/images/ground.png similarity index 100% rename from images/ground.png rename to project/images/ground.png diff --git a/images/hero.png b/project/images/hero.png similarity index 100% rename from images/hero.png rename to project/images/hero.png diff --git a/images/hp.png b/project/images/hp.png similarity index 100% rename from images/hp.png rename to project/images/hp.png diff --git a/images/items.png b/project/images/items.png similarity index 100% rename from images/items.png rename to project/images/items.png diff --git a/images/load.png b/project/images/load.png similarity index 100% rename from images/load.png rename to project/images/load.png diff --git a/images/lv.png b/project/images/lv.png similarity index 100% rename from images/lv.png rename to project/images/lv.png diff --git a/images/mdef.png b/project/images/mdef.png similarity index 100% rename from images/mdef.png rename to project/images/mdef.png diff --git a/images/money.png b/project/images/money.png similarity index 100% rename from images/money.png rename to project/images/money.png diff --git a/images/npcs.png b/project/images/npcs.png similarity index 100% rename from images/npcs.png rename to project/images/npcs.png diff --git a/images/save.png b/project/images/save.png similarity index 100% rename from images/save.png rename to project/images/save.png diff --git a/images/settings.png b/project/images/settings.png similarity index 100% rename from images/settings.png rename to project/images/settings.png diff --git a/images/shop.png b/project/images/shop.png similarity index 100% rename from images/shop.png rename to project/images/shop.png diff --git a/images/terrains.png b/project/images/terrains.png similarity index 100% rename from images/terrains.png rename to project/images/terrains.png diff --git a/images/toolbox.png b/project/images/toolbox.png similarity index 100% rename from images/toolbox.png rename to project/images/toolbox.png diff --git a/images/up.png b/project/images/up.png similarity index 100% rename from images/up.png rename to project/images/up.png diff --git a/images/yewai.png b/project/images/yewai.png similarity index 100% rename from images/yewai.png rename to project/images/yewai.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile0.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile0.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile0.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile0.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile1.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile1.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile1.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile1.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile10.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile10.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile10.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile10.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile11.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile11.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile11.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile11.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile12.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile12.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile12.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile12.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile13.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile13.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile13.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile13.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile14.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile14.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile14.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile14.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile2.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile2.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile2.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile2.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile3.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile3.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile3.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile3.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile4.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile4.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile4.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile4.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile5.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile5.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile5.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile5.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile6.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile6.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile6.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile6.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile7.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile7.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile7.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile7.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile8.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile8.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile8.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile8.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/autotile9.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile9.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/autotile9.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/autotile9.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero0.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero0.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero0.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero0.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero1.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero1.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero1.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero1.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero10.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero10.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero10.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero10.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero2.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero2.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero2.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero2.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero3.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero3.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero3.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero3.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero4.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero4.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero4.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero4.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero5.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero5.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero5.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero5.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero6.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero6.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero6.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero6.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero7.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero7.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero7.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero7.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero8.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero8.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero8.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero8.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/hero9.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/hero9.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/hero9.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/hero9.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/items0:经典.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/items0:经典.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/items0:经典.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/items0:经典.png diff --git a/images/常用素材:如需使用请直接替换目录中的对应文件/items1:圆形宝石.png b/project/images/常用素材:如需使用请直接替换目录中的对应文件/items1:圆形宝石.png similarity index 100% rename from images/常用素材:如需使用请直接替换目录中的对应文件/items1:圆形宝石.png rename to project/images/常用素材:如需使用请直接替换目录中的对应文件/items1:圆形宝石.png diff --git a/libs/project/items.js b/project/items.js similarity index 100% rename from libs/project/items.js rename to project/items.js diff --git a/libs/project/maps.js b/project/maps.js similarity index 100% rename from libs/project/maps.js rename to project/maps.js diff --git a/sounds/058-Slow01.mid b/project/sounds/058-Slow01.mid similarity index 100% rename from sounds/058-Slow01.mid rename to project/sounds/058-Slow01.mid diff --git a/sounds/attack.ogg b/project/sounds/attack.ogg similarity index 100% rename from sounds/attack.ogg rename to project/sounds/attack.ogg diff --git a/sounds/bgm.mp3 b/project/sounds/bgm.mp3 similarity index 100% rename from sounds/bgm.mp3 rename to project/sounds/bgm.mp3 diff --git a/sounds/door.ogg b/project/sounds/door.ogg similarity index 100% rename from sounds/door.ogg rename to project/sounds/door.ogg diff --git a/sounds/floor.mp3 b/project/sounds/floor.mp3 similarity index 100% rename from sounds/floor.mp3 rename to project/sounds/floor.mp3 diff --git a/sounds/item.ogg b/project/sounds/item.ogg similarity index 100% rename from sounds/item.ogg rename to project/sounds/item.ogg diff --git a/sounds/qianjin.mid b/project/sounds/qianjin.mid similarity index 100% rename from sounds/qianjin.mid rename to project/sounds/qianjin.mid diff --git a/sounds/star.mid b/project/sounds/star.mid similarity index 100% rename from sounds/star.mid rename to project/sounds/star.mid diff --git a/styles.css b/styles.css index 6523b3b8..b7031156 100644 --- a/styles.css +++ b/styles.css @@ -169,7 +169,7 @@ box-sizing: border-box; -moz-box-sizing: border-box; -webkit-box-sizing: border-box; - background: url(images/ground.png) round; + background: url(project/images/ground.png) round; z-index: 7; display: none; } @@ -198,7 +198,7 @@ } #toolBar { position: absolute; - background: url(images/ground.png) round; + background: url(project/images/ground.png) round; z-index: 6; box-sizing: border-box; -moz-box-sizing: border-box; From 62fbd21836b3ed7491d964c975fb98d48fbef7de Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Fri, 5 Jan 2018 20:43:11 +0800 Subject: [PATCH 017/102] Update editor_file.js --- {project => _server}/comment.js | 2 +- _server/editor_file.demo.js | 20 +++++------ _server/editor_file.js | 61 +++++++++++++++++++++++---------- 3 files changed, 53 insertions(+), 30 deletions(-) rename {project => _server}/comment.js (97%) diff --git a/project/comment.js b/_server/comment.js similarity index 97% rename from project/comment.js rename to _server/comment.js index df355d73..60762edb 100644 --- a/project/comment.js +++ b/_server/comment.js @@ -1,4 +1,4 @@ -comment = +comment_c456ea59_6018_45ef_8bcc_211a24c627dc = { "items" : { 'items':{ diff --git a/_server/editor_file.demo.js b/_server/editor_file.demo.js index 7f70e19e..6b5dc288 100644 --- a/_server/editor_file.demo.js +++ b/_server/editor_file.demo.js @@ -27,19 +27,19 @@ //callback(err:String) editor_file.editItem = function(editor,id,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (isset(callback)) callback([ {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"}, {'items':{'cls': "只能取keys items constants tools\n$range(thiseval in ['keys','items','constants','tools'])$end", 'name': '', 'text': ''},'itemEffect':'','itemEffectTip':''}, - null); + null]); //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items } //callback(obj,commentObj,err:String) editor_file.editEnemy = function(editor,id,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (isset(callback)) callback([ {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, "bomb": false}, {'name': '名称', 'hp': '生命值', 'atk': '攻击力', 'def': '防御力', 'money': '金币', 'experience': '经验', 'special': '特殊属性\n1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:4连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨\n多个属性例如用010411表示先攻2连击吸血\n模仿怪的攻防设为0就好\n', 'value': '特殊属性的数值\n领域怪需要加value表示领域伤害的数值\n吸血怪需要在后面添加value代表吸血比例', 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉'}, - null); + null]); } //callback(obj,commentObj,err:String) @@ -47,10 +47,10 @@ editor_file.editLoc = function(editor,x,y,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (isset(callback)) callback([ {"events":['\t[老人,man]这些是本样板支持的所有的道具。\n\n道具分为三类:items, constants, tools。\nitems 为即捡即用类道具,例如宝石、血瓶、剑盾等。\nconstants 为永久道具,例如怪物手册、楼层传送器、幸运金币等。\ntools 为消耗类道具,例如破墙镐、炸弹、中心对称飞行器等。\n\n后两类道具在工具栏中可以看到并使用。', '\t[老人,man]有关道具效果,定义在items.js中。\n目前大多数道具已有默认行为,如有自定义的需求则需在items.js中修改代码。', '\t[老人,man]constants 和 tools 各最多只允许12种,多了会导致图标溢出。', '\t[老人,man]拾取道具结束后可触发 afterGetItem 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。', {'type': 'hide', 'time': 500}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, {"events":['', '', '', '', {'type': '', 'time': ' // 消失 \n // 守着门的老人 '}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, - null); + null]); } //callback(obj,commentObj,err:String) @@ -58,10 +58,10 @@ editor_file.editFloor = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (isset(callback)) callback([ {'floorId': 'sample0', 'title': '样板 0 层', 'name': '0', 'canFlyTo': True, 'canUseQuickShop': True, 'defaultGround': 'ground', 'firstArrive': ['\t[样板提示]首次到达某层可以触发 firstArrive 事件,该事件可类似于RMXP中的“自动执行脚本”。\n\n本事件支持一切的事件类型,常常用来触发对话,例如:', '\t[hero]我是谁?我从哪来?我又要到哪去?', '\t[仙子,fairy]你问我...?我也不知道啊...', '本层主要对道具、门、怪物等进行介绍,有关事件的各种信息在下一层会有更为详细的说明。']}, {'floorId': '// 这里需要改楼层名,请和文件名及下面的floorId保持完全一致 // 楼层唯一标识符仅能由字母、数字、下划线组成,且不能由数字开头 // 推荐用法:第20层就用MT20,第38层就用MT38,地下6层就用MT_6(用下划线代替负号),隐藏3层用MT3h(h表示隐藏),等等 \n // 楼层唯一标识符,需要和名字完全一致 ', 'title': ' // 楼层中文名 ', 'name': ' // 显示在状态栏中的层数 ', 'canFlyTo': ' // 该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) ', 'canUseQuickShop': ' // 该层是否允许使用快捷商店 ', 'defaultGround': ' // 默认地面的图块ID(terrains中) \n // 地图数据,需要是13x13,建议使用地图生成器来生成 ', 'firstArrive': ['', '', '', ' // 该楼的所有可能事件列表 \n // 守着道具的老人 ']}, - null); + null]); } //callback(obj,commentObj,err:String) @@ -71,10 +71,10 @@ editor_file.editTower = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 - if (isset(callback)) callback( + if (isset(callback)) callback([ {'main': {'useCompress': False, 'floorIds': ['sample0', 'sample1', 'sample2', 'test']}, 'firstData': {'title': '魔塔样板', 'name': 'template', 'version': 'Ver 1.0.0 (Beta)', 'floorId': 'sample0', 'hero': {'name': '阳光', 'lv': 1, 'hp': 2000, 'atk': 100, 'def': 100, 'mdef': 100, 'money': 100, 'experience': 0, 'items': {'keys': {'yellowKey': 0, 'blueKey': 0, 'redKey': 0}, 'constants': {}, 'tools': {}}, 'flyRange': [], 'loc': {'direction': 'up', 'x': 6, 'y': 10}, 'flags': {'poison': False, 'weak': False, 'curse': False}}, 'startText': ['Hi,欢迎来到 HTML5 魔塔样板!\n\n本样板由艾之葵制作,可以让你在不会写任何代码\n的情况下也能做出属于自己的H5魔塔!', '这里游戏开始时的剧情。\n定义在data.js的startText处。\n\n你可以在这里写上自己的内容。', '赶快来试一试吧!'], 'shops': {'moneyShop1': {'name': '贪婪之神', 'icon': 'blueShop', 'textInList': '1F金币商店', 'use': 'money', 'need': '20+10*times*(times+1)', 'text': '勇敢的武士啊,给我${need}金币就可以:', 'choices': [{'text': '生命+800', 'effect': 'status:hp+=800'}, {'text': '攻击+4', 'effect': 'status:atk+=4'}, {'text': '防御+4', 'effect': 'status:def+=4'}, {'text': '魔防+10', 'effect': 'status:mdef+=10'}]}, 'expShop1': {'name': '经验之神', 'icon': 'pinkShop', 'textInList': '1F经验商店', 'use': 'experience', 'need': '-1', 'text': '勇敢的武士啊,给我若干经验就可以:', 'choices': [{'text': '等级+1', 'need': '100', 'effect': 'status:lv+=1;status:hp+=1000;status:atk+=7;status:def+=7'}, {'text': '攻击+5', 'need': '30', 'effect': 'status:atk+=5'}, {'text': '防御+5', 'need': '30', 'effect': 'status:def+=5'}]}}, 'levelUp': [{}, {'need': 20, 'name': '第二级', 'effect': 'status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10'}, {'need': 40, 'effect': 'function () {\n core.drawText("恭喜升级!");\n core.status.hero.hp *= 2;\n core.status.hero.atk += 100;\n core.status.hero.def += 100;\n }'}]}, 'values': {'HPMAX': 999999, 'lavaDamage': 100, 'poisonDamage': 10, 'weakValue': 20, 'redJewel': 3, 'blueJewel': 3, 'greenJewel': 5, 'redPotion': 100, 'bluePotion': 250, 'yellowPotion': 500, 'greenPotion': 800, 'sword1': 10, 'shield1': 10, 'sword2': 20, 'shield2': 20, 'sword3': 40, 'shield3': 40, 'sword4': 80, 'shield4': 80, 'sword5': 160, 'shield5': 160, 'moneyPocket': 500, 'breakArmor': 0.9, 'counterAttack': 0.1, 'purify': 3, 'hatred': 2, 'animateSpeed': 500}, 'flags': {'enableNegativeDamage': True, 'enableFloor': False, 'enableLv': True, 'enableMDef': True, 'enableMoney': True, 'enableExperience': True, 'enableLevelUp': False, 'enableDebuff': True, 'flyNearStair': True, 'pickaxeFourDirections': True, 'bombFourDirections': True, 'bigKeyIsBox': False, 'startDirectly': False, 'canOpenBattleAnimate': True, 'showBattleAnimateConfirm': True, 'battleAnimate': True, 'displayEnemyDamage': True, 'displayExtraDamage': False, 'enableGentleClick': True, 'portalWithoutTrigger': True, 'potionWhileRouting': False}}, {'main': {'useCompress': ' // 是否使用压缩文件 // 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 // 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 // 如果要进行剧本的修改请务必将其改成false。 \n // 在这里按顺序放所有的楼层;其顺序直接影响到楼层传送器的顺序和上楼器/下楼器的顺序 ', 'floorIds': ['', '', '', '']}, 'firstData': {'title': ' // 游戏名,将显示在标题页面以及切换楼层的界面中 ', 'name': ' // 游戏的唯一英文标识符。由英文、数字、下划线组成,不能超过20个字符。 ', 'version': ' // 当前游戏版本;版本不一致的存档不能通用。 ', 'floorId': ' // 初始楼层ID \n // 勇士初始数据 ', 'hero': {'name': ' // 勇士名;可以改成喜欢的 ', 'lv': ' // 初始等级,该项必须为正整数 ', 'hp': ' // 初始生命值 ', 'atk': ' // 初始攻击 ', 'def': ' // 初始防御 ', 'mdef': ' // 初始魔防 ', 'money': ' // 初始金币 ', 'experience': ' // 初始经验 \n // 初始道具个数 ', 'items': {'keys': {'yellowKey': '', 'blueKey': '', 'redKey': ''}, 'constants': '', 'tools': ''}, 'flyRange': ' // 初始可飞的楼层;一般留空数组即可 ', 'loc': {'direction': '', 'x': '', 'y': ' // 勇士初始位置 \n // 游戏过程中的变量或flags '}, 'flags': {'poison': ' // 毒 ', 'weak': ' // 衰 ', 'curse': ' // 咒 \n // 游戏开始前剧情。如果无剧情直接留一个空数组即可。 '}}, 'startText': ['', '', ' // 定义全局商店(即快捷商店) \n // 商店唯一ID '], 'shops': {'moneyShop1': {'name': ' // 商店名称(标题) ', 'icon': ' // 商店图标,blueShop为蓝色商店,pinkShop为粉色商店 ', 'textInList': ' // 在快捷商店栏中显示的名称 ', 'use': ' // 商店所要使用的。只能是"money"或"experience"。 ', 'need': ' // 商店需要的金币/经验数值;可以是一个表达式,以times作为参数计算。 // 这里用到的times为该商店的已经的访问次数。首次访问该商店时times的值为0。 // 上面的例子是50层商店的计算公式。你也可以写任意其他的计算公式,只要以times作为参数即可。 // 例如: "need": "25" 就是恒定需要25金币的商店; "need": "20+2*times" 就是第一次访问要20金币,以后每次递增2金币的商店。 // 如果是对于每个选项有不同的计算公式,写 "need": "-1" 即可。可参见下面的经验商店。 ', 'text': ' // 显示的文字,需手动加换行符。可以使用${need}表示上面的need值。 \n // 商店的选项 ', 'choices': [{'text': '', 'effect': ' // 如果有多个effect以分号分开,参见下面的经验商店 '}, {'text': '', 'effect': ''}, {'text': '', 'effect': ''}, {'text': '', 'effect': ' // effect只能对status和item进行操作,不能修改flag值。 // 必须是X+=Y的形式,其中Y可以是一个表达式,以status:xxx或item:xxx为参数 // 其他effect样例: // "item:yellowKey+=1" 黄钥匙+1 // "item:pickaxe+=3" 破墙镐+3 // "status:hp+=2*(status:atk+status:def)" 将生命提升攻防和的数值的两倍 \n // 商店唯一ID '}]}, 'expShop1': {'name': '', 'icon': '', 'textInList': '', 'use': ' // 该商店使用的是经验进行计算 ', 'need': ' // 如果是对于每个选项所需要的数值不同,这里直接写-1,然后下面选项里给定具体数值 ', 'text': ' // 在choices中写need,可以针对每个选项都有不同的需求。 // 这里的need同样可以以times作为参数,比如 "need": "100+20*times" ', 'choices': [{'text': '', 'need': '', 'effect': ' // 多个effect直接以分号分开即可。如上面的意思是生命+1000,攻击+7,防御+7。 '}, {'text': '', 'need': '', 'effect': ''}, {'text': '', 'need': '', 'effect': ' // 经验升级所需要的数值,是一个数组 '}]}}, 'levelUp': [' // 第一项为初始等级,可以简单留空,也可以写name // 每一个里面可以含有三个参数 name, need, effect // need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 // name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 // effect为本次升级所执行的操作,可由若干项组成,由分号分开 // 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 ', {'need': '', 'name': '', 'effect': ' // 先将生命提升攻防和的2倍;再将攻击+10,防御+10 // effect也允许写一个function,代表本次升级将会执行的操作 '}, {'need': '', 'effect': ' // 依次往下写需要的数值即可 \n // 各种数值;一些数值可以在这里设置 \n /****** 角色相关 ******/ '}]}, 'values': {'HPMAX': ' // HP上限;-1则无上限 ', 'lavaDamage': ' // 经过血网受到的伤害 ', 'poisonDamage': ' // 中毒后每步受到的伤害 ', 'weakValue': ' // 衰弱状态下攻防减少的数值 /****** 道具相关 ******/ ', 'redJewel': ' // 红宝石加攻击的数值 ', 'blueJewel': ' // 蓝宝石加防御的数值 ', 'greenJewel': ' // 绿宝石加魔防的数值 ', 'redPotion': ' // 红血瓶加血数值 ', 'bluePotion': ' // 蓝血瓶加血数值 ', 'yellowPotion': ' // 黄血瓶加血数值 ', 'greenPotion': ' // 绿血瓶加血数值 ', 'sword1': ' // 铁剑加攻数值 ', 'shield1': ' // 铁盾加防数值 ', 'sword2': ' // 银剑加攻数值 ', 'shield2': ' // 银盾加防数值 ', 'sword3': ' // 骑士剑加攻数值 ', 'shield3': ' // 骑士盾加防数值 ', 'sword4': ' // 圣剑加攻数值 ', 'shield4': ' // 圣盾加防数值 ', 'sword5': ' // 神圣剑加攻数值 ', 'shield5': ' // 神圣盾加防数值 ', 'moneyPocket': ' // 金钱袋加金币的数值 /****** 怪物相关 ******/ ', 'breakArmor': ' // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) ', 'counterAttack': ' // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) ', 'purify': ' // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) ', 'hatred': ' // 仇恨属性中,每杀死一个怪物获得的仇恨值 /****** 系统相关 ******/ ', 'animateSpeed': ' // 动画时间 \n // 系统FLAG,在游戏运行中中请不要修改它。 \n /****** 角色状态相关 ******/ '}, 'flags': {'enableNegativeDamage': ' // 是否支持负伤害(回血) ', 'enableFloor': ' // 是否在状态栏显示当前楼层 ', 'enableLv': ' // 是否在状态栏显示当前等级 ', 'enableMDef': ' // 是否在状态栏及战斗界面显示魔防(护盾) ', 'enableMoney': ' // 是否在状态栏、怪物手册及战斗界面显示金币 ', 'enableExperience': ' // 是否在状态栏、怪物手册及战斗界面显示经验 ', 'enableLevelUp': ' // 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false ', 'enableDebuff': ' // 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff ////// 上述的几个开关将直接影响状态栏的显示效果 ////// /****** 道具相关 ******/ ', 'flyNearStair': ' // 是否需要在楼梯边使用传送器 ', 'pickaxeFourDirections': ' // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 ', 'bombFourDirections': ' // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) ', 'bigKeyIsBox': ' // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 /****** 系统相关 ******/ ', 'startDirectly': ' // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 ', 'canOpenBattleAnimate': ' // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false ', 'showBattleAnimateConfirm': ' // 是否在游戏开始时提供“是否开启战斗动画”的选项 ', 'battleAnimate': ' // 是否默认显示战斗动画;用户可以手动在菜单栏中开关 ', 'displayEnemyDamage': ' // 是否地图怪物显伤;用户可以手动在菜单栏中开关 ', 'displayExtraDamage': ' // 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 ', 'enableGentleClick': ' // 是否允许轻触(获得面前物品) ', 'portalWithoutTrigger': ' // 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 ', 'potionWhileRouting': ' // 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 '}}, - null); + null]); } //callback(obj,commentObj,err:String) diff --git a/_server/editor_file.js b/_server/editor_file.js index d458b341..d547915a 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -1,11 +1,20 @@ (function(){ editor_file = {}; + (function(){ + var script = document.createElement('script'); + script.src = 'comment.js'; + document.body.appendChild(script); + script.onload = function () { + editor_file.comment=comment_c456ea59_6018_45ef_8bcc_211a24c627dc; + delete(comment_c456ea59_6018_45ef_8bcc_211a24c627dc); + } + })(); editor_file.getFloorFileList = function(editor,callback){ if (!isset(callback)) throw('未设置callback'); var fs = editor.fs; - fs.readdir('libs/project/floors',function(err, data){ + fs.readdir('project/floors',function(err, data){ callback([data,err]); }); } @@ -14,7 +23,7 @@ //filename不含'/'不含'.js' if (!isset(callback)) throw('未设置callback'); var fs = editor.fs; - fs.readFile('libs/project/floors/'+filename+'.js','utf-8',function(err, data){ + fs.readFile('project/floors/'+filename+'.js','utf-8',function(err, data){ if (err!=null){callback(err);return;} data=data.split('='); data=[data[0],data.slice(1).join('=')]; @@ -39,7 +48,7 @@ if (!isset(editor.currentFloorId) || !isset(editor.currentfloorData)) { callback('未选中文件或无数据'); } - var filename = 'libs/project/floors/' + editor.currentFloorId + '.js'; + var filename = 'project/floors/' + editor.currentFloorId + '.js'; var datastr = ['main.floors.' , editor.currentFloorId , '=\n{']; for(var ii in editor.currentfloorData) if (editor.currentfloorData.hasOwnProperty(ii)) { @@ -75,17 +84,18 @@ var change = -1; for(var ii in core.maps.blocksInfo){ if (ii==idnum) { - if (info.idnum==idnum){change=ii;break;}//修改id + //暂时只允许创建新的不允许修改已有的 + //if (info.idnum==idnum){change=ii;break;}//修改id callback('idnum重复了'); return; } if (core.maps.blocksInfo[ii].id==id) { - if (info.id==id){change=ii;break;}//修改idnum + //if (info.id==id){change=ii;break;}//修改idnum callback('id重复了'); return; } } - throw('需要改实现') + /* if (change!=-1 && change!=idnum){//修改idnum core.maps.blocksInfo[idnum] = core.maps.blocksInfo[change]; delete(core.maps.blocksInfo[change]); @@ -102,8 +112,20 @@ core.maps.blocksInfo[idnum]={'cls': info.images, 'id':id}; core.icons.icons[info.images][id]=info.y; } + */ + var templist=[]; + var tempcallback = function (err) { + templist.push(err); + if (templist.length ==2 ) { + if (templist[0]!=null || templist[1]!=null) + callback((templist[0]||'')+'\n'+(templist[1]||'')); + else + callback(null); + } + } + saveSetting('maps',[["add","['"+idnum+"']",{'cls': info.images, 'id':id}]],tempcallback); + saveSetting('icons',[["add","['"+info.images+"']['"+id+"']",info.y]],tempcallback); - throw('尚未实现:save(core.maps.blocksInfo,map.js);save(core.icons.icons,icons.js);') callback(null); } //callback(err:String) @@ -116,10 +138,10 @@ 为[]时只查询不修改 */ if (!isset(callback)) throw('未设置callback'); - callback( + callback([ {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"}, - {'items':{'cls': "/*只能取keys items constants tools\\n$range(thiseval in ['keys','items','constants','tools'])\\n*/", 'name': '', 'text': ''},'itemEffect':'','itemEffectTip':''}, - null); + editor_file.comment.items, + null]); //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items } @@ -127,10 +149,10 @@ editor_file.editEnemy = function(editor,id,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); - callback( + callback([ {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, "bomb": false}, - {'name': '名称', 'hp': '生命值', 'atk': '攻击力', 'def': '防御力', 'money': '金币', 'experience': '经验', 'special': '特殊属性\n1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:4连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨\n多个属性例如用010411表示先攻2连击吸血\n模仿怪的攻防设为0就好\n', 'value': '特殊属性的数值\n领域怪需要加value表示领域伤害的数值\n吸血怪需要在后面添加value代表吸血比例', 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉'}, - null); + editor_file.comment.enemys, + null]); } //callback(obj,commentObj,err:String) @@ -139,10 +161,10 @@ editor_file.editLoc = function(editor,x,y,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); - callback( + callback([ {"events":['\t[老人,man]这些是本样板支持的所有的道具。\n\n道具分为三类:items, constants, tools。\nitems 为即捡即用类道具,例如宝石、血瓶、剑盾等。\nconstants 为永久道具,例如怪物手册、楼层传送器、幸运金币等。\ntools 为消耗类道具,例如破墙镐、炸弹、中心对称飞行器等。\n\n后两类道具在工具栏中可以看到并使用。', '\t[老人,man]有关道具效果,定义在items.js中。\n目前大多数道具已有默认行为,如有自定义的需求则需在items.js中修改代码。', '\t[老人,man]constants 和 tools 各最多只允许12种,多了会导致图标溢出。', '\t[老人,man]拾取道具结束后可触发 afterGetItem 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。', {'type': 'hide', 'time': 500}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, {"events":['', '', '', '', {'type': '', 'time': ' // 消失 \n // 守着门的老人 '}],"changeFloor":"","afterBattle":"","afterGetItem":"","afterOpenDoor":""}, - null); + null]); } //callback(obj,commentObj,err:String) @@ -151,10 +173,10 @@ editor_file.editFloor = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); - callback( + callback([ {'floorId': 'sample0', 'title': '样板 0 层', 'name': '0', 'canFlyTo': True, 'canUseQuickShop': True, 'defaultGround': 'ground', 'firstArrive': ['\t[样板提示]首次到达某层可以触发 firstArrive 事件,该事件可类似于RMXP中的“自动执行脚本”。\n\n本事件支持一切的事件类型,常常用来触发对话,例如:', '\t[hero]我是谁?我从哪来?我又要到哪去?', '\t[仙子,fairy]你问我...?我也不知道啊...', '本层主要对道具、门、怪物等进行介绍,有关事件的各种信息在下一层会有更为详细的说明。']}, {'floorId': '// 这里需要改楼层名,请和文件名及下面的floorId保持完全一致 // 楼层唯一标识符仅能由字母、数字、下划线组成,且不能由数字开头 // 推荐用法:第20层就用MT20,第38层就用MT38,地下6层就用MT_6(用下划线代替负号),隐藏3层用MT3h(h表示隐藏),等等 \n // 楼层唯一标识符,需要和名字完全一致 ', 'title': ' // 楼层中文名 ', 'name': ' // 显示在状态栏中的层数 ', 'canFlyTo': ' // 该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) ', 'canUseQuickShop': ' // 该层是否允许使用快捷商店 ', 'defaultGround': ' // 默认地面的图块ID(terrains中) \n // 地图数据,需要是13x13,建议使用地图生成器来生成 ', 'firstArrive': ['', '', '', ' // 该楼的所有可能事件列表 \n // 守着道具的老人 ']}, - null); + null]); } //callback(obj,commentObj,err:String) @@ -165,10 +187,10 @@ editor_file.editTower = function(editor,actionList,callback){ //obj形式同callback的obj,为null或undefined时只查询不修改 if (!isset(callback)) throw('未设置callback'); - callback( + callback([ {'main': {'useCompress': False, 'floorIds': ['sample0', 'sample1', 'sample2', 'test']}, 'firstData': {'title': '魔塔样板', 'name': 'template', 'version': 'Ver 1.0.0 (Beta)', 'floorId': 'sample0', 'hero': {'name': '阳光', 'lv': 1, 'hp': 2000, 'atk': 100, 'def': 100, 'mdef': 100, 'money': 100, 'experience': 0, 'items': {'keys': {'yellowKey': 0, 'blueKey': 0, 'redKey': 0}, 'constants': {}, 'tools': {}}, 'flyRange': [], 'loc': {'direction': 'up', 'x': 6, 'y': 10}, 'flags': {'poison': False, 'weak': False, 'curse': False}}, 'startText': ['Hi,欢迎来到 HTML5 魔塔样板!\n\n本样板由艾之葵制作,可以让你在不会写任何代码\n的情况下也能做出属于自己的H5魔塔!', '这里游戏开始时的剧情。\n定义在data.js的startText处。\n\n你可以在这里写上自己的内容。', '赶快来试一试吧!'], 'shops': {'moneyShop1': {'name': '贪婪之神', 'icon': 'blueShop', 'textInList': '1F金币商店', 'use': 'money', 'need': '20+10*times*(times+1)', 'text': '勇敢的武士啊,给我${need}金币就可以:', 'choices': [{'text': '生命+800', 'effect': 'status:hp+=800'}, {'text': '攻击+4', 'effect': 'status:atk+=4'}, {'text': '防御+4', 'effect': 'status:def+=4'}, {'text': '魔防+10', 'effect': 'status:mdef+=10'}]}, 'expShop1': {'name': '经验之神', 'icon': 'pinkShop', 'textInList': '1F经验商店', 'use': 'experience', 'need': '-1', 'text': '勇敢的武士啊,给我若干经验就可以:', 'choices': [{'text': '等级+1', 'need': '100', 'effect': 'status:lv+=1;status:hp+=1000;status:atk+=7;status:def+=7'}, {'text': '攻击+5', 'need': '30', 'effect': 'status:atk+=5'}, {'text': '防御+5', 'need': '30', 'effect': 'status:def+=5'}]}}, 'levelUp': [{}, {'need': 20, 'name': '第二级', 'effect': 'status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10'}, {'need': 40, 'effect': 'function () {\n core.drawText("恭喜升级!");\n core.status.hero.hp *= 2;\n core.status.hero.atk += 100;\n core.status.hero.def += 100;\n }'}]}, 'values': {'HPMAX': 999999, 'lavaDamage': 100, 'poisonDamage': 10, 'weakValue': 20, 'redJewel': 3, 'blueJewel': 3, 'greenJewel': 5, 'redPotion': 100, 'bluePotion': 250, 'yellowPotion': 500, 'greenPotion': 800, 'sword1': 10, 'shield1': 10, 'sword2': 20, 'shield2': 20, 'sword3': 40, 'shield3': 40, 'sword4': 80, 'shield4': 80, 'sword5': 160, 'shield5': 160, 'moneyPocket': 500, 'breakArmor': 0.9, 'counterAttack': 0.1, 'purify': 3, 'hatred': 2, 'animateSpeed': 500}, 'flags': {'enableNegativeDamage': True, 'enableFloor': False, 'enableLv': True, 'enableMDef': True, 'enableMoney': True, 'enableExperience': True, 'enableLevelUp': False, 'enableDebuff': True, 'flyNearStair': True, 'pickaxeFourDirections': True, 'bombFourDirections': True, 'bigKeyIsBox': False, 'startDirectly': False, 'canOpenBattleAnimate': True, 'showBattleAnimateConfirm': True, 'battleAnimate': True, 'displayEnemyDamage': True, 'displayExtraDamage': False, 'enableGentleClick': True, 'portalWithoutTrigger': True, 'potionWhileRouting': False}}, {'main': {'useCompress': ' // 是否使用压缩文件 // 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 // 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 // 如果要进行剧本的修改请务必将其改成false。 \n // 在这里按顺序放所有的楼层;其顺序直接影响到楼层传送器的顺序和上楼器/下楼器的顺序 ', 'floorIds': ['', '', '', '']}, 'firstData': {'title': ' // 游戏名,将显示在标题页面以及切换楼层的界面中 ', 'name': ' // 游戏的唯一英文标识符。由英文、数字、下划线组成,不能超过20个字符。 ', 'version': ' // 当前游戏版本;版本不一致的存档不能通用。 ', 'floorId': ' // 初始楼层ID \n // 勇士初始数据 ', 'hero': {'name': ' // 勇士名;可以改成喜欢的 ', 'lv': ' // 初始等级,该项必须为正整数 ', 'hp': ' // 初始生命值 ', 'atk': ' // 初始攻击 ', 'def': ' // 初始防御 ', 'mdef': ' // 初始魔防 ', 'money': ' // 初始金币 ', 'experience': ' // 初始经验 \n // 初始道具个数 ', 'items': {'keys': {'yellowKey': '', 'blueKey': '', 'redKey': ''}, 'constants': '', 'tools': ''}, 'flyRange': ' // 初始可飞的楼层;一般留空数组即可 ', 'loc': {'direction': '', 'x': '', 'y': ' // 勇士初始位置 \n // 游戏过程中的变量或flags '}, 'flags': {'poison': ' // 毒 ', 'weak': ' // 衰 ', 'curse': ' // 咒 \n // 游戏开始前剧情。如果无剧情直接留一个空数组即可。 '}}, 'startText': ['', '', ' // 定义全局商店(即快捷商店) \n // 商店唯一ID '], 'shops': {'moneyShop1': {'name': ' // 商店名称(标题) ', 'icon': ' // 商店图标,blueShop为蓝色商店,pinkShop为粉色商店 ', 'textInList': ' // 在快捷商店栏中显示的名称 ', 'use': ' // 商店所要使用的。只能是"money"或"experience"。 ', 'need': ' // 商店需要的金币/经验数值;可以是一个表达式,以times作为参数计算。 // 这里用到的times为该商店的已经的访问次数。首次访问该商店时times的值为0。 // 上面的例子是50层商店的计算公式。你也可以写任意其他的计算公式,只要以times作为参数即可。 // 例如: "need": "25" 就是恒定需要25金币的商店; "need": "20+2*times" 就是第一次访问要20金币,以后每次递增2金币的商店。 // 如果是对于每个选项有不同的计算公式,写 "need": "-1" 即可。可参见下面的经验商店。 ', 'text': ' // 显示的文字,需手动加换行符。可以使用${need}表示上面的need值。 \n // 商店的选项 ', 'choices': [{'text': '', 'effect': ' // 如果有多个effect以分号分开,参见下面的经验商店 '}, {'text': '', 'effect': ''}, {'text': '', 'effect': ''}, {'text': '', 'effect': ' // effect只能对status和item进行操作,不能修改flag值。 // 必须是X+=Y的形式,其中Y可以是一个表达式,以status:xxx或item:xxx为参数 // 其他effect样例: // "item:yellowKey+=1" 黄钥匙+1 // "item:pickaxe+=3" 破墙镐+3 // "status:hp+=2*(status:atk+status:def)" 将生命提升攻防和的数值的两倍 \n // 商店唯一ID '}]}, 'expShop1': {'name': '', 'icon': '', 'textInList': '', 'use': ' // 该商店使用的是经验进行计算 ', 'need': ' // 如果是对于每个选项所需要的数值不同,这里直接写-1,然后下面选项里给定具体数值 ', 'text': ' // 在choices中写need,可以针对每个选项都有不同的需求。 // 这里的need同样可以以times作为参数,比如 "need": "100+20*times" ', 'choices': [{'text': '', 'need': '', 'effect': ' // 多个effect直接以分号分开即可。如上面的意思是生命+1000,攻击+7,防御+7。 '}, {'text': '', 'need': '', 'effect': ''}, {'text': '', 'need': '', 'effect': ' // 经验升级所需要的数值,是一个数组 '}]}}, 'levelUp': [' // 第一项为初始等级,可以简单留空,也可以写name // 每一个里面可以含有三个参数 name, need, effect // need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 // name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 // effect为本次升级所执行的操作,可由若干项组成,由分号分开 // 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 ', {'need': '', 'name': '', 'effect': ' // 先将生命提升攻防和的2倍;再将攻击+10,防御+10 // effect也允许写一个function,代表本次升级将会执行的操作 '}, {'need': '', 'effect': ' // 依次往下写需要的数值即可 \n // 各种数值;一些数值可以在这里设置 \n /****** 角色相关 ******/ '}]}, 'values': {'HPMAX': ' // HP上限;-1则无上限 ', 'lavaDamage': ' // 经过血网受到的伤害 ', 'poisonDamage': ' // 中毒后每步受到的伤害 ', 'weakValue': ' // 衰弱状态下攻防减少的数值 /****** 道具相关 ******/ ', 'redJewel': ' // 红宝石加攻击的数值 ', 'blueJewel': ' // 蓝宝石加防御的数值 ', 'greenJewel': ' // 绿宝石加魔防的数值 ', 'redPotion': ' // 红血瓶加血数值 ', 'bluePotion': ' // 蓝血瓶加血数值 ', 'yellowPotion': ' // 黄血瓶加血数值 ', 'greenPotion': ' // 绿血瓶加血数值 ', 'sword1': ' // 铁剑加攻数值 ', 'shield1': ' // 铁盾加防数值 ', 'sword2': ' // 银剑加攻数值 ', 'shield2': ' // 银盾加防数值 ', 'sword3': ' // 骑士剑加攻数值 ', 'shield3': ' // 骑士盾加防数值 ', 'sword4': ' // 圣剑加攻数值 ', 'shield4': ' // 圣盾加防数值 ', 'sword5': ' // 神圣剑加攻数值 ', 'shield5': ' // 神圣盾加防数值 ', 'moneyPocket': ' // 金钱袋加金币的数值 /****** 怪物相关 ******/ ', 'breakArmor': ' // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) ', 'counterAttack': ' // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) ', 'purify': ' // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) ', 'hatred': ' // 仇恨属性中,每杀死一个怪物获得的仇恨值 /****** 系统相关 ******/ ', 'animateSpeed': ' // 动画时间 \n // 系统FLAG,在游戏运行中中请不要修改它。 \n /****** 角色状态相关 ******/ '}, 'flags': {'enableNegativeDamage': ' // 是否支持负伤害(回血) ', 'enableFloor': ' // 是否在状态栏显示当前楼层 ', 'enableLv': ' // 是否在状态栏显示当前等级 ', 'enableMDef': ' // 是否在状态栏及战斗界面显示魔防(护盾) ', 'enableMoney': ' // 是否在状态栏、怪物手册及战斗界面显示金币 ', 'enableExperience': ' // 是否在状态栏、怪物手册及战斗界面显示经验 ', 'enableLevelUp': ' // 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false ', 'enableDebuff': ' // 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff ////// 上述的几个开关将直接影响状态栏的显示效果 ////// /****** 道具相关 ******/ ', 'flyNearStair': ' // 是否需要在楼梯边使用传送器 ', 'pickaxeFourDirections': ' // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 ', 'bombFourDirections': ' // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) ', 'bigKeyIsBox': ' // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 /****** 系统相关 ******/ ', 'startDirectly': ' // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 ', 'canOpenBattleAnimate': ' // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false ', 'showBattleAnimateConfirm': ' // 是否在游戏开始时提供“是否开启战斗动画”的选项 ', 'battleAnimate': ' // 是否默认显示战斗动画;用户可以手动在菜单栏中开关 ', 'displayEnemyDamage': ' // 是否地图怪物显伤;用户可以手动在菜单栏中开关 ', 'displayExtraDamage': ' // 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 ', 'enableGentleClick': ' // 是否允许轻触(获得面前物品) ', 'portalWithoutTrigger': ' // 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 ', 'potionWhileRouting': ' // 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 '}}, - null); + null]); } //callback(obj,commentObj,err:String) @@ -200,6 +222,7 @@ } var saveSetting = function(file,actionList,callback) { + throw('尚未实现'); if (file=='icons') {} if (file=='maps') {} if (file=='items') {} From 9197a4d727d07d58370eacdd8c992fe435a46750 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 6 Jan 2018 22:25:19 +0800 Subject: [PATCH 018/102] =?UTF-8?q?=E5=88=86=E7=A6=BB=E4=BA=86=E6=A5=BC?= =?UTF-8?q?=E5=B1=82=E6=96=87=E4=BB=B6=E4=B9=8B=E5=A4=96=E7=9A=84=E6=95=B0?= =?UTF-8?q?=E6=8D=AE=E7=9A=84=E6=B3=A8=E9=87=8A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/editor_file.js | 93 +++++++++++---- drawMapGUI.html | 14 ++- {_server => project}/comment.js | 4 +- project/data.comment.js | 165 +++++++++++++++++++++++++++ project/data.js | 109 ++++++++++-------- project/floors/sample1.js | 4 +- project/items.js | 14 ++- project/maps.comment.js | 193 ++++++++++++++++++++++++++++++++ test_main_init_mode.html | 38 ++++--- 9 files changed, 533 insertions(+), 101 deletions(-) rename {_server => project}/comment.js (87%) create mode 100644 project/data.comment.js create mode 100644 project/maps.comment.js diff --git a/_server/editor_file.js b/_server/editor_file.js index d547915a..42942c2d 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -1,15 +1,32 @@ (function(){ editor_file = {}; + (function(){ var script = document.createElement('script'); - script.src = 'comment.js'; + if (window.location.href.indexOf('_server')!==-1) + script.src = '../project/comment.js'; + else + script.src = 'project/comment.js'; document.body.appendChild(script); script.onload = function () { editor_file.comment=comment_c456ea59_6018_45ef_8bcc_211a24c627dc; delete(comment_c456ea59_6018_45ef_8bcc_211a24c627dc); } })(); + (function(){ + var script = document.createElement('script'); + if (window.location.href.indexOf('_server')!==-1) + script.src = '../project/data.comment.js'; + else + script.src = 'project/data.comment.js'; + document.body.appendChild(script); + script.onload = function () { + editor_file.dataComment=data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d; + delete(data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d); + } + })(); + editor_file.getFloorFileList = function(editor,callback){ if (!isset(callback)) throw('未设置callback'); @@ -38,24 +55,24 @@ return; } editor.currentFloorId = floorId; - editor.currentfloorData = floorData; + editor.currentFloorData = floorData; callback(null) }); } //callback(err:String) editor_file.saveFloorFile = function(editor,callback){ if (!isset(callback)) throw('未设置callback'); - if (!isset(editor.currentFloorId) || !isset(editor.currentfloorData)) { + if (!isset(editor.currentFloorId) || !isset(editor.currentFloorData)) { callback('未选中文件或无数据'); } var filename = 'project/floors/' + editor.currentFloorId + '.js'; var datastr = ['main.floors.' , editor.currentFloorId , '=\n{']; - for(var ii in editor.currentfloorData) - if (editor.currentfloorData.hasOwnProperty(ii)) { + for(var ii in editor.currentFloorData) + if (editor.currentFloorData.hasOwnProperty(ii)) { if (ii=='map') - datastr=datastr.concat(['\n"',ii,'": [\n',formatMap(editor.currentfloorData[ii]),'\n],']); + datastr=datastr.concat(['\n"',ii,'": [\n',formatMap(editor.currentFloorData[ii]),'\n],']); else - datastr=datastr.concat(['\n"',ii,'": ',JSON.stringify(editor.currentfloorData[ii],null,4),',']); + datastr=datastr.concat(['\n"',ii,'": ',JSON.stringify(editor.currentFloorData[ii],null,4),',']); } datastr=datastr.concat(['\n}']); datastr=datastr.join(''); @@ -67,10 +84,10 @@ editor_file.saveFloorFileAs = function(editor,saveAsFilename,callback){ //saveAsFilename不含'/'不含'.js' if (!isset(callback)) throw('未设置callback'); - if (!isset(editor.currentfloorData)) { + if (!isset(editor.currentFloorData)) { callback('无数据'); } - editor.currentfloorData.floorId=saveAsFilename; + editor.currentFloorData.floorId=saveAsFilename; editor.currentFloorId=saveAsFilename; editor_file.saveFloorFile(editor,callback); } @@ -138,23 +155,53 @@ 为[]时只查询不修改 */ if (!isset(callback)) throw('未设置callback'); - callback([ - {'items':{'cls': 'items', 'name': '红宝石'},'itemEffect':'core.status.hero.atk += core.values.redJewel','itemEffectTip':"',攻击+'+core.values.redJewel"}, - editor_file.comment.items, - null]); - //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items + if (isset(actionList) && actionList.length > 0){ + actionList.forEach(function (value) { + var tempindex = value[1].indexOf(']')+1; + value[1] = [value[1].slice(0,tempindex),"['"+id+"']",value[1].slice(tempindex)].join(''); + }); + saveSetting('items',actionList,function (err) { + callback([ + {'items':editor.core.items.items[id],'itemEffect':editor.core.items.itemEffect[id],'itemEffectTip':editor.core.items.itemEffectTip[id]}, + editor_file.comment.items, + err]); + }); + } else { + callback([ + {'items':editor.core.items.items[id],'itemEffect':editor.core.items.itemEffect[id],'itemEffectTip':editor.core.items.itemEffectTip[id]}, + editor_file.comment.items, + null]); + } + //只有items.cls是items的才有itemEffect和itemEffectTip,keys和constants和tools只有items } - - //callback(obj,commentObj,err:String) + //callback([obj,commentObj,err:String]) editor_file.editEnemy = function(editor,id,actionList,callback){ - //obj形式同callback的obj,为null或undefined时只查询不修改 + /*actionList:[ + ["change","['name']","初级巫师的新名字"], + ["add","['新的和name同级的属性']",123], + ["change","['bomb']",null], + ] + 为[]时只查询不修改 + */ if (!isset(callback)) throw('未设置callback'); - callback([ - {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, "bomb": false}, - editor_file.comment.enemys, - null]); + if (isset(actionList) && actionList.length > 0){ + actionList.forEach(function (value) { + value[1] = "['"+id+"']"+value[1]; + }); + saveSetting('enemys',actionList,function (err) { + callback([ + editor.core.enemys.enemys[id], + editor_file.comment.enemys, + err]); + }); + } else { + callback([ + editor.core.enemys.enemys[id], + editor_file.comment.enemys, + null]); + } } - //callback(obj,commentObj,err:String) + //callback([obj,commentObj,err:String]) //////////////////////////////////////////////////////////////////// @@ -241,7 +288,7 @@ $range((function(){typeof(thiseval)==typeof(0)||})()) if( 注释.indexof('$range(')!= -1){ - thiseval = 新值; + var thiseval = 新值; evalstr = 注释.split('$range')[1].split('$end')[0]; if(eval(evalstr) !== true)alert('不在取值范围内') } diff --git a/drawMapGUI.html b/drawMapGUI.html index 309a9165..17c025f8 100644 --- a/drawMapGUI.html +++ b/drawMapGUI.html @@ -30,8 +30,8 @@
- - + +
@@ -167,8 +167,8 @@

- + + @@ -206,7 +206,7 @@ `的`drawMapGUI.html` + 不再独立的导入数据和画图,尽可能的通过`main.init('editor')`复用代码 -+ 能够在本地服务器环境中直接修改`project`中的数据,目前只完成了文件操作的代码`editor_file.js`,前端尚未完成 ++ 能够在本地服务器环境中直接修改`project`中的数据,目前只完成了文件操作的代码`_server/editor_file.js`,前端尚未完成 ++ 把`editor`的代码拆到了`_server/editor.js`中 ## 具体: @@ -48,37 +51,39 @@ 提供了以下函数进行楼层`map`数组相关的操作 ```javascript editor.file.getFloorFileList -editor_file.loadFloorFile -editor_file.saveFloorFile -editor_file.saveFloorFileAs +editor.file.loadFloorFile +editor.file.saveFloorFile +editor.file.saveFloorFileAs ``` 5个编辑模式有关的查询 ```javascript -editor_file.editItem(editor,'redJewel',[],function(a){console.log(a)}); -editor_file.editEnemy(editor,'redBat',[],function(a){console.log(a)}); -editor_file.editLoc(editor,2,0,[],function(a){console.log(a)}); -editor_file.editFloor(editor,[],function(a){console.log(a)}); +editor.file.editItem(editor,'redJewel',[],function(a){console.log(a)}); +editor.file.editEnemy(editor,'redBat',[],function(a){console.log(a)}); +editor.file.editLoc(editor,2,0,[],function(a){console.log(a)}); +editor.file.editFloor(editor,[],function(a){console.log(a)}); editor.file.editTower(editor,[],function(a){console.log(a)}); ``` 5个编辑模式有关的编辑 ```javascript editor.info={images: "terrains", y: 9}; editor.file.changeIdAndIdnum(editor,'yellowWall2',16,editor.info,function(a){console.log(a)}); -editor_file.editItem(editor,'book',[["change","['items']['name']","怪物手册的新名字"]],function(a){console.log(a)}); -editor_file.editEnemy(editor,'redBat',[['change',"['atk']",20]],function(a){console.log(a)}); -editor_file.editLoc(editor,2,6,[["change","['afterBattle']",null]],function(a){console.log(a)}); -editor_file.editFloor(editor,[["change","['title']",'样板 33 层']],function(a){console.log(a)}); +editor.file.editItem(editor,'book',[["change","['items']['name']","怪物手册的新名字"]],function(a){console.log(a)}); +editor.file.editEnemy(editor,'redBat',[['change',"['atk']",20]],function(a){console.log(a)}); +editor.file.editLoc(editor,2,6,[["change","['afterBattle']",null]],function(a){console.log(a)}); +editor.file.editFloor(editor,[["change","['title']",'样板 33 层']],function(a){console.log(a)}); editor.file.editTower(editor,[["change","['values']['lavaDamage']",200]],function(a){console.log(a)}); ``` ### drawMapGUI.html +把`editor`的代码拆到了`_server/editor.js`中 + 以`display:none`的形式引入了`index.html`的`dom`,修改了原来的`.gameCanvas #ui #data`等的名字以避免冲突 通过`main.init('editor')`加载数据,移除了原有的`editor.loadjs`等 背景层如果未设置`editor.bgY`则通过运行时中的代码画背景 -`updateMap`中只画未定义快的报错,其他的由运行时中的代码完成 +`editor.updateMap`中只画未定义快的报错,其他的由运行时中的代码完成 `editor.ids[0] = 0; editor.indexs[0]=[0];` diff --git a/_server/editor.js b/_server/editor.js new file mode 100644 index 00000000..1190bb85 --- /dev/null +++ b/_server/editor.js @@ -0,0 +1,508 @@ +function editor() { + this.version = "1.2"; + this.material = {}; +} + +editor.prototype.init = function(callback){ + var afterCoreReset = function(){ + + main.editor.disableGlobalAnimate=false;//允许GlobalAnimate + /* core.setHeroMoveTriggerInterval(); */ + + editor.reset(function(){ + editor.drawMapBg(); + var mapArray = core.maps.getMapArray(core.status.maps, core.status.floorId); + editor.map = mapArray.map(function(v){return v.map(function(v){return editor.ids[[editor.indexs[v][0]]]})}); + editor.updateMap(); + editor.currentFloorId=core.status.floorId; + editor.currentFloorData = core.floors[core.status.floorId]; + + if (Boolean(callback))callback(); + }); + } + var afterMainInit = function(){ + editor.main=main; + editor.core=core; + editor.fs=fs; + editor.file=editor_file; + editor.material.images=core.material.images; + editor.listen(); // 开始监听事件 + var hard = 'Hard'; + core.resetStatus(core.firstData.hero, hard, core.firstData.floorId, core.initStatus.maps); + //core.status.maps = core.clone(core.maps.initMaps(floorIds)); + core.changeFloor(core.status.floorId, null, core.firstData.hero.loc, null, function() { + afterCoreReset(); + }); + core.events.setInitData(hard); + } + setTimeout(afterMainInit, 300); +} + +editor.prototype.reset = function(callback){ + editor.idsInit(core.maps, core.icons.icons); // 初始化图片素材信息 + editor.drawInitData(core.icons.icons); // 初始化绘图 + if(Boolean(callback))callback(); +} + +editor.prototype.idsInit = function(maps, icons){ + editor.ids = [0]; + editor.indexs = []; + var MAX_NUM = 400; + var getInfoById = function(id){ + var block = maps.getBlock(0, 0, id); + if(hasOwnProp(block, 'event')){ + return block; + } + } + var point = 0; + for(var i=0; i edata.width) edata.style.width = (edata.width = fullWidth)/ratio + 'px'; + edata.style.height = (edata.height = fullHeight)/ratio + 'px'; + var dc = edata.getContext('2d'); + var nowx = 0; + var nowy = 0; + for(var ii=0; ii=0 && y >=0 && x<13 && y<13 && isAutotile(editor.map[y][x]) && editor.map[y][x].idnum == currId) + return 1; + else if(x<0 || y<0 || x>12 || y>12) return 1; //边界外视为通用autotile,这样好看些 + else + return 0; + } + var checkAround = function(x, y){ // 得到周围四个32*32块(周围每块都包含当前块的1/4,不清楚的话画下图你就明白)的数组索引 + var currId = editor.map[y][x].idnum; + var pointBlock = []; + for(var i=0; i<4; i++){ + var bsum = 0; + var offsetx = i%2, offsety = ~~(i/2); + for(var j=0; j<4; j++){ + var mx = j%2, my = ~~(j/2); + var b = getAutotileAroundId(currId, x+offsetx+mx-1, y+offsety+my-1); + bsum += b*(Math.pow(2, 3-j)); + } + pointBlock.push(bsum); + } + return pointBlock; + } + var addIndexToAutotileInfo = function(x, y){ + var indexArr = []; + var pointBlocks = checkAround(x, y); + for(var i=0; i<4; i++){ + var arr = indexArrs[pointBlocks[i]] + indexArr.push(arr[3-i]); + } + editor.map[y][x].blockIndex = indexArr; + } + var drawAutotile = function(ctx, x, y, info){ // 绘制一个autotile + ctx.clearRect(x*32, y*32, 32, 32); + //修正四个边角的固定搭配 + if(info.blockIndex[0] == 13){ + if(info.blockIndex[1] == 16) info.blockIndex[1] = 14; + if(info.blockIndex[2] == 31) info.blockIndex[2] = 19; + } + if(info.blockIndex[1] == 18){ + if(info.blockIndex[0] == 15) info.blockIndex[0] = 17; + if(info.blockIndex[3] == 36) info.blockIndex[3] = 24; + } + if(info.blockIndex[2] == 43){ + if(info.blockIndex[0] == 25) info.blockIndex[0] = 37; + if(info.blockIndex[3] == 46) info.blockIndex[3] = 44; + } + if(info.blockIndex[3] == 48){ + if(info.blockIndex[1] == 30) info.blockIndex[1] = 42; + if(info.blockIndex[2] == 45) info.blockIndex[2] = 47; + } + for(var i=0; i<4; i++){ + var index = info.blockIndex[i]; + var dx = x*32 + 16*(i%2), dy = y*32 + 16*(~~(i/2)); + drawBlockByIndex(ctx, dx, dy, editor.material.images[info.images][info.id], index); + } + } + */ + // 绘制地图 start + var eventCtx = document.getElementById('event').getContext("2d"); + for(var y=0; y<13; y++) + for(var x=0; x<13; x++){ + var tileInfo = editor.map[y][x]; + if(false && isAutotile(tileInfo)){ + addIndexToAutotileInfo(x, y); + drawAutotile(eventCtx, x, y, tileInfo); + }else drawTile(eventCtx, x, y, tileInfo); + } + // 绘制地图 end +} + +editor.prototype.changeFloor = function(floorId,callback) { + core.changeFloor(floorId, null, core.firstData.hero.loc, null, function(){ + editor.drawMapBg(); + var mapArray = core.maps.getMapArray(core.status.maps, core.status.floorId); + editor.map = mapArray.map(function(v){return v.map(function(v){return editor.ids[[editor.indexs[v][0]]]})}); + editor.updateMap(); + editor.currentFloorId=core.status.floorId; + editor.currentFloorData = core.floors[core.status.floorId]; + if (core.isset(callback))callback(); + }); +} + +editor.prototype.listen = function() { + + var uc = eui.getContext('2d'); + + function fillPos(pos) { + uc.fillStyle = '#' + ~~(Math.random() * 8) + ~~(Math.random() * 8) + ~~(Math.random() * 8); + uc.fillRect(pos.x * 32 + 12, pos.y * 32 + 12, 8, 8); + }//在格子内画一个随机色块 + + function eToLoc(e) { + editor.loc = { + 'x': document.documentElement.scrollLeft+e.clientX - mid.offsetLeft-mapEdit.offsetLeft, + 'y': document.documentElement.scrollTop+e.clientY - mid.offsetTop-mapEdit.offsetTop, + 'size': 32 + }; + return editor.loc; }//返回可用的组件内坐标 + + function locToPos(loc) { + editor.pos = { 'x': ~~(loc.x / loc.size), 'y': ~~(loc.y / loc.size) } + return editor.pos; + } + + var holdingPath = 0; + var stepPostfix = null;//用于存放寻路检测的第一个点之后的后续移动 + + var mouseOutCheck = 2; + function clear1() { + if (mouseOutCheck > 1) { + mouseOutCheck--; + setTimeout(clear1, 1000); + return; + } + holdingPath = 0; + stepPostfix = []; + uc.clearRect(0, 0, 416, 416); + }//用于鼠标移出canvas时的自动清除状态 + + eui.onmousedown = function (e) { + if(!selectBox.isSelected) { + tip.whichShow = 1; + return; + } + + holdingPath = 1; + mouseOutCheck = 2; + setTimeout(clear1); + e.stopPropagation(); + uc.clearRect(0, 0, 416, 416); + var loc = eToLoc(e); + var pos = locToPos(loc) + stepPostfix = []; + stepPostfix.push(pos); + fillPos(pos); + } + + eui.onmousemove = function (e) { + if(!selectBox.isSelected) { + // tip.whichShow = 1; + return; + } + + if (holdingPath == 0) { return; } + mouseOutCheck = 2; + e.stopPropagation(); + var loc = eToLoc(e); + var pos = locToPos(loc); + var pos0 = stepPostfix[stepPostfix.length - 1] + var directionDistance = [pos.y - pos0.y, pos0.x - pos.x, pos0.y - pos.y, pos.x - pos0.x] + var max = 0, index = 4; + for (var i = 0; i < 4; i++) { + if (directionDistance[i] > max) { + index = i; + max = directionDistance[i]; + } + } + var pos = [{ 'x': 0, 'y': 1 }, { 'x': -1, 'y': 0 }, { 'x': 0, 'y': -1 }, { 'x': 1, 'y': 0 }, false][index] + if (pos) { + pos.x += pos0.x; + pos.y += pos0.y; + stepPostfix.push(pos); + fillPos(pos); + } + } + + eui.onmouseup = function (e) { + if(!selectBox.isSelected) { + tip.whichShow = 1; + return; + } + holdingPath = 0; + e.stopPropagation(); + var loc = eToLoc(e); + if (stepPostfix.length) { + preMapData = JSON.parse(JSON.stringify(editor.map)); + currDrawData.pos = JSON.parse(JSON.stringify(stepPostfix)); + currDrawData.info = JSON.parse(JSON.stringify(editor.info)); + reDo = null; + // console.log(stepPostfix); + for (var ii = 0; ii < stepPostfix.length; ii++) + editor.map[stepPostfix[ii].y][stepPostfix[ii].x] = editor.info; + // console.log(editor.map); + editor.updateMap(); + holdingPath = 0; + stepPostfix = []; + uc.clearRect(0, 0, 416, 416); + } + } + + var preMapData = {}; + var currDrawData = { + pos: [], + info: {} + }; + var reDo = null; + document.body.onkeydown = function(e) { + // 禁止快捷键的默认行为 + if( e.ctrlKey && ( e.keyCode == 90 || e.keyCode == 89 ) ) + e.preventDefault(); + //Ctrl+z 撤销上一步undo + if(e.keyCode == 90 && e.ctrlKey && preMapData && currDrawData.pos.length){ + editor.map = JSON.parse(JSON.stringify(preMapData)); + editor.updateMap(); + reDo = JSON.parse(JSON.stringify(currDrawData)); + currDrawData = {pos: [],info: {}}; + preMapData = null; + } + //Ctrl+y 重做一步redo + if(e.keyCode == 89 && e.ctrlKey && reDo && reDo.pos.length){ + preMapData = JSON.parse(JSON.stringify(editor.map)); + for(var j=0; j=editor.widthsX[spriter][1] && pos.x editor.widthsX[spriter][3]) + pos.y = ~~(editor.widthsX[spriter][3]/32)-4; + else{ + for(var i=0; i= 4*i && pos.y < 4*(i+1)){ + pos.images = imNames[i]; + pos.y = 4*i; + } + } + } + }else if((pos.y+1)*32 > editor.widthsX[spriter][3]) + pos.y = ~~(editor.widthsX[spriter][3]/32)-1; + + selectBox.isSelected = true; + // console.log(pos,editor.material.images[pos.images].height) + dataSelection.style.left = pos.x*32 +'px'; + dataSelection.style.top = pos.y*32 +'px'; + + if(pos.x==0&&pos.y==0){ + // editor.info={idnum:0, id:'empty','images':'清除块', 'y':0}; + editor.info=0; + }else{ + if(hasOwnProp(autotiles, pos.images)) editor.info={'images':pos.images, 'y':0}; + else if(pos.images == 'terrains') editor.info={'images':pos.images, 'y':pos.y-1}; + else editor.info={'images':pos.images, 'y':pos.y}; + + for (var ii=0;ii - - - - - - -
-
-
-
-
-
- -

{{ errors[error-1] }}

-
-
- -
-
-
- -
-
- -
- -
-
-
-
-
- - - -
-
-
-
-

当前选择为清除块,可擦除地图上块

-
-

图块编号:{{ infos['idnum'] }}

-

图块ID:{{ infos['id'] }}

-

该图块无对应的数字或ID存在,请先前往icons.js和maps.js中进行定义!

-

图块所在素材:{{ infos['images'] + (isAutotile ? '( '+infos['id']+' )' : '') }}

-

图块索引:{{ infos['y'] }}

-
-
-
-

{{ mapMsg }}

-
-
- - - -
- 当前地板: - -
- - -
-
-
-
- -
- - - - - - - - - - - - - - - - - + \ No newline at end of file diff --git a/editor.html b/editor.html new file mode 100644 index 00000000..3b0f15cf --- /dev/null +++ b/editor.html @@ -0,0 +1,227 @@ + + + + + + + +
+
+
+
+
+
+ +

{{ errors[error-1] }}

+
+
+ +
+
+
+ +
+
+ +
+ +
+
+
+
+
+ + + +
+
+
+
+

当前选择为清除块,可擦除地图上块

+
+

图块编号:{{ infos['idnum'] }}

+

图块ID:{{ infos['id'] }}

+

该图块无对应的数字或ID存在,请先前往icons.js和maps.js中进行定义!

+

图块所在素材:{{ infos['images'] + (isAutotile ? '( '+infos['id']+' )' : '') }}

+

图块索引:{{ infos['y'] }}

+
+
+
+

{{ mapMsg }}

+
+
+ + + +
+ 当前地板: + +
+ + +
+
+
+
+ +
+ + + + + + + + + + + + + + + + + + + diff --git a/libs/core.js b/libs/core.js index caf786d0..93926547 100644 --- a/libs/core.js +++ b/libs/core.js @@ -79,7 +79,6 @@ function core() { 'mouseOutCheck': 1, 'moveStepBeforeStop': [], - // 勇士状态;中心对称飞行器 // event事件 'saveIndex': null, From 8977ac51375a1f79bf734755af290327455235f7 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Tue, 9 Jan 2018 15:22:11 +0800 Subject: [PATCH 023/102] =?UTF-8?q?editor=20=E5=85=A8GUI=E7=BC=96=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/css/editor_mode.css | 119 +++++++++++++++++++ _server/editor.js | 11 +- _server/editor_file.js | 37 +++--- _server/editor_file_test.html | 2 +- _server/editor_mode.js | 210 ++++++++++++++++++++++++++++++++++ _server/vm.js | 1 + editor.html | 92 ++++++++++++++- project/comment.js | 16 +-- project/data.comment.js | 48 ++++---- 9 files changed, 479 insertions(+), 57 deletions(-) create mode 100644 _server/css/editor_mode.css create mode 100644 _server/editor_mode.js diff --git a/_server/css/editor_mode.css b/_server/css/editor_mode.css new file mode 100644 index 00000000..fc13bace --- /dev/null +++ b/_server/css/editor_mode.css @@ -0,0 +1,119 @@ +.leftTab { + border-radius: 2px; + box-sizing: border-box; + box-shadow: 0 2px 2px 0 rgba(0,0,0,.14), 0 3px 1px -2px rgba(0,0,0,.2), 0 1px 5px 0 rgba(0,0,0,.12); +} + +.leftTab { + overflow: auto; + position: absolute; + height: 630px; +} +.leftTab > *{margin:2.5px 5px;} +.leftTab > :first-child{margin-top:5px;} +.leftTab > :last-child{margin-bottom:5px;} + +#left99 { + left: 5px; + top: 650px; + width: 435px; +} + +#left2 { + left: 448px; + top: 650px; + width: 440px; +} + +#left3 { + left: 900px; + top: 650px; + width: 440px; +} + +#left4 { + left: 5px; + top: 1290px; + width: 435px; +} + +#left5 { + left: 448px; + top: 1290px; + width: 440px; +} + +.etable table, +.etable table td { + color: #000; + cursor: auto; +} + +/* copy from github-css https://github.com/sindresorhus/github-markdown-css */ +.etable table { + border-spacing: 0; + border-collapse: collapse; +} +.etable table { + margin-top: 0; + margin-bottom: 16px; +} +.etable table { + display: block; + width: 100%; + overflow: auto; +} +.etable table th { + font-weight: 600; +} +.etable table th, +.etable table td { + padding: 6px 13px; + border: 1px solid #dfe2e5; +} +.etable table tr { + background-color: #fff; + border-top: 1px solid #c6cbd1; +} +.etable table tr:nth-child(2n) { + background-color: #f6f8fa; +} +/* copy end --------------------------------------------- */ +.etable tr {width:100%} +.etable tr > :nth-child(1) {width:20%} +.etable tr > :nth-child(2) {width:20%} +.etable tr > :nth-child(3) {width:60%} + +.etable table { + overflow: visible; +} + +.etable tr:not(:first-child) :last-child { + margin: 0; + padding: 0; + height: 100%; + width: 100%; +} + +.etable tr:not(:first-child) input:last-child { + +} + +.etable tr:not(:first-child) select:last-child { + +} + +.etable tr:not(:first-child) textarea:last-child { + +} + +.etable tr:not(:first-child) > :last-child:hover { + border: 1px solid rgb(87, 198, 232); + box-shadow: 0px 0px 3px rgb(87, 198, 232); +} + +.etable tr:not(:first-child) > :nth-child(2):hover, +.etable tr:not(:first-child) > :nth-child(1):hover { + border: 1px solid rgb(87, 232, 198); + box-shadow: 0px 0px 3px rgb(87, 232, 198); +} \ No newline at end of file diff --git a/_server/editor.js b/_server/editor.js index 1190bb85..e40c285c 100644 --- a/_server/editor.js +++ b/_server/editor.js @@ -295,6 +295,7 @@ editor.prototype.changeFloor = function(floorId,callback) { editor.updateMap(); editor.currentFloorId=core.status.floorId; editor.currentFloorData = core.floors[core.status.floorId]; + editor_mode.floor(); if (core.isset(callback))callback(); }); } @@ -338,6 +339,11 @@ editor.prototype.listen = function() { eui.onmousedown = function (e) { if(!selectBox.isSelected) { + var loc = eToLoc(e); + var pos = locToPos(loc); + editor_mode.onmode('');//为了强制触发doAction + editor_mode.onmode('loc'); + editor_mode.loc(); tip.whichShow = 1; return; } @@ -348,7 +354,7 @@ editor.prototype.listen = function() { e.stopPropagation(); uc.clearRect(0, 0, 416, 416); var loc = eToLoc(e); - var pos = locToPos(loc) + var pos = locToPos(loc); stepPostfix = []; stepPostfix.push(pos); fillPos(pos); @@ -491,6 +497,9 @@ editor.prototype.listen = function() { } } tip.infos = JSON.parse(JSON.stringify(editor.info)); + editor_mode.onmode('');//为了强制触发doAction + editor_mode.onmode('emenyitem'); + editor_mode.emenyitem(); } } } diff --git a/_server/editor_file.js b/_server/editor_file.js index 6adfd457..e43f1c54 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -30,16 +30,17 @@ editor_file.getFloorFileList = function(editor,callback){ if (!isset(callback)) throw('未设置callback'); - var fs = editor.fs; + /* var fs = editor.fs; fs.readdir('project/floors',function(err, data){ callback([data,err]); - }); + }); */ + callback([editor.core.floorIds,null]); } //callback([Array,err:String]) editor_file.loadFloorFile = function(editor,filename,callback){ //filename不含'/'不含'.js' if (!isset(callback)) throw('未设置callback'); - var fs = editor.fs; + /* var fs = editor.fs; fs.readFile('project/floors/'+filename+'.js','utf-8',function(err, data){ if (err!=null){callback(err);return;} data=data.split('='); @@ -57,7 +58,9 @@ editor.currentFloorId = floorId; editor.currentFloorData = floorData; callback(null) - }); + }); */ + editor.currentFloorId=editor.core.status.floorId; + editor.currentFloorData = editor.core.floors[editor.currentFloorId]; } //callback(err:String) editor_file.saveFloorFile = function(editor,callback){ @@ -87,6 +90,7 @@ if (!isset(editor.currentFloorData)) { callback('无数据'); } + editor.currentFloorData=JSON.parse(JSON.stringify(editor.currentFloorData)); editor.currentFloorData.floorId=saveAsFilename; editor.currentFloorId=saveAsFilename; editor_file.saveFloorFile(editor,callback); @@ -465,19 +469,13 @@ } /* - $range(thiseval in ['keys','items','constants','tools'])$end + $select({\"values\":[\"keys\",\"items\",\"constants\",\"tools\"]})$end $range(thiseval==~~thiseval &&thiseval>0)$end - $range(thiseval in [true,false])$end - $range(false)$end $leaf(true)$end + $select({\"values\":[true]})$end + $select({\"values\":[false]})$end + $select({\"values\":[true,false]})$end - //$range((function(){typeof(thiseval)==typeof(0)||})())$end - - if( 注释.indexof('$range(')!= -1){ - var thiseval = 新值; - evalstr = 注释.split('$range')[1].split('$end')[0]; - if(eval(evalstr) !== true)alert('不在取值范围内') - } */ /* @@ -487,19 +485,16 @@ $leaf(evalstr:thiseval)$end 强制指定为叶节点,如果eval(evalstr)为true - todo: //以下几个中选一个 [ $select(evalstr)$end 渲染成,此为默认选项 + $input(evalstr)$end + 渲染成 $textarea(evalstr)$end - 渲染成\n'].join(''); + } +} + +editor_mode.prototype.guid = function() { + return 'id_'+'xxxxxxxx_xxxx_4xxx_yxxx_xxxxxxxxxxxx'.replace(/[xy]/g, function(c) { + var r = Math.random()*16|0, v = c == 'x' ? r : (r&0x3|0x8); + return v.toString(16); + }); +} + +editor_mode.prototype.addAction = function(action){ + editor_mode.actionList.push(action); +} + +editor_mode.prototype.doActionList = function(mode,actionList){ + if (actionList.length==0)return; + //尚未完成 +} + +editor_mode.prototype.onmode = function (mode) { + if (editor_mode.mode!=mode) { + console.log('change mode into : '+mode); + editor_mode.doActionList(editor_mode.mode,editor_mode.actionList); + editor_mode.mode=mode; + editor_mode.actionList=[]; + } +} + +editor_mode.prototype.loc = function(callback){ + //editor.pos={x: 0, y: 0}; + if (!core.isset(editor.pos))return; + document.getElementById('pos_a6771a78_a099_417c_828f_0a24851ebfce').innerText=editor.pos.x+','+editor.pos.y; + + var objs=[]; + editor_file.editLoc(editor,editor.pos.x,editor.pos.y,[],function(objs_){objs=objs_;console.log(objs_)}); + //只查询不修改时,内部实现不是异步的,所以可以这么写 + var tableinfo=editor_mode.objToTable(objs[0],objs[1]); + document.getElementById('table_3d846fc4_7644_44d1_aa04_433d266a73df').innerHTML=tableinfo.HTML; + tableinfo.listen(tableinfo.guids); + + if (Boolean(callback))callback(); +} + +editor_mode.prototype.emenyitem = function(callback){ + //editor.info=editor.ids[editor.indexs[201]]; + if (!core.isset(editor.info))return; + editor_mode.info=editor.info;//避免editor.info被清空导致无法获得是物品还是怪物 + + if (!core.isset(editor_mode.info.id)){ + return; + }//尚未完成 + + var objs=[]; + if (editor_mode.info.images=='enemys'){ + editor_file.editEnemy(editor,editor_mode.info.id,[],function(objs_){objs=objs_;console.log(objs_)}); + } else if (editor_mode.info.images=='items'){ + editor_file.editItem(editor,editor_mode.info.id,[],function(objs_){objs=objs_;console.log(objs_)}); + } else { + return; + } + //只查询不修改时,内部实现不是异步的,所以可以这么写 + var tableinfo=editor_mode.objToTable(objs[0],objs[1]); + document.getElementById('table_a3f03d4c_55b8_4ef6_b362_b345783acd72').innerHTML=tableinfo.HTML; + tableinfo.listen(tableinfo.guids); + + if (Boolean(callback))callback(); +} + +editor_mode.prototype.floor = function(callback){ + var objs=[]; + editor_file.editFloor(editor,[],function(objs_){objs=objs_;console.log(objs_)}); + //只查询不修改时,内部实现不是异步的,所以可以这么写 + var tableinfo=editor_mode.objToTable(objs[0],objs[1]); + document.getElementById('table_4a3b1b09_b2fb_4bdf_b9ab_9f4cdac14c74').innerHTML=tableinfo.HTML; + tableinfo.listen(tableinfo.guids); + if (Boolean(callback))callback(); +} + +editor_mode.prototype.tower = function(callback){ + var objs=[]; + editor.file.editTower(editor,[],function(objs_){objs=objs_;console.log(objs_)}); + //只查询不修改时,内部实现不是异步的,所以可以这么写 + var tableinfo=editor_mode.objToTable(objs[0],objs[1]); + document.getElementById('table_b6a03e4c_5968_4633_ac40_0dfdd2c9cde5').innerHTML=tableinfo.HTML; + tableinfo.listen(tableinfo.guids); + if (Boolean(callback))callback(); +} + +editor_mode = new editor_mode(); +editor_mode.init(); \ No newline at end of file diff --git a/_server/vm.js b/_server/vm.js index ba4e640e..3ae26442 100644 --- a/_server/vm.js +++ b/_server/vm.js @@ -2,6 +2,7 @@ document.body.onmousedown = function(e){ selectBox.isSelected = false; + editor_mode.onmode(''); editor.info = {}; } iconLib.onmousedown = function(e){ diff --git a/editor.html b/editor.html index 3b0f15cf..31c6634a 100644 --- a/editor.html +++ b/editor.html @@ -3,6 +3,7 @@ +
@@ -26,6 +27,85 @@
+
+
+

测试用标签页

+
+ + + + + + + + + +
条目注释aaa
变量名字符串可能显示不全但是hover时通过span title='xxx'来显示高度以此为准
此处是利用slice实现
+
+
+ + + + + + + +
条目注释
+
+
+ +
+
+
+
+

地图选点

+

0,0

+
+ + + + +
条目注释
+
+
+
+

图块属性

+
+ +
+
+
+ + + + +
条目注释
+
+
+
+
+

楼层属性

+
+ + + + +
条目注释
+
+
+
+

全塔属性

+
+ + + + +
条目注释
+
+
@@ -201,11 +281,12 @@ + diff --git a/project/comment.js b/project/comment.js index 780f32f9..fe2726a1 100644 --- a/project/comment.js +++ b/project/comment.js @@ -2,7 +2,7 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = { "items" : { 'items':{ - 'cls': "只能取keys(钥匙) items(宝石、血瓶) constants(物品) tools(道具)\n$range(thiseval in ['keys','items','constants','tools'])$end", + 'cls': "只能取keys(钥匙) items(宝石、血瓶) constants(物品) tools(道具)\n$select({\"values\":[\"keys\",\"items\",\"constants\",\"tools\"]})$end", 'name': '名称', 'text': '道具在道具栏中显示的描述' }, @@ -16,21 +16,21 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = 'def': '防御力', 'money': '金币', 'experience': '经验', - 'special': '特殊属性\n0:无,1:先攻,2:魔攻,3:坚固,4:2连击,5:3连击,6:n连击,7:破甲,8:反击,9:净化,10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,15:领域,16:夹击,17:仇恨,18:阻击,19:自爆,20:无敌\n多个属性例如用[1,4,11]表示先攻2连击吸血\n模仿怪的攻防设为0就好\n$leaf(true)$end', + 'special': '特殊属性\n\n0:无,1:先攻,2:魔攻,3:坚固,4:2连击,\n5:3连击,6:n连击,7:破甲,8:反击,9:净化,\n10:模仿,11:吸血,12:中毒,13:衰弱,14:诅咒,\n15:领域,16:夹击,17:仇恨,18:阻击,19:自爆,\n20:无敌\n\n多个属性例如用[1,4,11]表示先攻2连击吸血\n模仿怪的攻防设为0就好\n$leaf(true)$end', 'value': '特殊属性的数值\n领域怪需要加value表示领域伤害的数值\n吸血怪需要在后面添加value代表吸血比例', 'zoneSquare': '领域怪zoneSquare代表是否九宫格伤害', - 'range': 'range可选,代表领域伤害的范围;不加默认为1\n$range(thiseval==~~thiseval &&thiseval>0)$end', - 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉\n$range(thiseval in [true,false])$end', - 'point': 'point可以在打败怪物后进行加点,详见文档说明\n$range(thiseval==~~thiseval && thiseval>0)$end', - 'n': '多连击需要在后面指定n代表是几连击\n$range(thiseval==~~thiseval &&thiseval>0)$end', + 'range': 'range可选,代表领域伤害的范围;不加默认为1\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', + 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉\n$select({\"values\":[true,false]})$end', + 'point': 'point可以在打败怪物后进行加点,详见文档说明\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', + 'n': '多连击需要在后面指定n代表是几连击\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', }, "floors" : { 'floor' : { "floorId": "文件名和floorId需要保持完全一致 \n楼层唯一标识符仅能由字母、数字、下划线组成,且不能由数字开头 \n推荐用法:第20层就用MT20,第38层就用MT38,地下6层就用MT_6(用下划线代替负号),隐藏3层用MT3h(h表示隐藏),等等 \n楼层唯一标识符,需要和名字完全一致 \n这里不能更改floorId,请通过另存为来实现\n$range(false)$end", "title": "楼层中文名 ", "name": "显示在状态栏中的层数 ", - "canFlyTo": "该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) \n$range(thiseval in [true,false])$end", - "canUseQuickShop": "该层是否允许使用快捷商店 \n$range(thiseval in [true,false])$end", + "canFlyTo": "该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) \n$select({\"values\":[true,false]})$end", + "canUseQuickShop": "该层是否允许使用快捷商店 \n$select({\"values\":[true,false]})$end", "defaultGround": "默认地面的图块ID(terrains中) ", "png": "背景图;你可以选择一张png图片来作为背景素材。详细用法请参见文档“自定义素材”中的说明。 ", "color": "该层的默认画面色调。本项可不写(代表无色调),如果写需要是一个RGBA数组。 \n$leaf(true)$end", diff --git a/project/data.comment.js b/project/data.comment.js index aff279fe..22a42c9c 100644 --- a/project/data.comment.js +++ b/project/data.comment.js @@ -1,7 +1,7 @@ data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = { "main": { - "useCompress": " 是否使用压缩文件 \n 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 \n 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 \n 如果要进行剧本的修改请务必将其改成false。 ", + "useCompress": " 是否使用压缩文件 \n 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 \n 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 \n 如果要进行剧本的修改请务必将其改成false。 \n$select({\"values\":[false]})$end", "floorIds": " 在这里按顺序放所有的楼层;其顺序直接影响到楼层传送器的顺序和上楼器/下楼器的顺序 \n$leaf(true)$end", "pngs": " 在此存放所有可能的背景图片;背景图片最好是416*416像素,其他分辨率会被强制缩放成416*416 \n 建议对于较大的图片,在网上使用在线的“图片压缩工具”来进行压缩,以节省流量 \n 有关使用自定义背景图,请参见文档的“自定义素材”说明 \n\n 依次向后添加 \n$leaf(true)$end", "bgms": " 在此存放所有的bgm,和文件名一致。第一项为默认播放项 \n 音频名不能使用中文,不能带空格或特殊字符;可以直接改名拼音就好 \n$leaf(true)$end", @@ -14,7 +14,7 @@ data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "floorId": " 初始楼层ID ", "hero": { "name": " 勇士初始数据 \n 勇士名;可以改成喜欢的 ", - "lv": " 初始等级,该项必须为正整数 ", + "lv": " 初始等级,该项必须为正整数 \n$range(thiseval==~~thiseval &&thiseval>0)$end", "hp": " 初始生命值 ", "atk": " 初始攻击 ", "def": " 初始防御 ", @@ -139,27 +139,27 @@ data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "animateSpeed": " /****** 系统相关 ******/ \n 动画时间 " }, "flags": { - "enableFloor": " 系统FLAG,在游戏运行中中请不要修改它。 /****** 状态栏相关 ******/ \n 是否在状态栏显示当前楼层 ", - "enableLv": " 是否在状态栏显示当前等级 ", - "enableMDef": " 是否在状态栏及战斗界面显示魔防(护盾) ", - "enableMoney": " 是否在状态栏、怪物手册及战斗界面显示金币 ", - "enableExperience": " 是否在状态栏、怪物手册及战斗界面显示经验 ", - "enableLevelUp": " 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false ", - "enableDebuff": " 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff ////// 上述的几个开关将直接影响状态栏的显示效果 ////// ", - "flyNearStair": " /****** 道具相关 ******/ \n 是否需要在楼梯边使用传送器 ", - "pickaxeFourDirections": " 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 ", - "bombFourDirections": " 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) ", - "bigKeyIsBox": " 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 ", - "enableNegativeDamage": " /****** 怪物相关 ******/ \n 是否支持负伤害(回血) ", - "zoneSquare": " 领域类型。如果此项为true则为九宫格伤害,为false则为十字伤害 ", - "startDirectly": " /****** 系统相关 ******/ \n 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 ", - "canOpenBattleAnimate": " 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false ", - "showBattleAnimateConfirm": " 是否在游戏开始时提供“是否开启战斗动画”的选项 ", - "battleAnimate": " 是否默认显示战斗动画;用户可以手动在菜单栏中开关 ", - "displayEnemyDamage": " 是否地图怪物显伤;用户可以手动在菜单栏中开关 ", - "displayExtraDamage": " 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 ", - "enableGentleClick": " 是否允许轻触(获得面前物品) ", - "portalWithoutTrigger": " 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 ", - "potionWhileRouting": " 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 " + "enableFloor": " 系统FLAG,在游戏运行中中请不要修改它。 /****** 状态栏相关 ******/ \n 是否在状态栏显示当前楼层 \n$select({\"values\":[true,false]})$end", + "enableLv": " 是否在状态栏显示当前等级 \n$select({\"values\":[true,false]})$end", + "enableMDef": " 是否在状态栏及战斗界面显示魔防(护盾) \n$select({\"values\":[true,false]})$end", + "enableMoney": " 是否在状态栏、怪物手册及战斗界面显示金币 \n$select({\"values\":[true,false]})$end", + "enableExperience": " 是否在状态栏、怪物手册及战斗界面显示经验 \n$select({\"values\":[true,false]})$end", + "enableLevelUp": " 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false \n$select({\"values\":[true,false]})$end", + "enableDebuff": " 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff ////// 上述的几个开关将直接影响状态栏的显示效果 ////// \n$select({\"values\":[true,false]})$end", + "flyNearStair": " /****** 道具相关 ******/ \n 是否需要在楼梯边使用传送器 \n$select({\"values\":[true,false]})$end", + "pickaxeFourDirections": " 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 \n$select({\"values\":[true,false]})$end", + "bombFourDirections": " 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) \n$select({\"values\":[true,false]})$end", + "bigKeyIsBox": " 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 \n$select({\"values\":[true,false]})$end", + "enableNegativeDamage": " /****** 怪物相关 ******/ \n 是否支持负伤害(回血) \n$select({\"values\":[true,false]})$end", + "zoneSquare": " 领域类型。如果此项为true则为九宫格伤害,为false则为十字伤害 \n$select({\"values\":[true,false]})$end", + "startDirectly": " /****** 系统相关 ******/ \n 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 \n$select({\"values\":[true,false]})$end", + "canOpenBattleAnimate": " 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false \n$select({\"values\":[true,false]})$end", + "showBattleAnimateConfirm": " 是否在游戏开始时提供“是否开启战斗动画”的选项 \n$select({\"values\":[true,false]})$end", + "battleAnimate": " 是否默认显示战斗动画;用户可以手动在菜单栏中开关 \n$select({\"values\":[true,false]})$end", + "displayEnemyDamage": " 是否地图怪物显伤;用户可以手动在菜单栏中开关 \n$select({\"values\":[true,false]})$end", + "displayExtraDamage": " 是否地图高级显伤(领域、夹击等);用户可以手动在菜单栏中开关 \n$select({\"values\":[true,false]})$end", + "enableGentleClick": " 是否允许轻触(获得面前物品) \n$select({\"values\":[true,false]})$end", + "portalWithoutTrigger": " 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 \n$select({\"values\":[true,false]})$end", + "potionWhileRouting": " 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 \n$select({\"values\":[true,false]})$end" } } \ No newline at end of file From bb08b1fb61494be56135509e1dd2f715e7ede356 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Tue, 9 Jan 2018 15:44:44 +0800 Subject: [PATCH 024/102] Update editor_mode.js --- _server/editor_mode.js | 34 ++++++++++++++++++++++++++++++---- 1 file changed, 30 insertions(+), 4 deletions(-) diff --git a/_server/editor_mode.js b/_server/editor_mode.js index fbec35fc..aa36d6c4 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -134,7 +134,30 @@ editor_mode.prototype.addAction = function(action){ editor_mode.prototype.doActionList = function(mode,actionList){ if (actionList.length==0)return; - //尚未完成 + switch (mode) { + case 'loc': + + editor_file.editLoc(editor,editor_mode.pos.x,editor_mode.pos.y,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + break; + case 'emenyitem': + + if (editor_mode.info.images=='enemys'){ + editor_file.editEnemy(editor,editor_mode.info.id,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + } else if (editor_mode.info.images=='items'){ + editor_file.editItem(editor,editor_mode.info.id,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + } + break; + case 'floor': + + editor_file.editFloor(editor,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + break; + case 'tower': + + editor.file.editTower(editor,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + break; + default: + break; + } } editor_mode.prototype.onmode = function (mode) { @@ -149,10 +172,11 @@ editor_mode.prototype.onmode = function (mode) { editor_mode.prototype.loc = function(callback){ //editor.pos={x: 0, y: 0}; if (!core.isset(editor.pos))return; - document.getElementById('pos_a6771a78_a099_417c_828f_0a24851ebfce').innerText=editor.pos.x+','+editor.pos.y; + editor_mode.pos=editor.pos; + document.getElementById('pos_a6771a78_a099_417c_828f_0a24851ebfce').innerText=editor_mode.pos.x+','+editor_mode.pos.y; var objs=[]; - editor_file.editLoc(editor,editor.pos.x,editor.pos.y,[],function(objs_){objs=objs_;console.log(objs_)}); + editor_file.editLoc(editor,editor_mode.pos.x,editor_mode.pos.y,[],function(objs_){objs=objs_;console.log(objs_)}); //只查询不修改时,内部实现不是异步的,所以可以这么写 var tableinfo=editor_mode.objToTable(objs[0],objs[1]); document.getElementById('table_3d846fc4_7644_44d1_aa04_433d266a73df').innerHTML=tableinfo.HTML; @@ -167,8 +191,9 @@ editor_mode.prototype.emenyitem = function(callback){ editor_mode.info=editor.info;//避免editor.info被清空导致无法获得是物品还是怪物 if (!core.isset(editor_mode.info.id)){ + document.getElementById('table_a3f03d4c_55b8_4ef6_b362_b345783acd72').innerHTML=''; return; - }//尚未完成 + }//尚未完成,此处要设置成允许添加新的id 和 idnum var objs=[]; if (editor_mode.info.images=='enemys'){ @@ -176,6 +201,7 @@ editor_mode.prototype.emenyitem = function(callback){ } else if (editor_mode.info.images=='items'){ editor_file.editItem(editor,editor_mode.info.id,[],function(objs_){objs=objs_;console.log(objs_)}); } else { + document.getElementById('table_a3f03d4c_55b8_4ef6_b362_b345783acd72').innerHTML=''; return; } //只查询不修改时,内部实现不是异步的,所以可以这么写 From 0c24e662c92dfa7d8b5cfc04faa62829d608396a Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Tue, 9 Jan 2018 23:45:16 +0800 Subject: [PATCH 025/102] editor --- 2.0diff.md | 67 ++++++++++++++++++++++++++++++------------ _server/editor.js | 8 +++++ _server/editor_file.js | 3 +- _server/editor_mode.js | 52 ++++++++++++++++++++++++++++++-- editor.html | 10 +++++-- 5 files changed, 117 insertions(+), 23 deletions(-) diff --git a/2.0diff.md b/2.0diff.md index 0f9ad4eb..814b4b04 100644 --- a/2.0diff.md +++ b/2.0diff.md @@ -12,8 +12,10 @@ + 重命名为`editor.html` * 需要相应的修改本地服务的按钮打开的网址,为了兼容,临时加了个内容为``的`drawMapGUI.html` + 不再独立的导入数据和画图,尽可能的通过`main.init('editor')`复用代码 -+ 能够在本地服务器环境中直接修改`project`中的数据,目前只完成了文件操作的代码`_server/editor_file.js`,前端尚未完成 ++ 能够在本地服务器环境中直接修改`project`中的数据,即全GUI下做塔 + 把`editor`的代码拆到了`_server/editor.js`中 ++ 添加了`_server/css/editor_mode.css`存放编辑模式有关的样式 ++ 添加了`_server/editor_mode.js`存放编辑模式的实现 ## 具体: @@ -24,7 +26,7 @@ `main.listen`和`main.init`改为在`index.html`中执行 -添加了`main.prototype.loadPureData`,在`main.init`中先加载存数据再加载`libs` +添加了`main.prototype.loadPureData`,在`main.init`中先加载纯数据再加载`libs` ### core.js `core.drawMap`中`editor`模式下不再画图,而是生成画图的函数提供给`editor` @@ -74,7 +76,35 @@ editor.file.editFloor(editor,[["change","['title']",'样板 33 层']],function(a editor.file.editTower(editor,[["change","['values']['lavaDamage']",200]],function(a){console.log(a)}); ``` +### editor_mode.js +4个生成表格并绑定事件的函数 +```javascript +editor_mode.loc(); +editor_mode.emenyitem(); +editor_mode.floor(); +editor_mode.tower(); +``` +切换模式 +```javascript +editor_mode.onmode(''); +editor_mode.onmode('loc'); +editor_mode.onmode('emenyitem'); +editor_mode.onmode('floor'); +editor_mode.onmode('tower'); +``` +在切换模式时,改动才会保存到文件,并且需要刷新页面使得`editor`能看到改动 + +表格的`onchange`的实现中,获得当前模式的方式.不注意的话,修改`index.html`中页面的结构,会被坑 +```javascript +var node = thisTr.parentNode; +while (!editor_mode._ids.hasOwnProperty(node.getAttribute('id'))) { + node = node.parentNode; +} +editor_mode.onmode(editor_mode._ids[node.getAttribute('id')]); +``` ### drawMapGUI.html +重命名为`editor.html` + 把`editor`的代码拆到了`_server/editor.js`中 以`display:none`的形式引入了`index.html`的`dom`,修改了原来的`.gameCanvas #ui #data`等的名字以避免冲突 @@ -96,26 +126,27 @@ $range(evalstr:thiseval)$end $leaf(evalstr:thiseval)$end 强制指定为叶节点,如果eval(evalstr)为true -todo: //以下几个中选一个 [ $select(evalstr)$end 渲染成,此为默认选项 +$input(evalstr)$end + 渲染成 $textarea(evalstr)$end - 渲染成
@@ -300,8 +321,8 @@ + + + + + + + + diff --git a/project/comment.js b/project/comment.js index 3e325f1b..af33e2bd 100644 --- a/project/comment.js +++ b/project/comment.js @@ -33,7 +33,7 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "canFlyTo": "该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) \n$select({\"values\":[true,false]})$end", "canUseQuickShop": "该层是否允许使用快捷商店 \n$select({\"values\":[true,false]})$end", "defaultGround": "默认地面的图块ID(terrains中) ", - "png": "背景图;你可以选择一张png图片来作为背景素材。详细用法请参见文档“自定义素材”中的说明。 ", + "png": "背景图;你可以选择一张png图片来作为背景素材。详细用法请参见文档“自定义素材”中的说明。 \n$leaf(true)$end", "color": "该层的默认画面色调。本项可不写(代表无色调),如果写需要是一个RGBA数组。 \n$leaf(true)$end", "bgm": "到达该层后默认播放的BGM。本项可忽略。 ", //"map": "地图数据,需要是13x13,建议使用地图生成器来生成 ", From 7c33ce6b1f50192f38fac4b14ef18c0c297dfc1d Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Thu, 15 Feb 2018 10:00:02 +0800 Subject: [PATCH 030/102] fix bug MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 可以正确的处理null了 --- _server/blockly/MotaAction.g4 | 3 +++ _server/editor.js | 10 +++++----- _server/editor_blockly.js | 7 +++++++ editor.html | 1 + 4 files changed, 16 insertions(+), 5 deletions(-) diff --git a/_server/blockly/MotaAction.g4 b/_server/blockly/MotaAction.g4 index 4fe3294e..a350fc9c 100644 --- a/_server/blockly/MotaAction.g4 +++ b/_server/blockly/MotaAction.g4 @@ -1001,6 +1001,7 @@ function ActionParser(){ ActionParser.prototype.parse = function (obj,type) { switch (type) { case 'event': + if(!obj)obj={}; if(typeof(obj)===typeof('')) obj={'data':[obj]}; if(obj instanceof Array) obj={'data':obj}; return MotaActionBlocks['event_m'].xmlText([ @@ -1008,12 +1009,14 @@ ActionParser.prototype.parse = function (obj,type) { ]); case 'changeFloor': + if(!obj)obj={}; if(!this.isset(obj.loc))obj.loc=[0,0]; return MotaActionBlocks['changeFloor_m'].xmlText([ obj.floorId,obj.stair||'loc',obj.loc[0],obj.loc[1],this.Direction(obj.direction),obj.time||0,!this.isset(obj.portalWithoutTrigger) ]); case 'point': + if(!obj)obj={}; var text_choices = null; for(var ii=obj.choices.length-1,choice;choice=obj.choices[ii];ii--) { text_choices=MotaActionBlocks['choicesContext'].xmlText([ diff --git a/_server/editor.js b/_server/editor.js index a6dc7b18..e19309cd 100644 --- a/_server/editor.js +++ b/_server/editor.js @@ -11,8 +11,8 @@ editor.prototype.init = function(callback){ editor.reset(function(){ editor.drawMapBg(); - var mapArray = core.maps.getMapArray(core.status.maps[core.status.floorId].blocks); - editor.map = mapArray.map(function(v){return v.map(function(v){return editor.ids[[editor.indexs[v][0]]]})}); + var mapArray = core.maps.save(core.status.maps,core.status.floorId); + editor.map = mapArray.map(function(v){return v.map(function(v){return editor.ids[[editor.indexs[parseInt(v)][0]]]})}); editor.updateMap(); editor.currentFloorId=core.status.floorId; editor.currentFloorData = core.floors[core.status.floorId]; @@ -35,7 +35,7 @@ editor.prototype.init = function(callback){ }); core.events.setInitData(hard); } - setTimeout(afterMainInit, 300); + setTimeout(afterMainInit, 500); } editor.prototype.reset = function(callback){ @@ -298,8 +298,8 @@ editor.prototype.changeFloor = function(floorId,callback) { editor.currentFloorData.map = editor.map.map(function(v){return v.map(function(v){return v.idnum||v||0})}); core.changeFloor(floorId, null, core.firstData.hero.loc, null, function(){ editor.drawMapBg(); - var mapArray = core.maps.getMapArray(core.status.maps[core.status.floorId].blocks); - editor.map = mapArray.map(function(v){return v.map(function(v){return editor.ids[[editor.indexs[v][0]]]})}); + var mapArray = core.maps.save(core.status.maps,core.status.floorId); + editor.map = mapArray.map(function(v){return v.map(function(v){return editor.ids[[editor.indexs[parseInt(v)][0]]]})}); editor.updateMap(); editor.currentFloorId=core.status.floorId; editor.currentFloorData = core.floors[core.status.floorId]; diff --git a/_server/editor_blockly.js b/_server/editor_blockly.js index 6e535c62..dee70dae 100644 --- a/_server/editor_blockly.js +++ b/_server/editor_blockly.js @@ -304,6 +304,9 @@ editor_blockly.import = function(id_){ "['firstData']['shops']":'shop', + "['firstArrive']":'firstArrive', + "['firstData']['startText']":'firstArrive', + "--point--未完成数据转移":'point', }[field]; if(!type)return; @@ -311,8 +314,11 @@ editor_blockly.import = function(id_){ document.getElementById('codeArea').value = input.value; document.getElementById('entryType').value = type; editor_blockly.parse(); + editor_blockly.show(); } +editor_blockly.show = function(){} + editor_blockly.confirm = function (){ if(!editor_blockly.id){ editor_blockly.id=''; @@ -346,6 +352,7 @@ editor_blockly.doubleClickBlock = function (blockId){ var f=textStringDict[b]; if(f){ var value = b.getFieldValue(f); + //多行编辑 //func(value,function(newvalue,b,f){b.setFieldValue(newvalue,f);}) } } diff --git a/editor.html b/editor.html index f0ecb527..7c2c5599 100644 --- a/editor.html +++ b/editor.html @@ -123,6 +123,7 @@ + From 9fe928530ce5ab68d0a17fe0e0b222631e734b89 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Thu, 15 Feb 2018 19:23:37 +0800 Subject: [PATCH 031/102] fix bug: default floor in floor selecter of editor --- _server/editor_mode.js | 1 + 1 file changed, 1 insertion(+) diff --git a/_server/editor_mode.js b/_server/editor_mode.js index 8835baa4..f21f93b2 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -257,6 +257,7 @@ editor_mode.prototype.listen = function(callback){ outstr.push(["\n'].join('')); }); selectFloor.innerHTML=outstr.join(''); + selectFloor.value=core.status.floorId; selectFloor.onchange = function(){ editor_mode.onmode(''); editor.changeFloor(selectFloor.value); From 93160d21561d6b59579a7155e5a6ac5b9ff093fa Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 17 Feb 2018 17:16:05 +0800 Subject: [PATCH 032/102] =?UTF-8?q?=E5=BC=95=E5=85=A5CodeMirror=E4=BD=9C?= =?UTF-8?q?=E4=B8=BA=E5=A4=9A=E8=A1=8C=E6=96=87=E6=9C=AC=E7=BC=96=E8=BE=91?= =?UTF-8?q?=E5=99=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/CodeMirror/LICENSE | 21 ++ _server/CodeMirror/codeMirror.bundle.min.js | 1 + _server/CodeMirror/codemirror.css | 346 ++++++++++++++++++++ _server/css/editor_mode.css | 11 + _server/editor_blockly.js | 30 +- editor.html | 10 +- 6 files changed, 415 insertions(+), 4 deletions(-) create mode 100644 _server/CodeMirror/LICENSE create mode 100644 _server/CodeMirror/codeMirror.bundle.min.js create mode 100644 _server/CodeMirror/codemirror.css diff --git a/_server/CodeMirror/LICENSE b/_server/CodeMirror/LICENSE new file mode 100644 index 00000000..ff7db4b9 --- /dev/null +++ b/_server/CodeMirror/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (C) 2017 by Marijn Haverbeke and others + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/_server/CodeMirror/codeMirror.bundle.min.js b/_server/CodeMirror/codeMirror.bundle.min.js new file mode 100644 index 00000000..f8a06300 --- /dev/null +++ b/_server/CodeMirror/codeMirror.bundle.min.js @@ -0,0 +1 @@ +!function(e){var t={};function n(r){if(t[r])return t[r].exports;var i=t[r]={i:r,l:!1,exports:{}};return e[r].call(i.exports,i,i.exports,n),i.l=!0,i.exports}n.m=e,n.c=t,n.d=function(e,t,r){n.o(e,t)||Object.defineProperty(e,t,{configurable:!1,enumerable:!0,get:r})},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,"a",t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p="",n(n.s=0)}([function(e,t){CodeMirror=function(){"use strict";var e=navigator.userAgent,t=navigator.platform,n=/gecko\/\d/i.test(e),r=/MSIE \d/.test(e),i=/Trident\/(?:[7-9]|\d{2,})\..*rv:(\d+)/.exec(e),o=/Edge\/(\d+)/.exec(e),l=r||i||o,a=l&&(r?document.documentMode||6:+(o||i)[1]),s=!o&&/WebKit\//.test(e),u=s&&/Qt\/\d+\.\d+/.test(e),c=!o&&/Chrome\//.test(e),f=/Opera\//.test(e),h=/Apple Computer/.test(navigator.vendor),d=/Mac OS X 1\d\D([8-9]|\d\d)\D/.test(e),p=/PhantomJS/.test(e),g=!o&&/AppleWebKit/.test(e)&&/Mobile\/\w+/.test(e),m=/Android/.test(e),v=g||m||/webOS|BlackBerry|Opera Mini|Opera Mobi|IEMobile/i.test(e),y=g||/Mac/.test(t),b=/\bCrOS\b/.test(e),x=/win/i.test(t),w=f&&e.match(/Version\/(\d*\.\d*)/);w&&(w=Number(w[1])),w&&w>=15&&(f=!1,s=!0);var C=y&&(u||f&&(null==w||w<12.11)),k=n||l&&a>=9;function S(e){return new RegExp("(^|\\s)"+e+"(?:$|\\s)\\s*")}var L,T=function(e,t){var n=e.className,r=S(t).exec(n);if(r){var i=n.slice(r.index+r[0].length);e.className=n.slice(0,r.index)+(i?r[1]+i:"")}};function M(e){for(var t=e.childNodes.length;t>0;--t)e.removeChild(e.firstChild);return e}function A(e,t){return M(e).appendChild(t)}function O(e,t,n,r){var i=document.createElement(e);if(n&&(i.className=n),r&&(i.style.cssText=r),"string"==typeof t)i.appendChild(document.createTextNode(t));else if(t)for(var o=0;o=t)return l+(t-o);l+=a-o,l+=n-l%n,o=a+1}}g?P=function(e){e.selectionStart=0,e.selectionEnd=e.value.length}:l&&(P=function(e){try{e.select()}catch(e){}});var R=function(){this.id=null};function B(e,t){for(var n=0;n=t)return r+Math.min(l,t-i);if(i+=o-r,r=o+1,(i+=n-i%n)>=t)return r}}var $=[""];function Y(e){for(;$.length<=e;)$.push(_($)+" ");return $[e]}function _(e){return e[e.length-1]}function q(e,t){for(var n=[],r=0;r"€"&&(e.toUpperCase()!=e.toLowerCase()||J.test(e))}function te(e,t){return t?!!(t.source.indexOf("\\w")>-1&&ee(e))||t.test(e):ee(e)}function ne(e){for(var t in e)if(e.hasOwnProperty(t)&&e[t])return!1;return!0}var re=/[\u0300-\u036f\u0483-\u0489\u0591-\u05bd\u05bf\u05c1\u05c2\u05c4\u05c5\u05c7\u0610-\u061a\u064b-\u065e\u0670\u06d6-\u06dc\u06de-\u06e4\u06e7\u06e8\u06ea-\u06ed\u0711\u0730-\u074a\u07a6-\u07b0\u07eb-\u07f3\u0816-\u0819\u081b-\u0823\u0825-\u0827\u0829-\u082d\u0900-\u0902\u093c\u0941-\u0948\u094d\u0951-\u0955\u0962\u0963\u0981\u09bc\u09be\u09c1-\u09c4\u09cd\u09d7\u09e2\u09e3\u0a01\u0a02\u0a3c\u0a41\u0a42\u0a47\u0a48\u0a4b-\u0a4d\u0a51\u0a70\u0a71\u0a75\u0a81\u0a82\u0abc\u0ac1-\u0ac5\u0ac7\u0ac8\u0acd\u0ae2\u0ae3\u0b01\u0b3c\u0b3e\u0b3f\u0b41-\u0b44\u0b4d\u0b56\u0b57\u0b62\u0b63\u0b82\u0bbe\u0bc0\u0bcd\u0bd7\u0c3e-\u0c40\u0c46-\u0c48\u0c4a-\u0c4d\u0c55\u0c56\u0c62\u0c63\u0cbc\u0cbf\u0cc2\u0cc6\u0ccc\u0ccd\u0cd5\u0cd6\u0ce2\u0ce3\u0d3e\u0d41-\u0d44\u0d4d\u0d57\u0d62\u0d63\u0dca\u0dcf\u0dd2-\u0dd4\u0dd6\u0ddf\u0e31\u0e34-\u0e3a\u0e47-\u0e4e\u0eb1\u0eb4-\u0eb9\u0ebb\u0ebc\u0ec8-\u0ecd\u0f18\u0f19\u0f35\u0f37\u0f39\u0f71-\u0f7e\u0f80-\u0f84\u0f86\u0f87\u0f90-\u0f97\u0f99-\u0fbc\u0fc6\u102d-\u1030\u1032-\u1037\u1039\u103a\u103d\u103e\u1058\u1059\u105e-\u1060\u1071-\u1074\u1082\u1085\u1086\u108d\u109d\u135f\u1712-\u1714\u1732-\u1734\u1752\u1753\u1772\u1773\u17b7-\u17bd\u17c6\u17c9-\u17d3\u17dd\u180b-\u180d\u18a9\u1920-\u1922\u1927\u1928\u1932\u1939-\u193b\u1a17\u1a18\u1a56\u1a58-\u1a5e\u1a60\u1a62\u1a65-\u1a6c\u1a73-\u1a7c\u1a7f\u1b00-\u1b03\u1b34\u1b36-\u1b3a\u1b3c\u1b42\u1b6b-\u1b73\u1b80\u1b81\u1ba2-\u1ba5\u1ba8\u1ba9\u1c2c-\u1c33\u1c36\u1c37\u1cd0-\u1cd2\u1cd4-\u1ce0\u1ce2-\u1ce8\u1ced\u1dc0-\u1de6\u1dfd-\u1dff\u200c\u200d\u20d0-\u20f0\u2cef-\u2cf1\u2de0-\u2dff\u302a-\u302f\u3099\u309a\ua66f-\ua672\ua67c\ua67d\ua6f0\ua6f1\ua802\ua806\ua80b\ua825\ua826\ua8c4\ua8e0-\ua8f1\ua926-\ua92d\ua947-\ua951\ua980-\ua982\ua9b3\ua9b6-\ua9b9\ua9bc\uaa29-\uaa2e\uaa31\uaa32\uaa35\uaa36\uaa43\uaa4c\uaab0\uaab2-\uaab4\uaab7\uaab8\uaabe\uaabf\uaac1\uabe5\uabe8\uabed\udc00-\udfff\ufb1e\ufe00-\ufe0f\ufe20-\ufe26\uff9e\uff9f]/;function ie(e){return e.charCodeAt(0)>=768&&re.test(e)}function oe(e,t,n){for(;(n<0?t>0:tn?-1:1;;){if(t==n)return t;var i=(t+n)/2,o=r<0?Math.ceil(i):Math.floor(i);if(o==t)return e(o)?t:n;e(o)?n=o:t=o+r}}function ae(e,t){if((t-=e.first)<0||t>=e.size)throw new Error("There is no line "+(t+e.first)+" in the document.");for(var n=e;!n.lines;)for(var r=0;;++r){var i=n.children[r],o=i.chunkSize();if(t=e.first&&tn?ge(n,ae(e,n).text.length):function(e,t){var n=e.ch;return null==n||n>t?ge(e.line,t):n<0?ge(e.line,0):e}(t,ae(e,t.line).text.length)}function ke(e,t){for(var n=[],r=0;r=t:o.to>t);(r||(r=[])).push(new Te(l,o.from,s?null:o.to))}}return r}(n,i,l),s=function(e,t,n){var r;if(e)for(var i=0;i=t:o.to>t);if(a||o.from==t&&"bookmark"==l.type&&(!n||o.marker.insertLeft)){var s=null==o.from||(l.inclusiveLeft?o.from<=t:o.from0&&a)for(var x=0;x=0&&f<=0||c<=0&&f>=0)&&(c<=0&&(s.marker.inclusiveRight&&i.inclusiveLeft?me(u.to,n)>=0:me(u.to,n)>0)||c>=0&&(s.marker.inclusiveRight&&i.inclusiveLeft?me(u.from,r)<=0:me(u.from,r)<0)))return!0}}}function Be(e){for(var t;t=Ie(e);)e=t.find(-1,!0).line;return e}function je(e,t){var n=ae(e,t),r=Be(n);return n==r?t:fe(r)}function Ve(e,t){if(t>e.lastLine())return t;var n,r=ae(e,t);if(!Ge(e,r))return t;for(;n=ze(r);)r=n.find(1,!0).line;return fe(r)+1}function Ge(e,t){var n=Le&&t.markedSpans;if(n)for(var r=void 0,i=0;it.maxLineLength&&(t.maxLineLength=n,t.maxLine=e)})}var Ye=null;function _e(e,t,n){var r;Ye=null;for(var i=0;it)return i;o.to==t&&(o.from!=o.to&&"before"==n?r=i:Ye=i),o.from==t&&(o.from!=o.to&&"before"!=n?r=i:Ye=i)}return null!=r?r:Ye}var qe=function(){var e="bbbbbbbbbtstwsbbbbbbbbbbbbbbssstwNN%%%NNNNNN,N,N1111111111NNNNNNNLLLLLLLLLLLLLLLLLLLLLLLLLLNNNNNNLLLLLLLLLLLLLLLLLLLLLLLLLLNNNNbbbbbbsbbbbbbbbbbbbbbbbbbbbbbbbbb,N%%%%NNNNLNNNNN%%11NLNNN1LNNNNNLLLLLLLLLLLLLLLLLLLLLLLNLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLN",t="nnnnnnNNr%%r,rNNmmmmmmmmmmmrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrmmmmmmmmmmmmmmmmmmmmmnnnnnnnnnn%nnrrrmrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrmmmmmmmnNmmmmmmrrmmNmmmmrr1111111111";var n=/[\u0590-\u05f4\u0600-\u06ff\u0700-\u08ac]/,r=/[stwN]/,i=/[LRr]/,o=/[Lb1n]/,l=/[1n]/;function a(e,t,n){this.level=e,this.from=t,this.to=n}return function(s,u){var c,f="ltr"==u?"L":"R";if(0==s.length||"ltr"==u&&!n.test(s))return!1;for(var h=s.length,d=[],p=0;p-1&&(r[t]=i.slice(0,o).concat(i.slice(o+1)))}}}function nt(e,t){var n=et(e,t);if(n.length)for(var r=Array.prototype.slice.call(arguments,2),i=0;i0}function lt(e){e.prototype.on=function(e,t){Je(this,e,t)},e.prototype.off=function(e,t){tt(this,e,t)}}function at(e){e.preventDefault?e.preventDefault():e.returnValue=!1}function st(e){e.stopPropagation?e.stopPropagation():e.cancelBubble=!0}function ut(e){return null!=e.defaultPrevented?e.defaultPrevented:0==e.returnValue}function ct(e){at(e),st(e)}function ft(e){return e.target||e.srcElement}function ht(e){var t=e.which;return null==t&&(1&e.button?t=1:2&e.button?t=3:4&e.button&&(t=2)),y&&e.ctrlKey&&1==t&&(t=3),t}var dt,pt,gt=function(){if(l&&a<9)return!1;var e=O("div");return"draggable"in e||"dragDrop"in e}();function mt(e){if(null==dt){var t=O("span","​");A(e,O("span",[t,document.createTextNode("x")])),0!=e.firstChild.offsetHeight&&(dt=t.offsetWidth<=1&&t.offsetHeight>2&&!(l&&a<8))}var n=dt?O("span","​"):O("span"," ",null,"display: inline-block; width: 1px; margin-right: -1px");return n.setAttribute("cm-text",""),n}function vt(e){if(null!=pt)return pt;var t=A(e,document.createTextNode("AخA")),n=L(t,0,1).getBoundingClientRect(),r=L(t,1,2).getBoundingClientRect();return M(e),!(!n||n.left==n.right)&&(pt=r.right-n.right<3)}var yt,bt=3!="\n\nb".split(/\n/).length?function(e){for(var t=0,n=[],r=e.length;t<=r;){var i=e.indexOf("\n",t);-1==i&&(i=e.length);var o=e.slice(t,"\r"==e.charAt(i-1)?i-1:i),l=o.indexOf("\r");-1!=l?(n.push(o.slice(0,l)),t+=l+1):(n.push(o),t=i+1)}return n}:function(e){return e.split(/\r\n?|\n/)},xt=window.getSelection?function(e){try{return e.selectionStart!=e.selectionEnd}catch(e){return!1}}:function(e){var t;try{t=e.ownerDocument.selection.createRange()}catch(e){}return!(!t||t.parentElement()!=e)&&0!=t.compareEndPoints("StartToEnd",t)},wt="oncopy"in(yt=O("div"))||(yt.setAttribute("oncopy","return;"),"function"==typeof yt.oncopy),Ct=null,kt={},St={};function Lt(e){if("string"==typeof e&&St.hasOwnProperty(e))e=St[e];else if(e&&"string"==typeof e.name&&St.hasOwnProperty(e.name)){var t=St[e.name];"string"==typeof t&&(t={name:t}),(e=Q(t,e)).name=t.name}else{if("string"==typeof e&&/^[\w\-]+\/[\w\-]+\+xml$/.test(e))return Lt("application/xml");if("string"==typeof e&&/^[\w\-]+\/[\w\-]+\+json$/.test(e))return Lt("application/json")}return"string"==typeof e?{name:e}:e||{name:"null"}}function Tt(e,t){t=Lt(t);var n=kt[t.name];if(!n)return Tt(e,"text/plain");var r=n(e,t);if(Mt.hasOwnProperty(t.name)){var i=Mt[t.name];for(var o in i)i.hasOwnProperty(o)&&(r.hasOwnProperty(o)&&(r["_"+o]=r[o]),r[o]=i[o])}if(r.name=t.name,t.helperType&&(r.helperType=t.helperType),t.modeProps)for(var l in t.modeProps)r[l]=t.modeProps[l];return r}var Mt={};function At(e,t){var n=Mt.hasOwnProperty(e)?Mt[e]:Mt[e]={};I(t,n)}function Ot(e,t){if(!0===t)return t;if(e.copyState)return e.copyState(t);var n={};for(var r in t){var i=t[r];i instanceof Array&&(i=i.concat([])),n[r]=i}return n}function Nt(e,t){for(var n;e.innerMode&&(n=e.innerMode(t))&&n.mode!=e;)t=n.state,e=n.mode;return n||{mode:e,state:t}}function Wt(e,t,n){return!e.startState||e.startState(t,n)}var Dt=function(e,t,n){this.pos=this.start=0,this.string=e,this.tabSize=t||8,this.lastColumnPos=this.lastColumnValue=0,this.lineStart=0,this.lineOracle=n};Dt.prototype.eol=function(){return this.pos>=this.string.length},Dt.prototype.sol=function(){return this.pos==this.lineStart},Dt.prototype.peek=function(){return this.string.charAt(this.pos)||void 0},Dt.prototype.next=function(){if(this.post},Dt.prototype.eatSpace=function(){for(var e=this.pos;/[\s\u00a0]/.test(this.string.charAt(this.pos));)++this.pos;return this.pos>e},Dt.prototype.skipToEnd=function(){this.pos=this.string.length},Dt.prototype.skipTo=function(e){var t=this.string.indexOf(e,this.pos);if(t>-1)return this.pos=t,!0},Dt.prototype.backUp=function(e){this.pos-=e},Dt.prototype.column=function(){return this.lastColumnPos0?null:(r&&!1!==t&&(this.pos+=r[0].length),r)}var i=function(e){return n?e.toLowerCase():e},o=this.string.substr(this.pos,e.length);if(i(o)==i(e))return!1!==t&&(this.pos+=e.length),!0},Dt.prototype.current=function(){return this.string.slice(this.start,this.pos)},Dt.prototype.hideFirstChars=function(e,t){this.lineStart+=e;try{return t()}finally{this.lineStart-=e}},Dt.prototype.lookAhead=function(e){var t=this.lineOracle;return t&&t.lookAhead(e)},Dt.prototype.baseToken=function(){var e=this.lineOracle;return e&&e.baseToken(this.pos)};var Ht=function(e,t){this.state=e,this.lookAhead=t},Et=function(e,t,n,r){this.state=t,this.doc=e,this.line=n,this.maxLookAhead=r||0,this.baseTokens=null,this.baseTokenPos=1};function Pt(e,t,n,r){var i=[e.state.modeGen],o={};Ut(e,t.text,e.doc.mode,n,function(e,t){return i.push(e,t)},o,r);for(var l=n.state,a=function(r){n.baseTokens=i;var a=e.state.overlays[r],s=1,u=0;n.state=!0,Ut(e,t.text,a.mode,n,function(e,t){for(var n=s;ue&&i.splice(s,1,e,i[s+1],r),s+=2,u=Math.min(e,r)}if(t)if(a.opaque)i.splice(n,s-n,e,"overlay "+t),s=n+2;else for(;ne.options.maxHighlightLength&&Ot(e.doc.mode,r.state),o=Pt(e,t,r);i&&(r.state=i),t.stateAfter=r.save(!i),t.styles=o.styles,o.classes?t.styleClasses=o.classes:t.styleClasses&&(t.styleClasses=null),n===e.doc.highlightFrontier&&(e.doc.modeFrontier=Math.max(e.doc.modeFrontier,++e.doc.highlightFrontier))}return t.styles}function It(e,t,n){var r=e.doc,i=e.display;if(!r.mode.startState)return new Et(r,!0,t);var o=function(e,t,n){for(var r,i,o=e.doc,l=n?-1:t-(e.doc.mode.innerMode?1e3:100),a=t;a>l;--a){if(a<=o.first)return o.first;var s=ae(o,a-1),u=s.stateAfter;if(u&&(!n||a+(u instanceof Ht?u.lookAhead:0)<=o.modeFrontier))return a;var c=z(s.text,null,e.options.tabSize);(null==i||r>c)&&(i=a-1,r=c)}return i}(e,t,n),l=o>r.first&&ae(r,o-1).stateAfter,a=l?Et.fromSaved(r,l,o):new Et(r,Wt(r.mode),o);return r.iter(o,t,function(n){zt(e,n.text,a);var r=a.line;n.stateAfter=r==t-1||r%5==0||r>=i.viewFrom&&rt.start)return o}throw new Error("Mode "+e.name+" failed to advance stream.")}Et.prototype.lookAhead=function(e){var t=this.doc.getLine(this.line+e);return null!=t&&e>this.maxLookAhead&&(this.maxLookAhead=e),t},Et.prototype.baseToken=function(e){if(!this.baseTokens)return null;for(;this.baseTokens[this.baseTokenPos]<=e;)this.baseTokenPos+=2;var t=this.baseTokens[this.baseTokenPos+1];return{type:t&&t.replace(/( |^)overlay .*/,""),size:this.baseTokens[this.baseTokenPos]-e}},Et.prototype.nextLine=function(){this.line++,this.maxLookAhead>0&&this.maxLookAhead--},Et.fromSaved=function(e,t,n){return t instanceof Ht?new Et(e,Ot(e.mode,t.state),n,t.lookAhead):new Et(e,Ot(e.mode,t),n)},Et.prototype.save=function(e){var t=!1!==e?Ot(this.doc.mode,this.state):this.state;return this.maxLookAhead>0?new Ht(t,this.maxLookAhead):t};var jt=function(e,t,n){this.start=e.start,this.end=e.pos,this.string=e.current(),this.type=t||null,this.state=n};function Vt(e,t,n,r){var i,o=e.doc,l=o.mode;t=Ce(o,t);var a,s=ae(o,t.line),u=It(e,t.line,n),c=new Dt(s.text,e.options.tabSize,u);for(r&&(a=[]);(r||c.pose.options.maxHighlightLength?(a=!1,l&&zt(e,t,r,f.pos),f.pos=t.length,s=null):s=Gt(Bt(n,f,r.state,h),o),h){var d=h[0].name;d&&(s="m-"+(s?d+" "+s:d))}if(!a||c!=s){for(;u1&&!/ /.test(e))return e;for(var n=t,r="",i=0;iu&&f.from<=u);h++);if(f.to>=c)return e(n,r,i,o,l,a,s);e(n,r.slice(0,f.to-u),i,o,null,a,s),o=null,r=r.slice(f.to-u),u=f.to}}}function en(e,t,n,r){var i=!r&&n.widgetNode;i&&e.map.push(e.pos,e.pos+t,i),!r&&e.cm.display.input.needsContentAttribute&&(i||(i=e.content.appendChild(document.createElement("span"))),i.setAttribute("cm-marker",n.id)),i&&(e.cm.display.input.setUneditable(i),e.content.appendChild(i)),e.pos+=t,e.trailingSpace=!1}function tn(e,t,n){var r=e.markedSpans,i=e.text,o=0;if(r)for(var l,a,s,u,c,f,h,d=i.length,p=0,g=1,m="",v=0;;){if(v==p){s=u=c=f=a="",h=null,v=1/0;for(var y=[],b=void 0,x=0;xp||C.collapsed&&w.to==p&&w.from==p)?(null!=w.to&&w.to!=p&&v>w.to&&(v=w.to,u=""),C.className&&(s+=" "+C.className),C.css&&(a=(a?a+";":"")+C.css),C.startStyle&&w.from==p&&(c+=" "+C.startStyle),C.endStyle&&w.to==v&&(b||(b=[])).push(C.endStyle,w.to),C.title&&!f&&(f=C.title),C.collapsed&&(!h||Pe(h.marker,C)<0)&&(h=w)):w.from>p&&v>w.from&&(v=w.from)}if(b)for(var k=0;k=d)break;for(var L=Math.min(d,v);;){if(m){var T=p+m.length;if(!h){var M=T>L?m.slice(0,L-p):m;t.addToken(t,M,l?l+s:s,c,p+M.length==v?u:"",f,a)}if(T>=L){m=m.slice(L-p),p=L;break}p=T,c=""}m=i.slice(o,o=n[g++]),l=_t(n[g++],t.cm.options)}}else for(var A=1;An)return{map:e.measure.maps[i],cache:e.measure.caches[i],before:!0}}function On(e,t,n,r){return Dn(e,Wn(e,t),n,r)}function Nn(e,t){if(t>=e.display.viewFrom&&t=n.lineN&&t2&&o.push((s.bottom+u.top)/2-n.top)}}o.push(n.bottom-n.top)}}(e,t.view,t.rect),t.hasHeights=!0),(o=function(e,t,n,r){var i,o=Pn(t.map,n,r),s=o.node,u=o.start,c=o.end,f=o.collapse;if(3==s.nodeType){for(var h=0;h<4;h++){for(;u&&ie(t.line.text.charAt(o.coverStart+u));)--u;for(;o.coverStart+c1}(e))return t;var n=screen.logicalXDPI/screen.deviceXDPI,r=screen.logicalYDPI/screen.deviceYDPI;return{left:t.left*n,right:t.right*n,top:t.top*r,bottom:t.bottom*r}}(e.display.measure,i))}else{var d;u>0&&(f=r="right"),i=e.options.lineWrapping&&(d=s.getClientRects()).length>1?d["right"==r?d.length-1:0]:s.getBoundingClientRect()}if(l&&a<9&&!u&&(!i||!i.left&&!i.right)){var p=s.parentNode.getClientRects()[0];i=p?{left:p.left,right:p.left+tr(e.display),top:p.top,bottom:p.bottom}:En}for(var g=i.top-t.rect.top,m=i.bottom-t.rect.top,v=(g+m)/2,y=t.view.measure.heights,b=0;bt)&&(i=(o=s-a)-1,t>=s&&(l="right")),null!=i){if(r=e[u+2],a==s&&n==(r.insertLeft?"left":"right")&&(l=n),"left"==n&&0==i)for(;u&&e[u-2]==e[u-3]&&e[u-1].insertLeft;)r=e[2+(u-=3)],l="left";if("right"==n&&i==s-a)for(;u=0&&(n=e[i]).left==n.right;i--);return n}function In(e){if(e.measure&&(e.measure.cache={},e.measure.heights=null,e.rest))for(var t=0;t=r.text.length?(s=r.text.length,u="before"):s<=0&&(s=0,u="after"),!a)return l("before"==u?s-1:s,"before"==u);function c(e,t,n){var r=a[t],i=1==r.level;return l(n?e-1:e,i!=n)}var f=_e(a,s,u),h=Ye,d=c(s,f,"before"==u);return null!=h&&(d.other=c(s,h,"before"!=u)),d}function $n(e,t){var n=0;t=Ce(e.doc,t),e.options.lineWrapping||(n=tr(e.display)*t.ch);var r=ae(e.doc,t.line),i=Ke(r)+Cn(e.display);return{left:n,right:n,top:i,bottom:i+r.height}}function Yn(e,t,n,r,i){var o=ge(e,t,n);return o.xRel=i,r&&(o.outside=!0),o}function _n(e,t,n){var r=e.doc;if((n+=e.display.viewOffset)<0)return Yn(r.first,0,null,!0,-1);var i=he(r,n),o=r.first+r.size-1;if(i>o)return Yn(r.first+r.size-1,ae(r,o).text.length,null,!0,1);t<0&&(t=0);for(var l=ae(r,i);;){var a=Jn(e,l,i,t,n),s=ze(l),u=s&&s.find(0,!0);if(!s||!(a.ch>u.from.ch||a.ch==u.from.ch&&a.xRel>0))return a;i=fe(l=u.to.line)}}function qn(e,t,n,r){r-=Vn(t);var i=t.text.length,o=le(function(t){return Dn(e,n,t-1).bottom<=r},i,0);return i=le(function(t){return Dn(e,n,t).top>r},o,i),{begin:o,end:i}}function Zn(e,t,n,r){n||(n=Wn(e,t));var i=Gn(e,t,Dn(e,n,r),"line").top;return qn(e,t,n,i)}function Qn(e,t,n,r){return!(e.bottom<=n)&&(e.top>n||(r?e.left:e.right)>t)}function Jn(e,t,n,r,i){i-=Ke(t);var o=Wn(e,t),l=Vn(t),a=0,s=t.text.length,u=!0,c=Ze(t,e.doc.direction);if(c){var f=(e.options.lineWrapping?function(e,t,n,r,i,o,l){var a=qn(e,t,r,l),s=a.begin,u=a.end;/\s/.test(t.text.charAt(u-1))&&u--;for(var c=null,f=null,h=0;h=u||d.to<=s)){var p=1!=d.level,g=Dn(e,r,p?Math.min(u,d.to)-1:Math.max(s,d.from)).right,m=gm)&&(c=d,f=m)}}return c||(c=i[i.length-1]),c.fromu&&(c={from:c.from,to:u,level:c.level}),c}:function(e,t,n,r,i,o,l){var a=le(function(a){var s=i[a],u=1!=s.level;return Qn(Xn(e,ge(n,u?s.to:s.from,u?"before":"after"),"line",t,r),o,l,!0)},0,i.length-1),s=i[a];if(a>0){var u=1!=s.level,c=Xn(e,ge(n,u?s.from:s.to,u?"after":"before"),"line",t,r);Qn(c,o,l,!0)&&c.top>l&&(s=i[a-1])}return s})(e,t,n,o,c,r,i);u=1!=f.level,a=u?f.from:f.to-1,s=u?f.to:f.from-1}var h,d,p=null,g=null,m=le(function(t){var n=Dn(e,o,t);return n.top+=l,n.bottom+=l,!!Qn(n,r,i,!1)&&(n.top<=i&&n.left<=r&&(p=t,g=n),!0)},a,s),v=!1;if(g){var y=r-g.left=x.bottom}return m=oe(t.text,m,1),Yn(n,m,d,v,r-h)}function er(e){if(null!=e.cachedTextHeight)return e.cachedTextHeight;if(null==Hn){Hn=O("pre");for(var t=0;t<49;++t)Hn.appendChild(document.createTextNode("x")),Hn.appendChild(O("br"));Hn.appendChild(document.createTextNode("x"))}A(e.measure,Hn);var n=Hn.offsetHeight/50;return n>3&&(e.cachedTextHeight=n),M(e.measure),n||1}function tr(e){if(null!=e.cachedCharWidth)return e.cachedCharWidth;var t=O("span","xxxxxxxxxx"),n=O("pre",[t]);A(e.measure,n);var r=t.getBoundingClientRect(),i=(r.right-r.left)/10;return i>2&&(e.cachedCharWidth=i),i||10}function nr(e){for(var t=e.display,n={},r={},i=t.gutters.clientLeft,o=t.gutters.firstChild,l=0;o;o=o.nextSibling,++l)n[e.options.gutters[l]]=o.offsetLeft+o.clientLeft+i,r[e.options.gutters[l]]=o.clientWidth;return{fixedPos:rr(t),gutterTotalWidth:t.gutters.offsetWidth,gutterLeft:n,gutterWidth:r,wrapperWidth:t.wrapper.clientWidth}}function rr(e){return e.scroller.getBoundingClientRect().left-e.sizer.getBoundingClientRect().left}function ir(e){var t=er(e.display),n=e.options.lineWrapping,r=n&&Math.max(5,e.display.scroller.clientWidth/tr(e.display)-3);return function(i){if(Ge(e.doc,i))return 0;var o=0;if(i.widgets)for(var l=0;l=e.display.viewTo)return null;if((t-=e.display.viewFrom)<0)return null;for(var n=e.display.view,r=0;r=e.display.viewTo||a.to().linet||t==n&&l.to==t)&&(r(Math.max(l.from,t),Math.min(l.to,n),1==l.level?"rtl":"ltr",o),i=!0)}i||r(t,n,"ltr")}(g,n||0,null==r?h:r,function(e,t,i,f){var m="ltr"==i,v=d(e,m?"left":"right"),y=d(t-1,m?"right":"left"),b=null==n&&0==e,x=null==r&&t==h,w=0==f,C=!g||f==g.length-1;if(y.top-v.top<=3){var k=(u?b:x)&&w,S=(u?x:b)&&C,L=k?a:(m?v:y).left,T=S?s:(m?y:v).right;c(L,v.top,T-L,v.bottom)}else{var M,A,O,N;m?(M=u&&b&&w?a:v.left,A=u?s:p(e,i,"before"),O=u?a:p(t,i,"after"),N=u&&x&&C?s:y.right):(M=u?p(e,i,"before"):a,A=!u&&b&&w?s:v.right,O=!u&&x&&C?a:y.left,N=u?p(t,i,"after"):s),c(M,v.top,A-M,v.bottom),v.bottom0?t.blinker=setInterval(function(){return t.cursorDiv.style.visibility=(n=!n)?"":"hidden"},e.options.cursorBlinkRate):e.options.cursorBlinkRate<0&&(t.cursorDiv.style.visibility="hidden")}}function pr(e){e.state.focused||(e.display.input.focus(),mr(e))}function gr(e){e.state.delayingBlurEvent=!0,setTimeout(function(){e.state.delayingBlurEvent&&(e.state.delayingBlurEvent=!1,vr(e))},100)}function mr(e,t){e.state.delayingBlurEvent&&(e.state.delayingBlurEvent=!1),"nocursor"!=e.options.readOnly&&(e.state.focused||(nt(e,"focus",e,t),e.state.focused=!0,H(e.display.wrapper,"CodeMirror-focused"),e.curOp||e.display.selForContextMenu==e.doc.sel||(e.display.input.reset(),s&&setTimeout(function(){return e.display.input.reset(!0)},20)),e.display.input.receivedFocus()),dr(e))}function vr(e,t){e.state.delayingBlurEvent||(e.state.focused&&(nt(e,"blur",e,t),e.state.focused=!1,T(e.display.wrapper,"CodeMirror-focused")),clearInterval(e.display.blinker),setTimeout(function(){e.state.focused||(e.display.shift=!1)},150))}function yr(e){for(var t=e.display,n=t.lineDiv.offsetTop,r=0;r.005||c<-.005)&&(ce(i.line,o),br(i.line),i.rest))for(var f=0;f=l&&(o=he(t,Ke(ae(t,s))-e.wrapper.clientHeight),l=s)}return{from:o,to:Math.max(l,o+1)}}function wr(e){var t=e.display,n=t.view;if(t.alignWidgets||t.gutters.firstChild&&e.options.fixedGutter){for(var r=rr(t)-t.scroller.scrollLeft+e.doc.scrollLeft,i=t.gutters.offsetWidth,o=r+"px",l=0;lo&&(t.bottom=t.top+o);var a=e.doc.height+kn(n),s=t.topa-r;if(t.topi+o){var c=Math.min(t.top,(u?a:t.bottom)-o);c!=i&&(l.scrollTop=c)}var f=e.curOp&&null!=e.curOp.scrollLeft?e.curOp.scrollLeft:n.scroller.scrollLeft,h=Tn(e)-(e.options.fixedGutter?n.gutters.offsetWidth:0),d=t.right-t.left>h;return d&&(t.right=t.left+h),t.left<10?l.scrollLeft=0:t.lefth+f-3&&(l.scrollLeft=t.right+(d?0:10)-h),l}function Sr(e,t){null!=t&&(Mr(e),e.curOp.scrollTop=(null==e.curOp.scrollTop?e.doc.scrollTop:e.curOp.scrollTop)+t)}function Lr(e){Mr(e);var t=e.getCursor();e.curOp.scrollToPos={from:t,to:t,margin:e.options.cursorScrollMargin}}function Tr(e,t,n){null==t&&null==n||Mr(e),null!=t&&(e.curOp.scrollLeft=t),null!=n&&(e.curOp.scrollTop=n)}function Mr(e){var t=e.curOp.scrollToPos;if(t){e.curOp.scrollToPos=null;var n=$n(e,t.from),r=$n(e,t.to);Ar(e,n,r,t.margin)}}function Ar(e,t,n,r){var i=kr(e,{left:Math.min(t.left,n.left),top:Math.min(t.top,n.top)-r,right:Math.max(t.right,n.right),bottom:Math.max(t.bottom,n.bottom)+r});Tr(e,i.scrollLeft,i.scrollTop)}function Or(e,t){Math.abs(e.doc.scrollTop-t)<2||(n||li(e,{top:t}),Nr(e,t,!0),n&&li(e),ti(e,100))}function Nr(e,t,n){t=Math.min(e.display.scroller.scrollHeight-e.display.scroller.clientHeight,t),(e.display.scroller.scrollTop!=t||n)&&(e.doc.scrollTop=t,e.display.scrollbars.setScrollTop(t),e.display.scroller.scrollTop!=t&&(e.display.scroller.scrollTop=t))}function Wr(e,t,n,r){t=Math.min(t,e.display.scroller.scrollWidth-e.display.scroller.clientWidth),(n?t==e.doc.scrollLeft:Math.abs(e.doc.scrollLeft-t)<2)&&!r||(e.doc.scrollLeft=t,wr(e),e.display.scroller.scrollLeft!=t&&(e.display.scroller.scrollLeft=t),e.display.scrollbars.setScrollLeft(t))}function Dr(e){var t=e.display,n=t.gutters.offsetWidth,r=Math.round(e.doc.height+kn(e.display));return{clientHeight:t.scroller.clientHeight,viewHeight:t.wrapper.clientHeight,scrollWidth:t.scroller.scrollWidth,clientWidth:t.scroller.clientWidth,viewWidth:t.wrapper.clientWidth,barLeft:e.options.fixedGutter?n:0,docHeight:r,scrollHeight:r+Ln(e)+t.barHeight,nativeBarWidth:t.nativeBarWidth,gutterWidth:n}}var Hr=function(e,t,n){this.cm=n;var r=this.vert=O("div",[O("div",null,null,"min-width: 1px")],"CodeMirror-vscrollbar"),i=this.horiz=O("div",[O("div",null,null,"height: 100%; min-height: 1px")],"CodeMirror-hscrollbar");e(r),e(i),Je(r,"scroll",function(){r.clientHeight&&t(r.scrollTop,"vertical")}),Je(i,"scroll",function(){i.clientWidth&&t(i.scrollLeft,"horizontal")}),this.checkedZeroWidth=!1,l&&a<8&&(this.horiz.style.minHeight=this.vert.style.minWidth="18px")};Hr.prototype.update=function(e){var t=e.scrollWidth>e.clientWidth+1,n=e.scrollHeight>e.clientHeight+1,r=e.nativeBarWidth;if(n){this.vert.style.display="block",this.vert.style.bottom=t?r+"px":"0";var i=e.viewHeight-(t?r:0);this.vert.firstChild.style.height=Math.max(0,e.scrollHeight-e.clientHeight+i)+"px"}else this.vert.style.display="",this.vert.firstChild.style.height="0";if(t){this.horiz.style.display="block",this.horiz.style.right=n?r+"px":"0",this.horiz.style.left=e.barLeft+"px";var o=e.viewWidth-e.barLeft-(n?r:0);this.horiz.firstChild.style.width=Math.max(0,e.scrollWidth-e.clientWidth+o)+"px"}else this.horiz.style.display="",this.horiz.firstChild.style.width="0";return!this.checkedZeroWidth&&e.clientHeight>0&&(0==r&&this.zeroWidthHack(),this.checkedZeroWidth=!0),{right:n?r:0,bottom:t?r:0}},Hr.prototype.setScrollLeft=function(e){this.horiz.scrollLeft!=e&&(this.horiz.scrollLeft=e),this.disableHoriz&&this.enableZeroWidthBar(this.horiz,this.disableHoriz,"horiz")},Hr.prototype.setScrollTop=function(e){this.vert.scrollTop!=e&&(this.vert.scrollTop=e),this.disableVert&&this.enableZeroWidthBar(this.vert,this.disableVert,"vert")},Hr.prototype.zeroWidthHack=function(){var e=y&&!d?"12px":"18px";this.horiz.style.height=this.vert.style.width=e,this.horiz.style.pointerEvents=this.vert.style.pointerEvents="none",this.disableHoriz=new R,this.disableVert=new R},Hr.prototype.enableZeroWidthBar=function(e,t,n){e.style.pointerEvents="auto",t.set(1e3,function r(){var i=e.getBoundingClientRect(),o="vert"==n?document.elementFromPoint(i.right-1,(i.top+i.bottom)/2):document.elementFromPoint((i.right+i.left)/2,i.bottom-1);o!=e?e.style.pointerEvents="none":t.set(1e3,r)})},Hr.prototype.clear=function(){var e=this.horiz.parentNode;e.removeChild(this.horiz),e.removeChild(this.vert)};var Er=function(){};function Pr(e,t){t||(t=Dr(e));var n=e.display.barWidth,r=e.display.barHeight;Fr(e,t);for(var i=0;i<4&&n!=e.display.barWidth||r!=e.display.barHeight;i++)n!=e.display.barWidth&&e.options.lineWrapping&&yr(e),Fr(e,Dr(e)),n=e.display.barWidth,r=e.display.barHeight}function Fr(e,t){var n=e.display,r=n.scrollbars.update(t);n.sizer.style.paddingRight=(n.barWidth=r.right)+"px",n.sizer.style.paddingBottom=(n.barHeight=r.bottom)+"px",n.heightForcer.style.borderBottom=r.bottom+"px solid transparent",r.right&&r.bottom?(n.scrollbarFiller.style.display="block",n.scrollbarFiller.style.height=r.bottom+"px",n.scrollbarFiller.style.width=r.right+"px"):n.scrollbarFiller.style.display="",r.bottom&&e.options.coverGutterNextToScrollbar&&e.options.fixedGutter?(n.gutterFiller.style.display="block",n.gutterFiller.style.height=r.bottom+"px",n.gutterFiller.style.width=t.gutterWidth+"px"):n.gutterFiller.style.display=""}Er.prototype.update=function(){return{bottom:0,right:0}},Er.prototype.setScrollLeft=function(){},Er.prototype.setScrollTop=function(){},Er.prototype.clear=function(){};var Ir={native:Hr,null:Er};function zr(e){e.display.scrollbars&&(e.display.scrollbars.clear(),e.display.scrollbars.addClass&&T(e.display.wrapper,e.display.scrollbars.addClass)),e.display.scrollbars=new Ir[e.options.scrollbarStyle](function(t){e.display.wrapper.insertBefore(t,e.display.scrollbarFiller),Je(t,"mousedown",function(){e.state.focused&&setTimeout(function(){return e.display.input.focus()},0)}),t.setAttribute("cm-not-content","true")},function(t,n){"horizontal"==n?Wr(e,t):Or(e,t)},e),e.display.scrollbars.addClass&&H(e.display.wrapper,e.display.scrollbars.addClass)}var Rr=0;function Br(e){var t;e.curOp={cm:e,viewChanged:!1,startHeight:e.doc.height,forceUpdate:!1,updateInput:null,typing:!1,changeObjs:null,cursorActivityHandlers:null,cursorActivityCalled:0,selectionChanged:!1,updateMaxLine:!1,scrollLeft:null,scrollTop:null,scrollToPos:null,focus:!1,id:++Rr},t=e.curOp,on?on.ops.push(t):t.ownsGroup=on={ops:[t],delayedCallbacks:[]}}function jr(e){var t=e.curOp;!function(e,t){var n=e.ownsGroup;if(n)try{!function(e){var t=e.delayedCallbacks,n=0;do{for(;n=n.viewTo)||n.maxLineChanged&&t.options.lineWrapping,e.update=e.mustUpdate&&new ri(t,e.mustUpdate&&{top:e.scrollTop,ensure:e.scrollToPos},e.forceUpdate)}function Gr(e){var t=e.cm,n=t.display;e.updatedDisplay&&yr(t),e.barMeasure=Dr(t),n.maxLineChanged&&!t.options.lineWrapping&&(e.adjustWidthTo=On(t,n.maxLine,n.maxLine.text.length).left+3,t.display.sizerWidth=e.adjustWidthTo,e.barMeasure.scrollWidth=Math.max(n.scroller.clientWidth,n.sizer.offsetLeft+e.adjustWidthTo+Ln(t)+t.display.barWidth),e.maxScrollLeft=Math.max(0,n.sizer.offsetLeft+e.adjustWidthTo-Tn(t))),(e.updatedDisplay||e.selectionChanged)&&(e.preparedSelection=n.input.prepareSelection())}function Ur(e){var t=e.cm;null!=e.adjustWidthTo&&(t.display.sizer.style.minWidth=e.adjustWidthTo+"px",e.maxScrollLeft1&&(l=!0)),null!=u.scrollLeft&&(Wr(e,u.scrollLeft),Math.abs(e.doc.scrollLeft-f)>1&&(l=!0)),!l)break}return i}(t,Ce(r,e.scrollToPos.from),Ce(r,e.scrollToPos.to),e.scrollToPos.margin);!function(e,t){if(!rt(e,"scrollCursorIntoView")){var n=e.display,r=n.sizer.getBoundingClientRect(),i=null;if(t.top+r.top<0?i=!0:t.bottom+r.top>(window.innerHeight||document.documentElement.clientHeight)&&(i=!1),null!=i&&!p){var o=O("div","​",null,"position: absolute;\n top: "+(t.top-n.viewOffset-Cn(e.display))+"px;\n height: "+(t.bottom-t.top+Ln(e)+n.barHeight)+"px;\n left: "+t.left+"px; width: "+Math.max(2,t.right-t.left)+"px;");e.display.lineSpace.appendChild(o),o.scrollIntoView(i),e.display.lineSpace.removeChild(o)}}}(t,i)}var o=e.maybeHiddenMarkers,l=e.maybeUnhiddenMarkers;if(o)for(var a=0;at)&&(i.updateLineNumbers=t),e.curOp.viewChanged=!0,t>=i.viewTo)Le&&je(e.doc,t)i.viewFrom?Qr(e):(i.viewFrom+=r,i.viewTo+=r);else if(t<=i.viewFrom&&n>=i.viewTo)Qr(e);else if(t<=i.viewFrom){var o=Jr(e,n,n+r,1);o?(i.view=i.view.slice(o.index),i.viewFrom=o.lineN,i.viewTo+=r):Qr(e)}else if(n>=i.viewTo){var l=Jr(e,t,t,-1);l?(i.view=i.view.slice(0,l.index),i.viewTo=l.lineN):Qr(e)}else{var a=Jr(e,t,t,-1),s=Jr(e,n,n+r,1);a&&s?(i.view=i.view.slice(0,a.index).concat(rn(e,a.lineN,s.lineN)).concat(i.view.slice(s.index)),i.viewTo+=r):Qr(e)}var u=i.externalMeasured;u&&(n=i.lineN&&t=r.viewTo)){var o=r.view[ar(e,t)];if(null!=o.node){var l=o.changes||(o.changes=[]);-1==B(l,n)&&l.push(n)}}}function Qr(e){e.display.viewFrom=e.display.viewTo=e.doc.first,e.display.view=[],e.display.viewOffset=0}function Jr(e,t,n,r){var i,o=ar(e,t),l=e.display.view;if(!Le||n==e.doc.first+e.doc.size)return{index:o,lineN:n};for(var a=e.display.viewFrom,s=0;s0){if(o==l.length-1)return null;i=a+l[o].size-t,o++}else i=a-t;t+=i,n+=i}for(;je(e.doc,n)!=n;){if(o==(r<0?0:l.length-1))return null;n+=r*l[o-(r<0?1:0)].size,o+=r}return{index:o,lineN:n}}function ei(e){for(var t=e.display.view,n=0,r=0;r=e.display.viewTo)){var n=+new Date+e.options.workTime,r=It(e,t.highlightFrontier),i=[];t.iter(r.line,Math.min(t.first+t.size,e.display.viewTo+500),function(o){if(r.line>=e.display.viewFrom){var l=o.styles,a=o.text.length>e.options.maxHighlightLength?Ot(t.mode,r.state):null,s=Pt(e,o,r,!0);a&&(r.state=a),o.styles=s.styles;var u=o.styleClasses,c=s.classes;c?o.styleClasses=c:u&&(o.styleClasses=null);for(var f=!l||l.length!=o.styles.length||u!=c&&(!u||!c||u.bgClass!=c.bgClass||u.textClass!=c.textClass),h=0;!f&&hn)return ti(e,e.options.workDelay),!0}),t.highlightFrontier=r.line,t.modeFrontier=Math.max(t.modeFrontier,r.line),i.length&&Xr(e,function(){for(var t=0;t=n.viewFrom&&t.visible.to<=n.viewTo&&(null==n.updateLineNumbers||n.updateLineNumbers>=n.viewTo)&&n.renderedView==n.view&&0==ei(e))return!1;Cr(e)&&(Qr(e),t.dims=nr(e));var i=r.first+r.size,o=Math.max(t.visible.from-e.options.viewportMargin,r.first),l=Math.min(i,t.visible.to+e.options.viewportMargin);n.viewFroml&&n.viewTo-l<20&&(l=Math.min(i,n.viewTo)),Le&&(o=je(e.doc,o),l=Ve(e.doc,l));var a=o!=n.viewFrom||l!=n.viewTo||n.lastWrapHeight!=t.wrapperHeight||n.lastWrapWidth!=t.wrapperWidth;!function(e,t,n){var r=e.display;0==r.view.length||t>=r.viewTo||n<=r.viewFrom?(r.view=rn(e,t,n),r.viewFrom=t):(r.viewFrom>t?r.view=rn(e,t,r.viewFrom).concat(r.view):r.viewFromn&&(r.view=r.view.slice(0,ar(e,n)))),r.viewTo=n}(e,o,l),n.viewOffset=Ke(ae(e.doc,n.viewFrom)),e.display.mover.style.top=n.viewOffset+"px";var u=ei(e);if(!a&&0==u&&!t.force&&n.renderedView==n.view&&(null==n.updateLineNumbers||n.updateLineNumbers>=n.viewTo))return!1;var c=function(e){if(e.hasFocus())return null;var t=D();if(!t||!W(e.display.lineDiv,t))return null;var n={activeElt:t};if(window.getSelection){var r=window.getSelection();r.anchorNode&&r.extend&&W(e.display.lineDiv,r.anchorNode)&&(n.anchorNode=r.anchorNode,n.anchorOffset=r.anchorOffset,n.focusNode=r.focusNode,n.focusOffset=r.focusOffset)}return n}(e);return u>4&&(n.lineDiv.style.display="none"),function(e,t,n){var r=e.display,i=e.options.lineNumbers,o=r.lineDiv,l=o.firstChild;function a(t){var n=t.nextSibling;return s&&y&&e.display.currentWheelTarget==t?t.style.display="none":t.parentNode.removeChild(t),n}for(var u=r.view,c=r.viewFrom,f=0;f-1&&(d=!1),un(e,h,c,n)),d&&(M(h.lineNumber),h.lineNumber.appendChild(document.createTextNode(pe(e.options,c)))),l=h.node.nextSibling}else{var p=mn(e,h,c,n);o.insertBefore(p,l)}c+=h.size}for(;l;)l=a(l)}(e,n.updateLineNumbers,t.dims),u>4&&(n.lineDiv.style.display=""),n.renderedView=n.view,function(e){if(e&&e.activeElt&&e.activeElt!=D()&&(e.activeElt.focus(),e.anchorNode&&W(document.body,e.anchorNode)&&W(document.body,e.focusNode))){var t=window.getSelection(),n=document.createRange();n.setEnd(e.anchorNode,e.anchorOffset),n.collapse(!1),t.removeAllRanges(),t.addRange(n),t.extend(e.focusNode,e.focusOffset)}}(c),M(n.cursorDiv),M(n.selectionDiv),n.gutters.style.height=n.sizer.style.minHeight=0,a&&(n.lastWrapHeight=t.wrapperHeight,n.lastWrapWidth=t.wrapperWidth,ti(e,400)),n.updateLineNumbers=null,!0}function oi(e,t){for(var n=t.viewport,r=!0;(r&&e.options.lineWrapping&&t.oldDisplayWidth!=Tn(e)||(n&&null!=n.top&&(n={top:Math.min(e.doc.height+kn(e.display)-Mn(e),n.top)}),t.visible=xr(e.display,e.doc,n),!(t.visible.from>=e.display.viewFrom&&t.visible.to<=e.display.viewTo)))&&ii(e,t);r=!1){yr(e);var i=Dr(e);sr(e),Pr(e,i),si(e,i),t.force=!1}t.signal(e,"update",e),e.display.viewFrom==e.display.reportedViewFrom&&e.display.viewTo==e.display.reportedViewTo||(t.signal(e,"viewportChange",e,e.display.viewFrom,e.display.viewTo),e.display.reportedViewFrom=e.display.viewFrom,e.display.reportedViewTo=e.display.viewTo)}function li(e,t){var n=new ri(e,t);if(ii(e,n)){yr(e),oi(e,n);var r=Dr(e);sr(e),Pr(e,r),si(e,r),n.finish()}}function ai(e){var t=e.display.gutters.offsetWidth;e.display.sizer.style.marginLeft=t+"px"}function si(e,t){e.display.sizer.style.minHeight=t.docHeight+"px",e.display.heightForcer.style.top=t.docHeight+"px",e.display.gutters.style.height=t.docHeight+e.display.barHeight+Ln(e)+"px"}function ui(e){var t=e.display.gutters,n=e.options.gutters;M(t);for(var r=0;r-1&&!e.lineNumbers&&(e.gutters=e.gutters.slice(0),e.gutters.splice(t,1))}ri.prototype.signal=function(e,t){ot(e,t)&&this.events.push(arguments)},ri.prototype.finish=function(){for(var e=0;ea.clientWidth,c=a.scrollHeight>a.clientHeight;if(i&&u||o&&c){if(o&&y&&s)e:for(var h=t.target,d=l.view;h!=a;h=h.parentNode)for(var p=0;p=0&&me(e,r.to())<=0)return n}return-1};var vi=function(e,t){this.anchor=e,this.head=t};function yi(e,t){var n=e[t];e.sort(function(e,t){return me(e.from(),t.from())}),t=B(e,n);for(var r=1;r=0){var l=xe(o.from(),i.from()),a=be(o.to(),i.to()),s=o.empty()?i.from()==i.head:o.from()==o.head;r<=t&&--t,e.splice(--r,2,new vi(s?a:l,s?l:a))}}return new mi(e,t)}function bi(e,t){return new mi([new vi(e,t||e)],0)}function xi(e){return e.text?ge(e.from.line+e.text.length-1,_(e.text).length+(1==e.text.length?e.from.ch:0)):e.to}function wi(e,t){if(me(e,t.from)<0)return e;if(me(e,t.to)<=0)return xi(t);var n=e.line+t.text.length-(t.to.line-t.from.line)-1,r=e.ch;return e.line==t.to.line&&(r+=xi(t).ch-t.to.ch),ge(n,r)}function Ci(e,t){for(var n=[],r=0;r1&&e.remove(a.line+1,p-1),e.insert(a.line+1,v)}an(e,"change",e,t)}function Ai(e,t,n){!function e(r,i,o){if(r.linked)for(var l=0;la-e.cm.options.historyEventDelay||"*"==t.origin.charAt(0)))&&(o=function(e,t){return t?(Hi(e.done),_(e.done)):e.done.length&&!_(e.done).ranges?_(e.done):e.done.length>1&&!e.done[e.done.length-2].ranges?(e.done.pop(),_(e.done)):void 0}(i,i.lastOp==r)))l=_(o.changes),0==me(t.from,t.to)&&0==me(t.from,l.to)?l.to=xi(t):o.changes.push(Di(e,t));else{var s=_(i.done);for(s&&s.ranges||Fi(e.sel,i.done),o={changes:[Di(e,t)],generation:i.generation},i.done.push(o);i.done.length>i.undoDepth;)i.done.shift(),i.done[0].ranges||i.done.shift()}i.done.push(n),i.generation=++i.maxGeneration,i.lastModTime=i.lastSelTime=a,i.lastOp=i.lastSelOp=r,i.lastOrigin=i.lastSelOrigin=t.origin,l||nt(e,"historyAdded")}function Pi(e,t,n,r){var i=e.history,o=r&&r.origin;n==i.lastSelOp||o&&i.lastSelOrigin==o&&(i.lastModTime==i.lastSelTime&&i.lastOrigin==o||function(e,t,n,r){var i=t.charAt(0);return"*"==i||"+"==i&&n.ranges.length==r.ranges.length&&n.somethingSelected()==r.somethingSelected()&&new Date-e.history.lastSelTime<=(e.cm?e.cm.options.historyEventDelay:500)}(e,o,_(i.done),t))?i.done[i.done.length-1]=t:Fi(t,i.done),i.lastSelTime=+new Date,i.lastSelOrigin=o,i.lastSelOp=n,r&&!1!==r.clearRedo&&Hi(i.undone)}function Fi(e,t){var n=_(t);n&&n.ranges&&n.equals(e)||t.push(e)}function Ii(e,t,n,r){var i=t["spans_"+e.id],o=0;e.iter(Math.max(e.first,n),Math.min(e.first+e.size,r),function(n){n.markedSpans&&((i||(i=t["spans_"+e.id]={}))[o]=n.markedSpans),++o})}function zi(e){if(!e)return null;for(var t,n=0;n-1&&(_(a)[f]=u[f],delete u[f])}}}return r}function ji(e,t,n,r){if(r){var i=e.anchor;if(n){var o=me(t,i)<0;o!=me(n,i)<0?(i=t,t=n):o!=me(t,n)<0&&(t=n)}return new vi(i,t)}return new vi(n||t,t)}function Vi(e,t,n,r,i){null==i&&(i=e.cm&&(e.cm.display.shift||e.extend)),$i(e,new mi([ji(e.sel.primary(),t,n,i)],0),r)}function Gi(e,t,n){for(var r=[],i=e.cm&&(e.cm.display.shift||e.extend),o=0;o=t.ch:a.to>t.ch))){if(i&&(nt(s,"beforeCursorEnter"),s.explicitlyCleared)){if(o.markedSpans){--l;continue}break}if(!s.atomic)continue;if(n){var u=s.find(r<0?1:-1),c=void 0;if((r<0?s.inclusiveRight:s.inclusiveLeft)&&(u=eo(e,u,-r,u&&u.line==t.line?o:null)),u&&u.line==t.line&&(c=me(u,n))&&(r<0?c<0:c>0))return Qi(e,u,t,r,i)}var f=s.find(r<0?-1:1);return(r<0?s.inclusiveLeft:s.inclusiveRight)&&(f=eo(e,f,r,f.line==t.line?o:null)),f?Qi(e,f,t,r,i):null}}return t}function Ji(e,t,n,r,i){var o=r||1,l=Qi(e,t,n,o,i)||!i&&Qi(e,t,n,o,!0)||Qi(e,t,n,-o,i)||!i&&Qi(e,t,n,-o,!0);return l||(e.cantEdit=!0,ge(e.first,0))}function eo(e,t,n,r){return n<0&&0==t.ch?t.line>e.first?Ce(e,ge(t.line-1)):null:n>0&&t.ch==(r||ae(e,t.line)).text.length?t.line0)){var c=[s,1],f=me(u.from,a.from),h=me(u.to,a.to);(f<0||!l.inclusiveLeft&&!f)&&c.push({from:u.from,to:a.from}),(h>0||!l.inclusiveRight&&!h)&&c.push({from:a.to,to:u.to}),i.splice.apply(i,c),s+=c.length-3}}return i}(e,t.from,t.to);if(r)for(var i=r.length-1;i>=0;--i)io(e,{from:r[i].from,to:r[i].to,text:i?[""]:t.text,origin:t.origin});else io(e,t)}}function io(e,t){if(1!=t.text.length||""!=t.text[0]||0!=me(t.from,t.to)){var n=Ci(e,t);Ei(e,t,n,e.cm?e.cm.curOp.id:NaN),ao(e,t,n,Oe(e,t));var r=[];Ai(e,function(e,n){n||-1!=B(r,e.history)||(fo(e.history,t),r.push(e.history)),ao(e,t,null,Oe(e,t))})}}function oo(e,t,n){var r=e.cm&&e.cm.state.suppressEdits;if(!r||n){for(var i,o=e.history,l=e.sel,a="undo"==t?o.done:o.undone,s="undo"==t?o.undone:o.done,u=0;u=0;--d){var p=h(d);if(p)return p.v}}}}function lo(e,t){if(0!=t&&(e.first+=t,e.sel=new mi(q(e.sel.ranges,function(e){return new vi(ge(e.anchor.line+t,e.anchor.ch),ge(e.head.line+t,e.head.ch))}),e.sel.primIndex),e.cm)){qr(e.cm,e.first,e.first-t,t);for(var n=e.cm.display,r=n.viewFrom;re.lastLine())){if(t.from.lineo&&(t={from:t.from,to:ge(o,ae(e,o).text.length),text:[t.text[0]],origin:t.origin}),t.removed=se(e,t.from,t.to),n||(n=Ci(e,t)),e.cm?function(e,t,n){var r=e.doc,i=e.display,o=t.from,l=t.to,a=!1,s=o.line;e.options.lineWrapping||(s=fe(Be(ae(r,o.line))),r.iter(s,l.line+1,function(e){if(e==i.maxLine)return a=!0,!0})),r.sel.contains(t.from,t.to)>-1&&it(e),Mi(r,t,n,ir(e)),e.options.lineWrapping||(r.iter(s,o.line+t.text.length,function(e){var t=Xe(e);t>i.maxLineLength&&(i.maxLine=e,i.maxLineLength=t,i.maxLineChanged=!0,a=!1)}),a&&(e.curOp.updateMaxLine=!0)),function(e,t){if(e.modeFrontier=Math.min(e.modeFrontier,t),!(e.highlightFrontiern;r--){var i=ae(e,r).stateAfter;if(i&&(!(i instanceof Ht)||r+i.lookAhead1||!(this.children[0]instanceof po))){var a=[];this.collapse(a),this.children=[new po(a)],this.children[0].parent=this}},collapse:function(e){for(var t=0;t50){for(var l=i.lines.length%25+25,a=l;a10);e.parent.maybeSpill()}},iterN:function(e,t,n){for(var r=0;r0||0==l&&!1!==o.clearWhenEmpty)return o;if(o.replacedWith&&(o.collapsed=!0,o.widgetNode=N("span",[o.replacedWith],"CodeMirror-widget"),r.handleMouseEvents||o.widgetNode.setAttribute("cm-ignore-events","true"),r.insertLeft&&(o.widgetNode.insertLeft=!0)),o.collapsed){if(Re(e,t.line,t,n,o)||t.line!=n.line&&Re(e,n.line,t,n,o))throw new Error("Inserting collapsed marker partially overlapping an existing one");Le=!0}o.addToHistory&&Ei(e,{from:t,to:n,origin:"markText"},e.sel,NaN);var a,s=t.line,u=e.cm;if(e.iter(s,n.line+1,function(e){u&&o.collapsed&&!u.options.lineWrapping&&Be(e)==u.display.maxLine&&(a=!0),o.collapsed&&s!=t.line&&ce(e,0),function(e,t){e.markedSpans=e.markedSpans?e.markedSpans.concat([t]):[t],t.marker.attachLine(e)}(e,new Te(o,s==t.line?t.ch:null,s==n.line?n.ch:null)),++s}),o.collapsed&&e.iter(t.line,n.line+1,function(t){Ge(e,t)&&ce(t,0)}),o.clearOnEnter&&Je(o,"beforeCursorEnter",function(){return o.clear()}),o.readOnly&&(Se=!0,(e.history.done.length||e.history.undone.length)&&e.clearHistory()),o.collapsed&&(o.id=++yo,o.atomic=!0),u){if(a&&(u.curOp.updateMaxLine=!0),o.collapsed)qr(u,t.line,n.line+1);else if(o.className||o.title||o.startStyle||o.endStyle||o.css)for(var c=t.line;c<=n.line;c++)Zr(u,c,"text");o.atomic&&qi(u.doc),an(u,"markerAdded",u,o)}return o}bo.prototype.clear=function(){if(!this.explicitlyCleared){var e=this.doc.cm,t=e&&!e.curOp;if(t&&Br(e),ot(this,"clear")){var n=this.find();n&&an(this,"clear",n.from,n.to)}for(var r=null,i=null,o=0;oe.display.maxLineLength&&(e.display.maxLine=u,e.display.maxLineLength=c,e.display.maxLineChanged=!0)}null!=r&&e&&this.collapsed&&qr(e,r,i+1),this.lines.length=0,this.explicitlyCleared=!0,this.atomic&&this.doc.cantEdit&&(this.doc.cantEdit=!1,e&&qi(e.doc)),e&&an(e,"markerCleared",e,this,r,i),t&&jr(e),this.parent&&this.parent.clear()}},bo.prototype.find=function(e,t){var n,r;null==e&&"bookmark"==this.type&&(e=1);for(var i=0;i=0;s--)ro(this,r[s]);a?Xi(this,a):this.cm&&Lr(this.cm)}),undo:_r(function(){oo(this,"undo")}),redo:_r(function(){oo(this,"redo")}),undoSelection:_r(function(){oo(this,"undo",!0)}),redoSelection:_r(function(){oo(this,"redo",!0)}),setExtending:function(e){this.extend=e},getExtending:function(){return this.extend},historySize:function(){for(var e=this.history,t=0,n=0,r=0;r=e.ch)&&t.push(i.marker.parent||i.marker)}return t},findMarks:function(e,t,n){e=Ce(this,e),t=Ce(this,t);var r=[],i=e.line;return this.iter(e.line,t.line+1,function(o){var l=o.markedSpans;if(l)for(var a=0;a=s.to||null==s.from&&i!=e.line||null!=s.from&&i==t.line&&s.from>=t.ch||n&&!n(s.marker)||r.push(s.marker.parent||s.marker)}++i}),r},getAllMarks:function(){var e=[];return this.iter(function(t){var n=t.markedSpans;if(n)for(var r=0;re)return t=e,!0;e-=o,++n}),Ce(this,ge(n,t))},indexFromPos:function(e){var t=(e=Ce(this,e)).ch;if(e.linet&&(t=e.from),null!=e.to&&e.to-1)return t.state.draggingText(e),void setTimeout(function(){return t.display.input.focus()},20);try{var c=e.dataTransfer.getData("Text");if(c){var f;if(t.state.draggingText&&!t.state.draggingText.copy&&(f=t.listSelections()),Yi(t.doc,bi(n,n)),f)for(var h=0;h=0;t--)so(e.doc,"",r[t].from,r[t].to,"+delete");Lr(e)})}function Xo(e,t,n){var r=oe(e.text,t+n,n);return r<0||r>e.text.length?null:r}function $o(e,t,n){var r=Xo(e,t.ch,n);return null==r?null:new ge(t.line,r,n<0?"after":"before")}function Yo(e,t,n,r,i){if(e){var o=Ze(n,t.doc.direction);if(o){var l,a=i<0?_(o):o[0],s=i<0==(1==a.level),u=s?"after":"before";if(a.level>0||"rtl"==t.doc.direction){var c=Wn(t,n);l=i<0?n.text.length-1:0;var f=Dn(t,c,l).top;l=le(function(e){return Dn(t,c,e).top==f},i<0==(1==a.level)?a.from:a.to-1,l),"before"==u&&(l=Xo(n,l,1))}else l=i<0?a.to:a.from;return new ge(r,l,u)}}return new ge(r,i<0?n.text.length:0,i<0?"before":"after")}Io.basic={Left:"goCharLeft",Right:"goCharRight",Up:"goLineUp",Down:"goLineDown",End:"goLineEnd",Home:"goLineStartSmart",PageUp:"goPageUp",PageDown:"goPageDown",Delete:"delCharAfter",Backspace:"delCharBefore","Shift-Backspace":"delCharBefore",Tab:"defaultTab","Shift-Tab":"indentAuto",Enter:"newlineAndIndent",Insert:"toggleOverwrite",Esc:"singleSelection"},Io.pcDefault={"Ctrl-A":"selectAll","Ctrl-D":"deleteLine","Ctrl-Z":"undo","Shift-Ctrl-Z":"redo","Ctrl-Y":"redo","Ctrl-Home":"goDocStart","Ctrl-End":"goDocEnd","Ctrl-Up":"goLineUp","Ctrl-Down":"goLineDown","Ctrl-Left":"goGroupLeft","Ctrl-Right":"goGroupRight","Alt-Left":"goLineStart","Alt-Right":"goLineEnd","Ctrl-Backspace":"delGroupBefore","Ctrl-Delete":"delGroupAfter","Ctrl-S":"save","Ctrl-F":"find","Ctrl-G":"findNext","Shift-Ctrl-G":"findPrev","Shift-Ctrl-F":"replace","Shift-Ctrl-R":"replaceAll","Ctrl-[":"indentLess","Ctrl-]":"indentMore","Ctrl-U":"undoSelection","Shift-Ctrl-U":"redoSelection","Alt-U":"redoSelection",fallthrough:"basic"},Io.emacsy={"Ctrl-F":"goCharRight","Ctrl-B":"goCharLeft","Ctrl-P":"goLineUp","Ctrl-N":"goLineDown","Alt-F":"goWordRight","Alt-B":"goWordLeft","Ctrl-A":"goLineStart","Ctrl-E":"goLineEnd","Ctrl-V":"goPageDown","Shift-Ctrl-V":"goPageUp","Ctrl-D":"delCharAfter","Ctrl-H":"delCharBefore","Alt-D":"delWordAfter","Alt-Backspace":"delWordBefore","Ctrl-K":"killLine","Ctrl-T":"transposeChars","Ctrl-O":"openLine"},Io.macDefault={"Cmd-A":"selectAll","Cmd-D":"deleteLine","Cmd-Z":"undo","Shift-Cmd-Z":"redo","Cmd-Y":"redo","Cmd-Home":"goDocStart","Cmd-Up":"goDocStart","Cmd-End":"goDocEnd","Cmd-Down":"goDocEnd","Alt-Left":"goGroupLeft","Alt-Right":"goGroupRight","Cmd-Left":"goLineLeft","Cmd-Right":"goLineRight","Alt-Backspace":"delGroupBefore","Ctrl-Alt-Backspace":"delGroupAfter","Alt-Delete":"delGroupAfter","Cmd-S":"save","Cmd-F":"find","Cmd-G":"findNext","Shift-Cmd-G":"findPrev","Cmd-Alt-F":"replace","Shift-Cmd-Alt-F":"replaceAll","Cmd-[":"indentLess","Cmd-]":"indentMore","Cmd-Backspace":"delWrappedLineLeft","Cmd-Delete":"delWrappedLineRight","Cmd-U":"undoSelection","Shift-Cmd-U":"redoSelection","Ctrl-Up":"goDocStart","Ctrl-Down":"goDocEnd",fallthrough:["basic","emacsy"]},Io.default=y?Io.macDefault:Io.pcDefault;var _o={selectAll:to,singleSelection:function(e){return e.setSelection(e.getCursor("anchor"),e.getCursor("head"),G)},killLine:function(e){return Ko(e,function(t){if(t.empty()){var n=ae(e.doc,t.head.line).text.length;return t.head.ch==n&&t.head.line0)i=new ge(i.line,i.ch+1),e.replaceRange(o.charAt(i.ch-1)+o.charAt(i.ch-2),ge(i.line,i.ch-2),i,"+transpose");else if(i.line>e.doc.first){var l=ae(e.doc,i.line-1).text;l&&(i=new ge(i.line,1),e.replaceRange(o.charAt(0)+e.doc.lineSeparator()+l.charAt(l.length-1),ge(i.line-1,l.length-1),i,"+transpose"))}n.push(new vi(i,i))}e.setSelections(n)})},newlineAndIndent:function(e){return Xr(e,function(){for(var t=e.listSelections(),n=t.length-1;n>=0;n--)e.replaceRange(e.doc.lineSeparator(),t[n].anchor,t[n].head,"+input");t=e.listSelections();for(var r=0;r-1&&(me((i=u.ranges[i]).from(),t)<0||t.xRel>0)&&(me(i.to(),t)>0||t.xRel<0)?function(e,t,n,r){var i=e.display,o=!1,u=$r(e,function(t){s&&(i.scroller.draggable=!1),e.state.draggingText=!1,tt(document,"mouseup",u),tt(document,"mousemove",c),tt(i.scroller,"dragstart",f),tt(i.scroller,"drop",u),o||(at(t),r.addNew||Vi(e.doc,n,null,null,r.extend),s||l&&9==a?setTimeout(function(){document.body.focus(),i.input.focus()},20):i.input.focus())}),c=function(e){o=o||Math.abs(t.clientX-e.clientX)+Math.abs(t.clientY-e.clientY)>=10},f=function(){return o=!0};s&&(i.scroller.draggable=!0),e.state.draggingText=u,u.copy=!r.moveOnDrag,i.scroller.dragDrop&&i.scroller.dragDrop(),Je(document,"mouseup",u),Je(document,"mousemove",c),Je(i.scroller,"dragstart",f),Je(i.scroller,"drop",u),gr(e),setTimeout(function(){return i.input.focus()},20)}(e,r,t,o):function(e,t,n,r){var i=e.display,o=e.doc;at(t);var l,a,s=o.sel,u=s.ranges;if(r.addNew&&!r.extend?(a=o.sel.contains(n),l=a>-1?u[a]:new vi(n,n)):(l=o.sel.primary(),a=o.sel.primIndex),"rectangle"==r.unit)r.addNew||(l=new vi(n,n)),n=lr(e,t,!0,!0),a=-1;else{var c=fl(e,n,r.unit);l=r.extend?ji(l,c.anchor,c.head,r.extend):c}r.addNew?-1==a?(a=u.length,$i(o,yi(u.concat([l]),a),{scroll:!1,origin:"*mouse"})):u.length>1&&u[a].empty()&&"char"==r.unit&&!r.extend?($i(o,yi(u.slice(0,a).concat(u.slice(a+1)),0),{scroll:!1,origin:"*mouse"}),s=o.sel):Ui(o,a,l,U):(a=0,$i(o,new mi([l],0),U),s=o.sel);var f=n;function h(t){if(0!=me(f,t))if(f=t,"rectangle"==r.unit){for(var i=[],u=e.options.tabSize,c=z(ae(o,n.line).text,n.ch,u),h=z(ae(o,t.line).text,t.ch,u),d=Math.min(c,h),p=Math.max(c,h),g=Math.min(n.line,t.line),m=Math.min(e.lastLine(),Math.max(n.line,t.line));g<=m;g++){var v=ae(o,g).text,y=X(v,d,u);d==p?i.push(new vi(ge(g,y),ge(g,y))):v.length>y&&i.push(new vi(ge(g,y),ge(g,X(v,p,u))))}i.length||i.push(new vi(n,n)),$i(o,yi(s.ranges.slice(0,a).concat(i),a),{origin:"*mouse",scroll:!1}),e.scrollIntoView(t)}else{var b,x=l,w=fl(e,t,r.unit),C=x.anchor;me(w.anchor,C)>0?(b=w.head,C=xe(x.from(),w.anchor)):(b=w.anchor,C=be(x.to(),w.head));var k=s.ranges.slice(0);k[a]=function(e,t){var n=t.anchor,r=t.head,i=ae(e.doc,n.line);if(0==me(n,r)&&n.sticky==r.sticky)return t;var o=Ze(i);if(!o)return t;var l=_e(o,n.ch,n.sticky),a=o[l];if(a.from!=n.ch&&a.to!=n.ch)return t;var s,u=l+(a.from==n.ch==(1!=a.level)?0:1);if(0==u||u==o.length)return t;if(r.line!=n.line)s=(r.line-n.line)*("ltr"==e.doc.direction?1:-1)>0;else{var c=_e(o,r.ch,r.sticky),f=c-l||(r.ch-n.ch)*(1==a.level?-1:1);s=c==u-1||c==u?f<0:f>0}var h=o[u+(s?-1:0)],d=s==(1==h.level),p=d?h.from:h.to,g=d?"after":"before";return n.ch==p&&n.sticky==g?t:new vi(new ge(n.line,p,g),r)}(e,new vi(Ce(o,C),b)),$i(o,yi(k,a),U)}}var d=i.wrapper.getBoundingClientRect(),p=0;function g(t){e.state.selectingText=!1,p=1/0,at(t),i.input.focus(),tt(document,"mousemove",m),tt(document,"mouseup",v),o.history.lastSelOrigin=null}var m=$r(e,function(t){ht(t)?function t(n){var l=++p,a=lr(e,n,!0,"rectangle"==r.unit);if(a)if(0!=me(a,f)){e.curOp.focus=D(),h(a);var s=xr(i,o);(a.line>=s.to||a.lined.bottom?20:0;u&&setTimeout($r(e,function(){p==l&&(i.scroller.scrollTop+=u,t(n))}),50)}}(t):g(t)}),v=$r(e,g);e.state.selectingText=v,Je(document,"mousemove",m),Je(document,"mouseup",v)}(e,r,t,o)}(t,r,o,e):ft(e)==n.scroller&&at(e):2==i?(r&&Vi(t.doc,r),setTimeout(function(){return n.input.focus()},20)):3==i&&(k?pl(t,e):gr(t)))}}function fl(e,t,n){if("char"==n)return new vi(t,t);if("word"==n)return e.findWordAt(t);if("line"==n)return new vi(ge(t.line,0),Ce(e.doc,ge(t.line+1,0)));var r=n(e,t);return new vi(r.from,r.to)}function hl(e,t,n,r){var i,o;if(t.touches)i=t.touches[0].clientX,o=t.touches[0].clientY;else try{i=t.clientX,o=t.clientY}catch(t){return!1}if(i>=Math.floor(e.display.gutters.getBoundingClientRect().right))return!1;r&&at(t);var l=e.display,a=l.lineDiv.getBoundingClientRect();if(o>a.bottom||!ot(e,n))return ut(t);o-=a.top-l.viewOffset;for(var s=0;s=i){var c=he(e.doc,o),f=e.options.gutters[s];return nt(e,n,e,c,f,t),ut(t)}}}function dl(e,t){return hl(e,t,"gutterClick",!0)}function pl(e,t){wn(e.display,t)||function(e,t){return!!ot(e,"gutterContextMenu")&&hl(e,t,"gutterContextMenu",!1)}(e,t)||rt(e,t,"contextmenu")||e.display.input.onContextMenu(t)}function gl(e){e.display.wrapper.className=e.display.wrapper.className.replace(/\s*cm-s-\S+/g,"")+e.options.theme.replace(/(^|\s)\s*/g," cm-s-"),Rn(e)}ul.prototype.compare=function(e,t,n){return this.time+400>e&&0==me(t,this.pos)&&n==this.button};var ml={toString:function(){return"CodeMirror.Init"}},vl={},yl={};function bl(e){ui(e),qr(e),wr(e)}function xl(e,t,n){var r=n&&n!=ml;if(!t!=!r){var i=e.display.dragFunctions,o=t?Je:tt;o(e.display.scroller,"dragstart",i.start),o(e.display.scroller,"dragenter",i.enter),o(e.display.scroller,"dragover",i.over),o(e.display.scroller,"dragleave",i.leave),o(e.display.scroller,"drop",i.drop)}}function wl(e){e.options.lineWrapping?(H(e.display.wrapper,"CodeMirror-wrap"),e.display.sizer.style.minWidth="",e.display.sizerWidth=null):(T(e.display.wrapper,"CodeMirror-wrap"),$e(e)),or(e),qr(e),Rn(e),setTimeout(function(){return Pr(e)},100)}function Cl(e,t){var r=this;if(!(this instanceof Cl))return new Cl(e,t);this.options=t=t?I(t):{},I(vl,t,!1),ci(t);var i=t.value;"string"==typeof i&&(i=new Lo(i,t.mode,null,t.lineSeparator,t.direction)),this.doc=i;var o=new Cl.inputStyles[t.inputStyle](this),u=this.display=new function(e,t,r){var i=this;this.input=r,i.scrollbarFiller=O("div",null,"CodeMirror-scrollbar-filler"),i.scrollbarFiller.setAttribute("cm-not-content","true"),i.gutterFiller=O("div",null,"CodeMirror-gutter-filler"),i.gutterFiller.setAttribute("cm-not-content","true"),i.lineDiv=N("div",null,"CodeMirror-code"),i.selectionDiv=O("div",null,null,"position: relative; z-index: 1"),i.cursorDiv=O("div",null,"CodeMirror-cursors"),i.measure=O("div",null,"CodeMirror-measure"),i.lineMeasure=O("div",null,"CodeMirror-measure"),i.lineSpace=N("div",[i.measure,i.lineMeasure,i.selectionDiv,i.cursorDiv,i.lineDiv],null,"position: relative; outline: none");var o=N("div",[i.lineSpace],"CodeMirror-lines");i.mover=O("div",[o],null,"position: relative"),i.sizer=O("div",[i.mover],"CodeMirror-sizer"),i.sizerWidth=null,i.heightForcer=O("div",null,null,"position: absolute; height: "+j+"px; width: 1px;"),i.gutters=O("div",null,"CodeMirror-gutters"),i.lineGutter=null,i.scroller=O("div",[i.sizer,i.heightForcer,i.gutters],"CodeMirror-scroll"),i.scroller.setAttribute("tabIndex","-1"),i.wrapper=O("div",[i.scrollbarFiller,i.gutterFiller,i.scroller],"CodeMirror"),l&&a<8&&(i.gutters.style.zIndex=-1,i.scroller.style.paddingRight=0),s||n&&v||(i.scroller.draggable=!0),e&&(e.appendChild?e.appendChild(i.wrapper):e(i.wrapper)),i.viewFrom=i.viewTo=t.first,i.reportedViewFrom=i.reportedViewTo=t.first,i.view=[],i.renderedView=null,i.externalMeasured=null,i.viewOffset=0,i.lastWrapHeight=i.lastWrapWidth=0,i.updateLineNumbers=null,i.nativeBarWidth=i.barHeight=i.barWidth=0,i.scrollbarsClipped=!1,i.lineNumWidth=i.lineNumInnerWidth=i.lineNumChars=null,i.alignWidgets=!1,i.cachedCharWidth=i.cachedTextHeight=i.cachedPaddingH=null,i.maxLine=null,i.maxLineLength=0,i.maxLineChanged=!1,i.wheelDX=i.wheelDY=i.wheelStartX=i.wheelStartY=null,i.shift=!1,i.selForContextMenu=null,i.activeTouch=null,r.init(i)}(e,i,o);for(var c in u.wrapper.CodeMirror=this,ui(this),gl(this),t.lineWrapping&&(this.display.wrapper.className+=" CodeMirror-wrap"),zr(this),this.state={keyMaps:[],overlays:[],modeGen:0,overwrite:!1,delayingBlurEvent:!1,focused:!1,suppressEdits:!1,pasteIncoming:!1,cutIncoming:!1,selectingText:!1,draggingText:!1,highlight:new R,keySeq:null,specialChars:null},t.autofocus&&!v&&u.input.focus(),l&&a<11&&setTimeout(function(){return r.display.input.reset(!0)},20),function(e){var t=e.display;Je(t.scroller,"mousedown",$r(e,cl)),Je(t.scroller,"dblclick",l&&a<11?$r(e,function(t){if(!rt(e,t)){var n=lr(e,t);if(n&&!dl(e,t)&&!wn(e.display,t)){at(t);var r=e.findWordAt(n);Vi(e.doc,r.anchor,r.head)}}}):function(t){return rt(e,t)||at(t)}),k||Je(t.scroller,"contextmenu",function(t){return pl(e,t)});var n,r={end:0};function i(){t.activeTouch&&(n=setTimeout(function(){return t.activeTouch=null},1e3),(r=t.activeTouch).end=+new Date)}function o(e,t){if(null==t.left)return!0;var n=t.left-e.left,r=t.top-e.top;return n*n+r*r>400}Je(t.scroller,"touchstart",function(i){if(!rt(e,i)&&!function(e){if(1!=e.touches.length)return!1;var t=e.touches[0];return t.radiusX<=1&&t.radiusY<=1}(i)&&!dl(e,i)){t.input.ensurePolled(),clearTimeout(n);var o=+new Date;t.activeTouch={start:o,moved:!1,prev:o-r.end<=300?r:null},1==i.touches.length&&(t.activeTouch.left=i.touches[0].pageX,t.activeTouch.top=i.touches[0].pageY)}}),Je(t.scroller,"touchmove",function(){t.activeTouch&&(t.activeTouch.moved=!0)}),Je(t.scroller,"touchend",function(n){var r=t.activeTouch;if(r&&!wn(t,n)&&null!=r.left&&!r.moved&&new Date-r.start<300){var l,a=e.coordsChar(t.activeTouch,"page");l=!r.prev||o(r,r.prev)?new vi(a,a):!r.prev.prev||o(r,r.prev.prev)?e.findWordAt(a):new vi(ge(a.line,0),Ce(e.doc,ge(a.line+1,0))),e.setSelection(l.anchor,l.head),e.focus(),at(n)}i()}),Je(t.scroller,"touchcancel",i),Je(t.scroller,"scroll",function(){t.scroller.clientHeight&&(Or(e,t.scroller.scrollTop),Wr(e,t.scroller.scrollLeft,!0),nt(e,"scroll",e))}),Je(t.scroller,"mousewheel",function(t){return gi(e,t)}),Je(t.scroller,"DOMMouseScroll",function(t){return gi(e,t)}),Je(t.wrapper,"scroll",function(){return t.wrapper.scrollTop=t.wrapper.scrollLeft=0}),t.dragFunctions={enter:function(t){rt(e,t)||ct(t)},over:function(t){rt(e,t)||(function(e,t){var n=lr(e,t);if(n){var r=document.createDocumentFragment();cr(e,n,r),e.display.dragCursor||(e.display.dragCursor=O("div",null,"CodeMirror-cursors CodeMirror-dragcursors"),e.display.lineSpace.insertBefore(e.display.dragCursor,e.display.cursorDiv)),A(e.display.dragCursor,r)}}(e,t),ct(t))},start:function(t){return function(e,t){if(l&&(!e.state.draggingText||+new Date-To<100))ct(t);else if(!rt(e,t)&&!wn(e.display,t)&&(t.dataTransfer.setData("Text",e.getSelection()),t.dataTransfer.effectAllowed="copyMove",t.dataTransfer.setDragImage&&!h)){var n=O("img",null,null,"position: fixed; left: 0; top: 0;");n.src="data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw==",f&&(n.width=n.height=1,e.display.wrapper.appendChild(n),n._top=n.offsetTop),t.dataTransfer.setDragImage(n,0,0),f&&n.parentNode.removeChild(n)}}(e,t)},drop:$r(e,Mo),leave:function(t){rt(e,t)||Ao(e)}};var s=t.input.getField();Je(s,"keyup",function(t){return ol.call(e,t)}),Je(s,"keydown",$r(e,il)),Je(s,"keypress",$r(e,ll)),Je(s,"focus",function(t){return mr(e,t)}),Je(s,"blur",function(t){return vr(e,t)})}(this),Wo(),Br(this),this.curOp.forceUpdate=!0,Oi(this,i),t.autofocus&&!v||this.hasFocus()?setTimeout(F(mr,this),20):vr(this),yl)yl.hasOwnProperty(c)&&yl[c](r,t[c],ml);Cr(this),t.finishInit&&t.finishInit(this);for(var d=0;d150)){if(!r)return;n="prev"}}else u=0,n="not";"prev"==n?u=t>o.first?z(ae(o,t-1).text,null,l):0:"add"==n?u=s+e.options.indentUnit:"subtract"==n?u=s-e.options.indentUnit:"number"==typeof n&&(u=s+n),u=Math.max(0,u);var f="",h=0;if(e.options.indentWithTabs)for(var d=Math.floor(u/l);d;--d)h+=l,f+="\t";if(h1)if(Ll&&Ll.text.join("\n")==t){if(r.ranges.length%Ll.text.length==0){u=[];for(var c=0;c=0;f--){var h=r.ranges[f],d=h.from(),p=h.to();h.empty()&&(n&&n>0?d=ge(d.line,d.ch-n):e.state.overwrite&&!a?p=ge(p.line,Math.min(ae(o,p.line).text.length,p.ch+_(s).length)):Ll&&Ll.lineWise&&Ll.text.join("\n")==t&&(d=p=ge(d.line,0))),l=e.curOp.updateInput;var g={from:d,to:p,text:u?u[f%u.length]:s,origin:i||(a?"paste":e.state.cutIncoming?"cut":"+input")};ro(e.doc,g),an(e,"inputRead",e,g)}t&&!a&&Ol(e,t),Lr(e),e.curOp.updateInput=l,e.curOp.typing=!0,e.state.pasteIncoming=e.state.cutIncoming=!1}function Al(e,t){var n=e.clipboardData&&e.clipboardData.getData("Text");if(n)return e.preventDefault(),t.isReadOnly()||t.options.disableInput||Xr(t,function(){return Ml(t,n,0,null,"paste")}),!0}function Ol(e,t){if(e.options.electricChars&&e.options.smartIndent)for(var n=e.doc.sel,r=n.ranges.length-1;r>=0;r--){var i=n.ranges[r];if(!(i.head.ch>100||r&&n.ranges[r-1].head.line==i.head.line)){var o=e.getModeAt(i.head),l=!1;if(o.electricChars){for(var a=0;a-1){l=Sl(e,i.head.line,"smart");break}}else o.electricInput&&o.electricInput.test(ae(e.doc,i.head.line).text.slice(0,i.head.ch))&&(l=Sl(e,i.head.line,"smart"));l&&an(e,"electricInput",e,i.head.line)}}}function Nl(e){for(var t=[],n=[],r=0;r=t.text.length?(n.ch=t.text.length,n.sticky="before"):n.ch<=0&&(n.ch=0,n.sticky="after");var o=_e(i,n.ch,n.sticky),l=i[o];if("ltr"==e.doc.direction&&l.level%2==0&&(r>0?l.to>n.ch:l.from=l.from&&h>=c.begin)){var d=f?"before":"after";return new ge(n.line,h,d)}}var p=function(e,t,r){for(var o=function(e,t){return t?new ge(n.line,s(e,1),"before"):new ge(n.line,e,"after")};e>=0&&e0==(1!=l.level),u=a?r.begin:s(r.end,-1);if(l.from<=u&&u0?c.end:s(c.begin,-1);return null==m||r>0&&m==t.text.length||!(g=p(r>0?0:i.length-1,r,u(m)))?null:g}(e.cm,a,t,n):$o(a,t,n))){if(r||((l=t.line+n)=e.first+e.size||(t=new ge(l,t.ch,t.sticky),!(a=ae(e,l)))))return!1;t=Yo(i,e.cm,a,t.line,n)}else t=o;return!0}if("char"==r)s();else if("column"==r)s(!0);else if("word"==r||"group"==r)for(var u=null,c="group"==r,f=e.cm&&e.cm.getHelper(t,"wordChars"),h=!0;!(n<0)||s(!h);h=!1){var d=a.text.charAt(t.ch)||"\n",p=te(d,f)?"w":c&&"\n"==d?"n":!c||/\s/.test(d)?null:"p";if(!c||h||p||(p="s"),u&&u!=p){n<0&&(n=1,s(),t.sticky="after");break}if(p&&(u=p),n>0&&!s(!h))break}var g=Ji(e,t,o,l,!0);return ve(o,g)&&(g.hitSide=!0),g}function El(e,t,n,r){var i,o,l=e.doc,a=t.left;if("page"==r){var s=Math.min(e.display.wrapper.clientHeight,window.innerHeight||document.documentElement.clientHeight),u=Math.max(s-.5*er(e.display),3);i=(n>0?t.bottom:t.top)+n*u}else"line"==r&&(i=n>0?t.bottom+3:t.top-3);for(;(o=_n(e,a,i)).outside;){if(n<0?i<=0:i>=l.height){o.hitSide=!0;break}i+=5*n}return o}var Pl=function(e){this.cm=e,this.lastAnchorNode=this.lastAnchorOffset=this.lastFocusNode=this.lastFocusOffset=null,this.polling=new R,this.composing=null,this.gracePeriod=!1,this.readDOMTimeout=null};function Fl(e,t){var n=Nn(e,t.line);if(!n||n.hidden)return null;var r=ae(e.doc,t.line),i=An(n,r,t.line),o=Ze(r,e.doc.direction),l="left";if(o){var a=_e(o,t.ch);l=a%2?"right":"left"}var s=Pn(i.map,t.ch,l);return s.offset="right"==s.collapse?s.end:s.start,s}function Il(e,t){return t&&(e.bad=!0),e}function zl(e,t,n){var r;if(t==e.display.lineDiv){if(!(r=e.display.lineDiv.childNodes[n]))return Il(e.clipPos(ge(e.display.viewTo-1)),!0);t=null,n=0}else for(r=t;;r=r.parentNode){if(!r||r==e.display.lineDiv)return null;if(r.parentNode&&r.parentNode==e.display.lineDiv)break}for(var i=0;i=t.display.viewTo||o.line=t.display.viewFrom&&Fl(t,i)||{node:s[0].measure.map[2],offset:0},c=o.liner.firstLine()&&(l=ge(l.line-1,ae(r.doc,l.line-1).length)),a.ch==ae(r.doc,a.line).text.length&&a.linei.viewTo-1)return!1;l.line==i.viewFrom||0==(e=ar(r,l.line))?(t=fe(i.view[0].line),n=i.view[0].node):(t=fe(i.view[e].line),n=i.view[e-1].node.nextSibling);var s,u,c=ar(r,a.line);if(c==i.view.length-1?(s=i.viewTo-1,u=i.lineDiv.lastChild):(s=fe(i.view[c+1].line)-1,u=i.view[c+1].node.previousSibling),!n)return!1;for(var f=r.doc.splitLines(function(e,t,n,r,i){var o="",l=!1,a=e.doc.lineSeparator();function s(){l&&(o+=a,l=!1)}function u(e){e&&(s(),o+=e)}function c(t){if(1==t.nodeType){var n=t.getAttribute("cm-text");if(null!=n)return void u(n||t.textContent.replace(/\u200b/g,""));var o,f=t.getAttribute("cm-marker");if(f){var h=e.findMarks(ge(r,0),ge(i+1,0),(g=+f,function(e){return e.id==g}));return void(h.length&&(o=h[0].find(0))&&u(se(e.doc,o.from,o.to).join(a)))}if("false"==t.getAttribute("contenteditable"))return;var d=/^(pre|div|p)$/i.test(t.nodeName);d&&s();for(var p=0;p1&&h.length>1;)if(_(f)==_(h))f.pop(),h.pop(),s--;else{if(f[0]!=h[0])break;f.shift(),h.shift(),t++}for(var d=0,p=0,g=f[0],m=h[0],v=Math.min(g.length,m.length);dl.ch&&y.charCodeAt(y.length-p-1)==b.charCodeAt(b.length-p-1);)d--,p++;f[f.length-1]=y.slice(0,y.length-p).replace(/^\u200b+/,""),f[0]=f[0].slice(d).replace(/\u200b+$/,"");var w=ge(t,d),C=ge(s,h.length?_(h).length-p:0);return f.length>1||f[0]||me(w,C)?(so(r.doc,f,w,C,"+input"),!0):void 0},Pl.prototype.ensurePolled=function(){this.forceCompositionEnd()},Pl.prototype.reset=function(){this.forceCompositionEnd()},Pl.prototype.forceCompositionEnd=function(){this.composing&&(clearTimeout(this.readDOMTimeout),this.composing=null,this.updateFromDOM(),this.div.blur(),this.div.focus())},Pl.prototype.readFromDOMSoon=function(){var e=this;null==this.readDOMTimeout&&(this.readDOMTimeout=setTimeout(function(){if(e.readDOMTimeout=null,e.composing){if(!e.composing.done)return;e.composing=null}e.updateFromDOM()},80))},Pl.prototype.updateFromDOM=function(){var e=this;!this.cm.isReadOnly()&&this.pollContent()||Xr(this.cm,function(){return qr(e.cm)})},Pl.prototype.setUneditable=function(e){e.contentEditable="false"},Pl.prototype.onKeyPress=function(e){0!=e.charCode&&(e.preventDefault(),this.cm.isReadOnly()||$r(this.cm,Ml)(this.cm,String.fromCharCode(null==e.charCode?e.keyCode:e.charCode),0))},Pl.prototype.readOnlyChanged=function(e){this.div.contentEditable=String("nocursor"!=e)},Pl.prototype.onContextMenu=function(){},Pl.prototype.resetPosition=function(){},Pl.prototype.needsContentAttribute=!0;var Bl=function(e){this.cm=e,this.prevInput="",this.pollingFast=!1,this.polling=new R,this.hasSelection=!1,this.composing=null};Bl.prototype.init=function(e){var t=this,n=this,r=this.cm,i=this.wrapper=Dl(),o=this.textarea=i.firstChild;function s(e){if(!rt(r,e)){if(r.somethingSelected())Tl({lineWise:!1,text:r.getSelections()});else{if(!r.options.lineWiseCopyCut)return;var t=Nl(r);Tl({lineWise:!0,text:t.text}),"cut"==e.type?r.setSelections(t.ranges,null,G):(n.prevInput="",o.value=t.text.join("\n"),P(o))}"cut"==e.type&&(r.state.cutIncoming=!0)}}e.wrapper.insertBefore(i,e.wrapper.firstChild),g&&(o.style.width="0px"),Je(o,"input",function(){l&&a>=9&&t.hasSelection&&(t.hasSelection=null),n.poll()}),Je(o,"paste",function(e){rt(r,e)||Al(e,r)||(r.state.pasteIncoming=!0,n.fastPoll())}),Je(o,"cut",s),Je(o,"copy",s),Je(e.scroller,"paste",function(t){wn(e,t)||rt(r,t)||(r.state.pasteIncoming=!0,n.focus())}),Je(e.lineSpace,"selectstart",function(t){wn(e,t)||at(t)}),Je(o,"compositionstart",function(){var e=r.getCursor("from");n.composing&&n.composing.range.clear(),n.composing={start:e,range:r.markText(e,r.getCursor("to"),{className:"CodeMirror-composing"})}}),Je(o,"compositionend",function(){n.composing&&(n.poll(),n.composing.range.clear(),n.composing=null)})},Bl.prototype.prepareSelection=function(){var e=this.cm,t=e.display,n=e.doc,r=ur(e);if(e.options.moveInputWithCursor){var i=Xn(e,n.sel.primary().head,"div"),o=t.wrapper.getBoundingClientRect(),l=t.lineDiv.getBoundingClientRect();r.teTop=Math.max(0,Math.min(t.wrapper.clientHeight-10,i.top+l.top-o.top)),r.teLeft=Math.max(0,Math.min(t.wrapper.clientWidth-10,i.left+l.left-o.left))}return r},Bl.prototype.showSelection=function(e){var t=this.cm,n=t.display;A(n.cursorDiv,e.cursors),A(n.selectionDiv,e.selection),null!=e.teTop&&(this.wrapper.style.top=e.teTop+"px",this.wrapper.style.left=e.teLeft+"px")},Bl.prototype.reset=function(e){if(!this.contextMenuPending&&!this.composing){var t=this.cm;if(t.somethingSelected()){this.prevInput="";var n=t.getSelection();this.textarea.value=n,t.state.focused&&P(this.textarea),l&&a>=9&&(this.hasSelection=n)}else e||(this.prevInput=this.textarea.value="",l&&a>=9&&(this.hasSelection=null))}},Bl.prototype.getField=function(){return this.textarea},Bl.prototype.supportsTouch=function(){return!1},Bl.prototype.focus=function(){if("nocursor"!=this.cm.options.readOnly&&(!v||D()!=this.textarea))try{this.textarea.focus()}catch(e){}},Bl.prototype.blur=function(){this.textarea.blur()},Bl.prototype.resetPosition=function(){this.wrapper.style.top=this.wrapper.style.left=0},Bl.prototype.receivedFocus=function(){this.slowPoll()},Bl.prototype.slowPoll=function(){var e=this;this.pollingFast||this.polling.set(this.cm.options.pollInterval,function(){e.poll(),e.cm.state.focused&&e.slowPoll()})},Bl.prototype.fastPoll=function(){var e=!1,t=this;t.pollingFast=!0,t.polling.set(20,function n(){var r=t.poll();r||e?(t.pollingFast=!1,t.slowPoll()):(e=!0,t.polling.set(60,n))})},Bl.prototype.poll=function(){var e=this,t=this.cm,n=this.textarea,r=this.prevInput;if(this.contextMenuPending||!t.state.focused||xt(n)&&!r&&!this.composing||t.isReadOnly()||t.options.disableInput||t.state.keySeq)return!1;var i=n.value;if(i==r&&!t.somethingSelected())return!1;if(l&&a>=9&&this.hasSelection===i||y&&/[\uf700-\uf7ff]/.test(i))return t.display.input.reset(),!1;if(t.doc.sel==t.display.selForContextMenu){var o=i.charCodeAt(0);if(8203!=o||r||(r="​"),8666==o)return this.reset(),this.cm.execCommand("undo")}for(var s=0,u=Math.min(r.length,i.length);s1e3||i.indexOf("\n")>-1?n.value=e.prevInput="":e.prevInput=i,e.composing&&(e.composing.range.clear(),e.composing.range=t.markText(e.composing.start,t.getCursor("to"),{className:"CodeMirror-composing"}))}),!0},Bl.prototype.ensurePolled=function(){this.pollingFast&&this.poll()&&(this.pollingFast=!1)},Bl.prototype.onKeyPress=function(){l&&a>=9&&(this.hasSelection=null),this.fastPoll()},Bl.prototype.onContextMenu=function(e){var t=this,n=t.cm,r=n.display,i=t.textarea,o=lr(n,e),u=r.scroller.scrollTop;if(o&&!f){var c=n.options.resetSelectionOnContextMenu;c&&-1==n.doc.sel.contains(o)&&$r(n,$i)(n.doc,bi(o),G);var h=i.style.cssText,d=t.wrapper.style.cssText;t.wrapper.style.cssText="position: absolute";var p,g=t.wrapper.getBoundingClientRect();if(i.style.cssText="position: absolute; width: 30px; height: 30px;\n top: "+(e.clientY-g.top-5)+"px; left: "+(e.clientX-g.left-5)+"px;\n z-index: 1000; background: "+(l?"rgba(255, 255, 255, .05)":"transparent")+";\n outline: none; border-width: 0; outline: none; overflow: hidden; opacity: .05; filter: alpha(opacity=5);",s&&(p=window.scrollY),r.input.focus(),s&&window.scrollTo(null,p),r.input.reset(),n.somethingSelected()||(i.value=t.prevInput=" "),t.contextMenuPending=!0,r.selForContextMenu=n.doc.sel,clearTimeout(r.detectingSelectAll),l&&a>=9&&v(),k){ct(e);var m=function(){tt(window,"mouseup",m),setTimeout(y,20)};Je(window,"mouseup",m)}else setTimeout(y,50)}function v(){if(null!=i.selectionStart){var e=n.somethingSelected(),o="​"+(e?i.value:"");i.value="⇚",i.value=o,t.prevInput=e?"":"​",i.selectionStart=1,i.selectionEnd=o.length,r.selForContextMenu=n.doc.sel}}function y(){if(t.contextMenuPending=!1,t.wrapper.style.cssText=d,i.style.cssText=h,l&&a<9&&r.scrollbars.setScrollTop(r.scroller.scrollTop=u),null!=i.selectionStart){(!l||l&&a<9)&&v();var e=0,o=function(){r.selForContextMenu==n.doc.sel&&0==i.selectionStart&&i.selectionEnd>0&&"​"==t.prevInput?$r(n,to)(n):e++<10?r.detectingSelectAll=setTimeout(o,500):(r.selForContextMenu=null,r.input.reset())};r.detectingSelectAll=setTimeout(o,200)}}},Bl.prototype.readOnlyChanged=function(e){e||this.reset(),this.textarea.disabled="nocursor"==e},Bl.prototype.setUneditable=function(){},Bl.prototype.needsContentAttribute=!1,function(e){var t=e.optionHandlers;function n(n,r,i,o){e.defaults[n]=r,i&&(t[n]=o?function(e,t,n){n!=ml&&i(e,t,n)}:i)}e.defineOption=n,e.Init=ml,n("value","",function(e,t){return e.setValue(t)},!0),n("mode",null,function(e,t){e.doc.modeOption=t,Si(e)},!0),n("indentUnit",2,Si,!0),n("indentWithTabs",!1),n("smartIndent",!0),n("tabSize",4,function(e){Li(e),Rn(e),qr(e)},!0),n("lineSeparator",null,function(e,t){if(e.doc.lineSep=t,t){var n=[],r=e.doc.first;e.doc.iter(function(e){for(var i=0;;){var o=e.text.indexOf(t,i);if(-1==o)break;i=o+t.length,n.push(ge(r,o))}r++});for(var i=n.length-1;i>=0;i--)so(e.doc,t,n[i],ge(n[i].line,n[i].ch+t.length))}}),n("specialChars",/[\u0000-\u001f\u007f-\u009f\u00ad\u061c\u200b-\u200f\u2028\u2029\ufeff]/g,function(e,t,n){e.state.specialChars=new RegExp(t.source+(t.test("\t")?"":"|\t"),"g"),n!=ml&&e.refresh()}),n("specialCharPlaceholder",Zt,function(e){return e.refresh()},!0),n("electricChars",!0),n("inputStyle",v?"contenteditable":"textarea",function(){throw new Error("inputStyle can not (yet) be changed in a running editor")},!0),n("spellcheck",!1,function(e,t){return e.getInputField().spellcheck=t},!0),n("rtlMoveVisually",!x),n("wholeLineUpdateBefore",!0),n("theme","default",function(e){gl(e),bl(e)},!0),n("keyMap","default",function(e,t,n){var r=Uo(t),i=n!=ml&&Uo(n);i&&i.detach&&i.detach(e,r),r.attach&&r.attach(e,i||null)}),n("extraKeys",null),n("configureMouse",null),n("lineWrapping",!1,wl,!0),n("gutters",[],function(e){ci(e.options),bl(e)},!0),n("fixedGutter",!0,function(e,t){e.display.gutters.style.left=t?rr(e.display)+"px":"0",e.refresh()},!0),n("coverGutterNextToScrollbar",!1,function(e){return Pr(e)},!0),n("scrollbarStyle","native",function(e){zr(e),Pr(e),e.display.scrollbars.setScrollTop(e.doc.scrollTop),e.display.scrollbars.setScrollLeft(e.doc.scrollLeft)},!0),n("lineNumbers",!1,function(e){ci(e.options),bl(e)},!0),n("firstLineNumber",1,bl,!0),n("lineNumberFormatter",function(e){return e},bl,!0),n("showCursorWhenSelecting",!1,sr,!0),n("resetSelectionOnContextMenu",!0),n("lineWiseCopyCut",!0),n("pasteLinesPerSelection",!0),n("readOnly",!1,function(e,t){"nocursor"==t&&(vr(e),e.display.input.blur()),e.display.input.readOnlyChanged(t)}),n("disableInput",!1,function(e,t){t||e.display.input.reset()},!0),n("dragDrop",!0,xl),n("allowDropFileTypes",null),n("cursorBlinkRate",530),n("cursorScrollMargin",0),n("cursorHeight",1,sr,!0),n("singleCursorHeightPerLine",!0,sr,!0),n("workTime",100),n("workDelay",100),n("flattenSpans",!0,Li,!0),n("addModeClass",!1,Li,!0),n("pollInterval",100),n("undoDepth",200,function(e,t){return e.doc.history.undoDepth=t}),n("historyEventDelay",1250),n("viewportMargin",10,function(e){return e.refresh()},!0),n("maxHighlightLength",1e4,Li,!0),n("moveInputWithCursor",!0,function(e,t){t||e.display.input.resetPosition()}),n("tabindex",null,function(e,t){return e.display.input.getField().tabIndex=t||""}),n("autofocus",null),n("direction","ltr",function(e,t){return e.doc.setDirection(t)},!0)}(Cl),function(e){var t=e.optionHandlers,n=e.helpers={};e.prototype={constructor:e,focus:function(){window.focus(),this.display.input.focus()},setOption:function(e,n){var r=this.options,i=r[e];r[e]==n&&"mode"!=e||(r[e]=n,t.hasOwnProperty(e)&&$r(this,t[e])(this,n,i),nt(this,"optionChange",this,e))},getOption:function(e){return this.options[e]},getDoc:function(){return this.doc},addKeyMap:function(e,t){this.state.keyMaps[t?"push":"unshift"](Uo(e))},removeKeyMap:function(e){for(var t=this.state.keyMaps,n=0;nn&&(Sl(this,i.head.line,e,!0),n=i.head.line,r==this.doc.sel.primIndex&&Lr(this));else{var o=i.from(),l=i.to(),a=Math.max(n,o.line);n=Math.min(this.lastLine(),l.line-(l.ch?0:1))+1;for(var s=a;s0&&Ui(this.doc,r,new vi(o,u[r].to()),G)}}}),getTokenAt:function(e,t){return Vt(this,e,t)},getLineTokens:function(e,t){return Vt(this,ge(e),t,!0)},getTokenTypeAt:function(e){e=Ce(this.doc,e);var t,n=Ft(this,ae(this.doc,e.line)),r=0,i=(n.length-1)/2,o=e.ch;if(0==o)t=n[2];else for(;;){var l=r+i>>1;if((l?n[2*l-1]:0)>=o)i=l;else{if(!(n[2*l+1]o&&(e=o,i=!0),r=ae(this.doc,e)}else r=e;return Gn(this,r,{top:0,left:0},t||"page",n||i).top+(i?this.doc.height-Ke(r):0)},defaultTextHeight:function(){return er(this.display)},defaultCharWidth:function(){return tr(this.display)},getViewport:function(){return{from:this.display.viewFrom,to:this.display.viewTo}},addWidget:function(e,t,n,r,i){var o,l,a,s=this.display,u=(e=Xn(this,Ce(this.doc,e))).bottom,c=e.left;if(t.style.position="absolute",t.setAttribute("cm-ignore-events","true"),this.display.input.setUneditable(t),s.sizer.appendChild(t),"over"==r)u=e.top;else if("above"==r||"near"==r){var f=Math.max(s.wrapper.clientHeight,this.doc.height),h=Math.max(s.sizer.clientWidth,s.lineSpace.clientWidth);("above"==r||e.bottom+t.offsetHeight>f)&&e.top>t.offsetHeight?u=e.top-t.offsetHeight:e.bottom+t.offsetHeight<=f&&(u=e.bottom),c+t.offsetWidth>h&&(c=h-t.offsetWidth)}t.style.top=u+"px",t.style.left=t.style.right="","right"==i?(c=s.sizer.clientWidth-t.offsetWidth,t.style.right="0px"):("left"==i?c=0:"middle"==i&&(c=(s.sizer.clientWidth-t.offsetWidth)/2),t.style.left=c+"px"),n&&(o=this,l={left:c,top:u,right:c+t.offsetWidth,bottom:u+t.offsetHeight},null!=(a=kr(o,l)).scrollTop&&Or(o,a.scrollTop),null!=a.scrollLeft&&Wr(o,a.scrollLeft))},triggerOnKeyDown:Yr(il),triggerOnKeyPress:Yr(ll),triggerOnKeyUp:ol,triggerOnMouseDown:Yr(cl),execCommand:function(e){if(_o.hasOwnProperty(e))return _o[e].call(null,this)},triggerElectric:Yr(function(e){Ol(this,e)}),findPosH:function(e,t,n,r){var i=1;t<0&&(i=-1,t=-t);for(var o=Ce(this.doc,e),l=0;l0&&a(n.charAt(r-1));)--r;for(;i.5)&&or(this),nt(this,"refresh",this)}),swapDoc:Yr(function(e){var t=this.doc;return t.cm=null,Oi(this,e),Rn(this),this.display.input.reset(),Tr(this,e.scrollLeft,e.scrollTop),this.curOp.forceScroll=!0,an(this,"swapDoc",this,t),t}),getInputField:function(){return this.display.input.getField()},getWrapperElement:function(){return this.display.wrapper},getScrollerElement:function(){return this.display.scroller},getGutterElement:function(){return this.display.gutters}},lt(e),e.registerHelper=function(t,r,i){n.hasOwnProperty(t)||(n[t]=e[t]={_global:[]}),n[t][r]=i},e.registerGlobalHelper=function(t,r,i,o){e.registerHelper(t,r,o),n[t]._global.push({pred:i,val:o})}}(Cl);var jl="iter insert remove copy getEditor constructor".split(" ");for(var Vl in Lo.prototype)Lo.prototype.hasOwnProperty(Vl)&&B(jl,Vl)<0&&(Cl.prototype[Vl]=function(e){return function(){return e.apply(this.doc,arguments)}}(Lo.prototype[Vl]));return lt(Lo),Cl.inputStyles={textarea:Bl,contenteditable:Pl},Cl.defineMode=function(e){Cl.defaults.mode||"null"==e||(Cl.defaults.mode=e),function(e,t){arguments.length>2&&(t.dependencies=Array.prototype.slice.call(arguments,2)),kt[e]=t}.apply(this,arguments)},Cl.defineMIME=function(e,t){St[e]=t},Cl.defineMode("null",function(){return{token:function(e){return e.skipToEnd()}}}),Cl.defineMIME("text/plain","null"),Cl.defineExtension=function(e,t){Cl.prototype[e]=t},Cl.defineDocExtension=function(e,t){Lo.prototype[e]=t},Cl.fromTextArea=function(e,t){if((t=t?I(t):{}).value=e.value,!t.tabindex&&e.tabIndex&&(t.tabindex=e.tabIndex),!t.placeholder&&e.placeholder&&(t.placeholder=e.placeholder),null==t.autofocus){var n=D();t.autofocus=n==e||null!=e.getAttribute("autofocus")&&n==document.body}function r(){e.value=a.getValue()}var i;if(e.form&&(Je(e.form,"submit",r),!t.leaveSubmitMethodAlone)){var o=e.form;i=o.submit;try{var l=o.submit=function(){r(),o.submit=i,o.submit(),o.submit=l}}catch(e){}}t.finishInit=function(t){t.save=r,t.getTextArea=function(){return e},t.toTextArea=function(){t.toTextArea=isNaN,r(),e.parentNode.removeChild(t.getWrapperElement()),e.style.display="",e.form&&(tt(e.form,"submit",r),"function"==typeof e.form.submit&&(e.form.submit=i))}},e.style.display="none";var a=Cl(function(t){return e.parentNode.insertBefore(t,e.nextSibling)},t);return a},function(e){e.off=tt,e.on=Je,e.wheelEventPixels=pi,e.Doc=Lo,e.splitLines=bt,e.countColumn=z,e.findColumn=X,e.isWordChar=ee,e.Pass=V,e.signal=nt,e.Line=Kt,e.changeEnd=xi,e.scrollbarModel=Ir,e.Pos=ge,e.cmpPos=me,e.modes=kt,e.mimeModes=St,e.resolveMode=Lt,e.getMode=Tt,e.modeExtensions=Mt,e.extendMode=At,e.copyState=Ot,e.startState=Wt,e.innerMode=Nt,e.commands=_o,e.keyMap=Io,e.keyName=Go,e.isModifierKey=jo,e.lookupKey=Bo,e.normalizeKeyMap=Ro,e.StringStream=Dt,e.SharedTextMarker=wo,e.TextMarker=bo,e.LineWidget=mo,e.e_preventDefault=at,e.e_stopPropagation=st,e.e_stop=ct,e.addClass=H,e.contains=W,e.rmClass=T,e.keyNames=Ho}(Cl),Cl.version="5.34.1",Cl}(),function(e){var t=/MSIE \d/.test(navigator.userAgent)&&(null==document.documentMode||document.documentMode<8),n=e.Pos,r={"(":")>",")":"(<","[":"]>","]":"[<","{":"}>","}":"{<"};function i(e,t,i){var l=e.getLineHandle(t.line),a=t.ch-1,s=i&&i.afterCursor;null==s&&(s=/(^| )cm-fat-cursor($| )/.test(e.getWrapperElement().className));var u=!s&&a>=0&&r[l.text.charAt(a)]||r[l.text.charAt(++a)];if(!u)return null;var c=">"==u.charAt(1)?1:-1;if(i&&i.strict&&c>0!=(a==t.ch))return null;var f=e.getTokenTypeAt(n(t.line,a+1)),h=o(e,n(t.line,a+(c>0?1:0)),c,f||null,i);return null==h?null:{from:n(t.line,a),to:h&&h.pos,match:h&&h.ch==u.charAt(0),forward:c>0}}function o(e,t,i,o,l){for(var a=l&&l.maxScanLineLength||1e4,s=l&&l.maxScanLines||1e3,u=[],c=l&&l.bracketRegex?l.bracketRegex:/[(){}[\]]/,f=i>0?Math.min(t.line+s,e.lastLine()+1):Math.max(e.firstLine()-1,t.line-s),h=t.line;h!=f;h+=i){var d=e.getLine(h);if(d){var p=i>0?0:d.length-1,g=i>0?d.length:-1;if(!(d.length>a))for(h==t.line&&(p=t.ch-(i<0?1:0));p!=g;p+=i){var m=d.charAt(p);if(c.test(m)&&(void 0===o||e.getTokenTypeAt(n(h,p+1))==o)){var v=r[m];if(">"==v.charAt(1)==i>0)u.push(m);else{if(!u.length)return{pos:n(h,p),ch:m};u.pop()}}}}}return h-i!=(i>0?e.lastLine():e.firstLine())&&null}function l(e,r,o){for(var l=e.state.matchBrackets.maxHighlightLineLength||1e3,a=[],s=e.listSelections(),u=0;u-1&&d>f){if(u=c.slice(0,d),/\S/.test(u)){u="";for(var h=0;h-1&&!/\S/.test(c.slice(0,d))&&(u=c.slice(0,d));null!=u&&(u+=r.blockCommentContinue)}if(null==u&&r.lineComment&&n(t)){var c=t.getLine(a.line),d=c.indexOf(r.lineComment);d>-1&&(u=c.slice(0,d),/\S/.test(u)?u=null:u+=r.lineComment+c.slice(d+r.lineComment.length).match(/^\s*/)[0])}if(null==u)return e.Pass;o[l]="\n"+u}t.operation(function(){for(var e=i.length-1;e>=0;e--)t.replaceRange(o[e],i[e].from(),i[e].to(),"+insert")})}function n(e){var t=e.getOption("continueComments");return!t||"object"!=typeof t||!1!==t.continueLineComment}e.defineOption("continueComments",null,function(n,r,i){if(i&&i!=e.Init&&n.removeKeyMap("continueComment"),r){var o="Enter";"string"==typeof r?o=r:"object"==typeof r&&r.key&&(o=r.key);var l={name:"continueComment"};l[o]=t,n.addKeyMap(l)}})}(CodeMirror),function(e){"use strict";var t={},n=/[^\s\u00a0]/,r=e.Pos;function i(e){var t=e.search(n);return-1==t?0:t}function o(e,t){var n=e.getMode();return!1!==n.useInnerComments&&n.innerMode?e.getModeAt(t):n}e.commands.toggleComment=function(e){e.toggleComment()},e.defineExtension("toggleComment",function(e){e||(e=t);for(var n=1/0,i=this.listSelections(),o=null,l=i.length-1;l>=0;l--){var a=i[l].from(),s=i[l].to();a.line>=n||(s.line>=n&&(s=r(n,0)),n=a.line,null==o?this.uncomment(a,s,e)?o="un":(this.lineComment(a,s,e),o="line"):"un"==o?this.uncomment(a,s,e):this.lineComment(a,s,e))}}),e.defineExtension("lineComment",function(e,l,a){a||(a=t);var s=this,u=o(s,e),c=s.getLine(e.line);if(null!=c&&(f=e,h=c,!/\bstring\b/.test(s.getTokenTypeAt(r(f.line,0)))||/^[\'\"\`]/.test(h))){var f,h,d=a.lineComment||u.lineComment;if(d){var p=Math.min(0!=l.ch||l.line==e.line?l.line+1:l.line,s.lastLine()+1),g=null==a.padding?" ":a.padding,m=a.commentBlankLines||e.line==l.line;s.operation(function(){if(a.indent){for(var t=null,o=e.line;ou.length)&&(t=u)}for(var o=e.line;of||a.operation(function(){if(0!=l.fullLines){var t=n.test(a.getLine(f));a.replaceRange(h+c,r(f)),a.replaceRange(u+h,r(e.line,0));var o=l.blockCommentLead||s.blockCommentLead;if(null!=o)for(var d=e.line+1;d<=f;++d)(d!=f||t)&&a.replaceRange(o+h,r(d,0))}else a.replaceRange(c,i),a.replaceRange(u,e)})}}else(l.lineComment||s.lineComment)&&0!=l.fullLines&&a.lineComment(e,i,l)}),e.defineExtension("uncomment",function(e,i,l){l||(l=t);var a,s=this,u=o(s,e),c=Math.min(0!=i.ch||i.line==e.line?i.line:i.line-1,s.lastLine()),f=Math.min(e.line,c),h=l.lineComment||u.lineComment,d=[],p=null==l.padding?" ":l.padding;e:if(h){for(var g=f;g<=c;++g){var m=s.getLine(g),v=m.indexOf(h);if(v>-1&&!/comment/.test(s.getTokenTypeAt(r(g,v+1)))&&(v=-1),-1==v&&n.test(m))break e;if(v>-1&&n.test(m.slice(0,v)))break e;d.push(m)}if(s.operation(function(){for(var e=f;e<=c;++e){var t=d[e-f],n=t.indexOf(h),i=n+h.length;n<0||(t.slice(i,i+p.length)==p&&(i+=p.length),a=!0,s.replaceRange("",r(e,n),r(e,i)))}}),a)return!0}var y=l.blockCommentStart||u.blockCommentStart,b=l.blockCommentEnd||u.blockCommentEnd;if(!y||!b)return!1;var x=l.blockCommentLead||u.blockCommentLead,w=s.getLine(f),C=w.indexOf(y);if(-1==C)return!1;var k=c==f?w:s.getLine(c),S=k.indexOf(b,c==f?C+y.length:0),L=r(f,C+1),T=r(c,S+1);if(-1==S||!/comment/.test(s.getTokenTypeAt(L))||!/comment/.test(s.getTokenTypeAt(T))||s.getRange(L,T,"\n").indexOf(b)>-1)return!1;var M=w.lastIndexOf(y,e.ch),A=-1==M?-1:w.slice(0,e.ch).indexOf(b,M+y.length);if(-1!=M&&-1!=A&&A+b.length!=e.ch)return!1;A=k.indexOf(b,i.ch);var O=k.slice(i.ch).lastIndexOf(y,A-i.ch);return M=-1==A||-1==O?-1:i.ch+O,(-1==A||-1==M||M==i.ch)&&(s.operation(function(){s.replaceRange("",r(c,S-(p&&k.slice(S-p.length,S)==p?p.length:0)),r(c,S+b.length));var e=C+y.length;if(p&&w.slice(e,e+p.length)==p&&(e+=p.length),s.replaceRange("",r(f,C),r(f,e)),x)for(var t=f+1;t<=c;++t){var i=s.getLine(t),o=i.indexOf(x);if(-1!=o&&!n.test(i.slice(0,o))){var l=o+x.length;p&&i.slice(l,l+p.length)==p&&(l+=p.length),s.replaceRange("",r(t,o),r(t,l))}}}),!0)})}(CodeMirror),function(e){"use strict";e.defineMode("javascript",function(t,n){var r,i,o=t.indentUnit,l=n.statementIndent,a=n.jsonld,s=n.json||a,u=n.typescript,c=n.wordCharacters||/[\w$\xa1-\uffff]/,f=function(){function e(e){return{type:e,style:"keyword"}}var t=e("keyword a"),n=e("keyword b"),r=e("keyword c"),i=e("keyword d"),o=e("operator"),l={type:"atom",style:"atom"};return{if:e("if"),while:t,with:t,else:n,do:n,try:n,finally:n,return:i,break:i,continue:i,new:e("new"),delete:r,void:r,throw:r,debugger:e("debugger"),var:e("var"),const:e("var"),let:e("var"),function:e("function"),catch:e("catch"),for:e("for"),switch:e("switch"),case:e("case"),default:e("default"),in:o,typeof:o,instanceof:o,true:l,false:l,null:l,undefined:l,NaN:l,Infinity:l,this:e("this"),class:e("class"),super:e("atom"),yield:r,export:e("export"),import:e("import"),extends:r,await:r}}(),h=/[+\-*&%=<>!?|~^@]/,d=/^@(context|id|value|language|type|container|list|set|reverse|index|base|vocab|graph)"/;function p(e,t,n){return r=e,i=n,t}function g(e,t){var n,r=e.next();if('"'==r||"'"==r)return t.tokenize=(n=r,function(e,t){var r,i=!1;if(a&&"@"==e.peek()&&e.match(d))return t.tokenize=g,p("jsonld-keyword","meta");for(;null!=(r=e.next())&&(r!=n||i);)i=!i&&"\\"==r;return i||(t.tokenize=g),p("string","string")}),t.tokenize(e,t);if("."==r&&e.match(/^\d+(?:[eE][+\-]?\d+)?/))return p("number","number");if("."==r&&e.match(".."))return p("spread","meta");if(/[\[\]{}\(\),;\:\.]/.test(r))return p(r);if("="==r&&e.eat(">"))return p("=>","operator");if("0"==r&&e.eat(/x/i))return e.eatWhile(/[\da-f]/i),p("number","number");if("0"==r&&e.eat(/o/i))return e.eatWhile(/[0-7]/i),p("number","number");if("0"==r&&e.eat(/b/i))return e.eatWhile(/[01]/i),p("number","number");if(/\d/.test(r))return e.match(/^\d*(?:\.\d*)?(?:[eE][+\-]?\d+)?/),p("number","number");if("/"==r)return e.eat("*")?(t.tokenize=m,m(e,t)):e.eat("/")?(e.skipToEnd(),p("comment","comment")):je(e,t,1)?(function(e){for(var t,n=!1,r=!1;null!=(t=e.next());){if(!n){if("/"==t&&!r)return;"["==t?r=!0:r&&"]"==t&&(r=!1)}n=!n&&"\\"==t}}(e),e.match(/^\b(([gimyu])(?![gimyu]*\2))+\b/),p("regexp","string-2")):(e.eat("="),p("operator","operator",e.current()));if("`"==r)return t.tokenize=v,v(e,t);if("#"==r)return e.skipToEnd(),p("error","error");if(h.test(r))return">"==r&&t.lexical&&">"==t.lexical.type||(e.eat("=")?"!"!=r&&"="!=r||e.eat("="):/[<>*+\-]/.test(r)&&(e.eat(r),">"==r&&e.eat(r))),p("operator","operator",e.current());if(c.test(r)){e.eatWhile(c);var i=e.current();if("."!=t.lastType){if(f.propertyIsEnumerable(i)){var o=f[i];return p(o.type,o.style,i)}if("async"==i&&e.match(/^(\s|\/\*.*?\*\/)*[\(\w]/,!1))return p("async","keyword",i)}return p("variable","variable",i)}}function m(e,t){for(var n,r=!1;n=e.next();){if("/"==n&&r){t.tokenize=g;break}r="*"==n}return p("comment","comment")}function v(e,t){for(var n,r=!1;null!=(n=e.next());){if(!r&&("`"==n||"$"==n&&e.eat("{"))){t.tokenize=g;break}r=!r&&"\\"==n}return p("quasi","string-2",e.current())}var y="([{}])";function b(e,t){t.fatArrowAt&&(t.fatArrowAt=null);var n=e.string.indexOf("=>",e.start);if(!(n<0)){if(u){var r=/:\s*(?:\w+(?:<[^>]*>|\[\])?|\{[^}]*\})\s*$/.exec(e.string.slice(e.start,n));r&&(n=r.index)}for(var i=0,o=!1,l=n-1;l>=0;--l){var a=e.string.charAt(l),s=y.indexOf(a);if(s>=0&&s<3){if(!i){++l;break}if(0==--i){"("==a&&(o=!0);break}}else if(s>=3&&s<6)++i;else if(c.test(a))o=!0;else{if(/["'\/]/.test(a))return;if(o&&!i){++l;break}}}o&&!i&&(t.fatArrowAt=l)}}var x={atom:!0,number:!0,variable:!0,string:!0,regexp:!0,this:!0,"jsonld-keyword":!0};function w(e,t,n,r,i,o){this.indented=e,this.column=t,this.type=n,this.prev=i,this.info=o,null!=r&&(this.align=r)}function C(e,t){for(var n=e.localVars;n;n=n.next)if(n.name==t)return!0;for(var r=e.context;r;r=r.prev)for(var n=r.vars;n;n=n.next)if(n.name==t)return!0}var k={state:null,column:null,marked:null,cc:null};function S(){for(var e=arguments.length-1;e>=0;e--)k.cc.push(arguments[e])}function L(){return S.apply(null,arguments),!0}function T(e){function t(t){for(var n=t;n;n=n.next)if(n.name==e)return!0;return!1}var r=k.state;if(k.marked="def",r.context){if(t(r.localVars))return;r.localVars={name:e,next:r.localVars}}else{if(t(r.globalVars))return;n.globalVars&&(r.globalVars={name:e,next:r.globalVars})}}function M(e){return"public"==e||"private"==e||"protected"==e||"abstract"==e||"readonly"==e}var A={name:"this",next:{name:"arguments"}};function O(){k.state.context={prev:k.state.context,vars:k.state.localVars},k.state.localVars=A}function N(){k.state.localVars=k.state.context.vars,k.state.context=k.state.context.prev}function W(e,t){var n=function(){var n=k.state,r=n.indented;if("stat"==n.lexical.type)r=n.lexical.indented;else for(var i=n.lexical;i&&")"==i.type&&i.align;i=i.prev)r=i.indented;n.lexical=new w(r,k.stream.column(),e,null,n.lexical,t)};return n.lex=!0,n}function D(){var e=k.state;e.lexical.prev&&(")"==e.lexical.type&&(e.indented=e.lexical.indented),e.lexical=e.lexical.prev)}function H(e){return function t(n){return n==e?L():";"==e?S():L(t)}}function E(e,t){return"var"==e?L(W("vardef",t.length),de,H(";"),D):"keyword a"==e?L(W("form"),I,E,D):"keyword b"==e?L(W("form"),E,D):"keyword d"==e?k.stream.match(/^\s*$/,!1)?L():L(W("stat"),R,H(";"),D):"debugger"==e?L(H(";")):"{"==e?L(W("}"),te,D):";"==e?L():"if"==e?("else"==k.state.lexical.info&&k.state.cc[k.state.cc.length-1]==D&&k.state.cc.pop()(),L(W("form"),I,E,D,ye)):"function"==e?L(Se):"for"==e?L(W("form"),be,E,D):"class"==e||u&&"interface"==t?(k.marked="keyword",L(W("form"),Me,D)):"variable"==e?u&&"declare"==t?(k.marked="keyword",L(E)):u&&("module"==t||"enum"==t||"type"==t)&&k.stream.match(/^\s*\w/,!1)?(k.marked="keyword","enum"==t?L(Re):"type"==t?L(oe,H("operator"),oe,H(";")):L(W("form"),pe,H("{"),W("}"),te,D,D)):u&&"namespace"==t?(k.marked="keyword",L(W("form"),P,te,D)):L(W("stat"),Y):"switch"==e?L(W("form"),I,H("{"),W("}","switch"),te,D,D):"case"==e?L(P,H(":")):"default"==e?L(H(":")):"catch"==e?L(W("form"),O,H("("),Le,H(")"),E,D,N):"export"==e?L(W("stat"),We,D):"import"==e?L(W("stat"),He,D):"async"==e?L(E):"@"==t?L(P,E):S(W("stat"),P,H(";"),D)}function P(e,t){return z(e,t,!1)}function F(e,t){return z(e,t,!0)}function I(e){return"("!=e?S():L(W(")"),P,H(")"),D)}function z(e,t,n){if(k.state.fatArrowAt==k.stream.start){var r=n?K:U;if("("==e)return L(O,W(")"),J(Le,")"),D,H("=>"),r,N);if("variable"==e)return S(O,pe,H("=>"),r,N)}var i=n?j:B;return x.hasOwnProperty(e)?L(i):"function"==e?L(Se,i):"class"==e||u&&"interface"==t?(k.marked="keyword",L(W("form"),Te,D)):"keyword c"==e||"async"==e?L(n?F:P):"("==e?L(W(")"),R,H(")"),D,i):"operator"==e||"spread"==e?L(n?F:P):"["==e?L(W("]"),ze,D,i):"{"==e?ee(q,"}",null,i):"quasi"==e?S(V,i):"new"==e?L(function(e){return function(t){return"."==t?L(e?$:X):"variable"==t&&u?L(ce,e?j:B):S(e?F:P)}}(n)):"import"==e?L(P):L()}function R(e){return e.match(/[;\}\)\],]/)?S():S(P)}function B(e,t){return","==e?L(P):j(e,t,!1)}function j(e,t,n){var r=0==n?B:j,i=0==n?P:F;return"=>"==e?L(O,n?K:U,N):"operator"==e?/\+\+|--/.test(t)||u&&"!"==t?L(r):u&&"<"==t&&k.stream.match(/^([^>]|<.*?>)*>\s*\(/,!1)?L(W(">"),J(oe,">"),D,r):"?"==t?L(P,H(":"),i):L(i):"quasi"==e?S(V,r):";"!=e?"("==e?ee(F,")","call",r):"."==e?L(_,r):"["==e?L(W("]"),R,H("]"),D,r):u&&"as"==t?(k.marked="keyword",L(oe,r)):"regexp"==e?(k.state.lastType=k.marked="operator",k.stream.backUp(k.stream.pos-k.stream.start-1),L(i)):void 0:void 0}function V(e,t){return"quasi"!=e?S():"${"!=t.slice(t.length-2)?L(V):L(P,G)}function G(e){if("}"==e)return k.marked="string-2",k.state.tokenize=v,L(V)}function U(e){return b(k.stream,k.state),S("{"==e?E:P)}function K(e){return b(k.stream,k.state),S("{"==e?E:F)}function X(e,t){if("target"==t)return k.marked="keyword",L(B)}function $(e,t){if("target"==t)return k.marked="keyword",L(j)}function Y(e){return":"==e?L(D,E):S(B,H(";"),D)}function _(e){if("variable"==e)return k.marked="property",L()}function q(e,t){if("async"==e)return k.marked="property",L(q);if("variable"==e||"keyword"==k.style){return k.marked="property","get"==t||"set"==t?L(Z):(u&&k.state.fatArrowAt==k.stream.start&&(n=k.stream.match(/^\s*:\s*/,!1))&&(k.state.fatArrowAt=k.stream.pos+n[0].length),L(Q));var n}else{if("number"==e||"string"==e)return k.marked=a?"property":k.style+" property",L(Q);if("jsonld-keyword"==e)return L(Q);if(u&&M(t))return k.marked="keyword",L(q);if("["==e)return L(P,ne,H("]"),Q);if("spread"==e)return L(F,Q);if("*"==t)return k.marked="keyword",L(q);if(":"==e)return S(Q)}}function Z(e){return"variable"!=e?S(Q):(k.marked="property",L(Se))}function Q(e){return":"==e?L(F):"("==e?S(Se):void 0}function J(e,t,n){function r(i,o){if(n?n.indexOf(i)>-1:","==i){var l=k.state.lexical;return"call"==l.info&&(l.pos=(l.pos||0)+1),L(function(n,r){return n==t||r==t?S():S(e)},r)}return i==t||o==t?L():L(H(t))}return function(n,i){return n==t||i==t?L():S(e,r)}}function ee(e,t,n){for(var r=3;r"==e)return L(oe)}function ae(e,t){return"variable"==e||"keyword"==k.style?(k.marked="property",L(ae)):"?"==t?L(ae):":"==e?L(oe):"["==e?L(P,ne,H("]"),ae):void 0}function se(e){return"variable"==e?L(se):":"==e?L(oe):void 0}function ue(e,t){return"<"==t?L(W(">"),J(oe,">"),D,ue):"|"==t||"."==e||"&"==t?L(oe):"["==e?L(H("]"),ue):"extends"==t||"implements"==t?(k.marked="keyword",L(oe)):void 0}function ce(e,t){if("<"==t)return L(W(">"),J(oe,">"),D,ue)}function fe(){return S(oe,he)}function he(e,t){if("="==t)return L(oe)}function de(e,t){return"enum"==t?(k.marked="keyword",L(Re)):S(pe,ne,me,ve)}function pe(e,t){return u&&M(t)?(k.marked="keyword",L(pe)):"variable"==e?(T(t),L()):"spread"==e?L(pe):"["==e?ee(pe,"]"):"{"==e?ee(ge,"}"):void 0}function ge(e,t){return"variable"!=e||k.stream.match(/^\s*:/,!1)?("variable"==e&&(k.marked="property"),"spread"==e?L(pe):"}"==e?S():L(H(":"),pe,me)):(T(t),L(me))}function me(e,t){if("="==t)return L(F)}function ve(e){if(","==e)return L(de)}function ye(e,t){if("keyword b"==e&&"else"==t)return L(W("form","else"),E,D)}function be(e,t){return"await"==t?L(be):"("==e?L(W(")"),xe,H(")"),D):void 0}function xe(e){return"var"==e?L(de,H(";"),Ce):";"==e?L(Ce):"variable"==e?L(we):S(P,H(";"),Ce)}function we(e,t){return"in"==t||"of"==t?(k.marked="keyword",L(P)):L(B,Ce)}function Ce(e,t){return";"==e?L(ke):"in"==t||"of"==t?(k.marked="keyword",L(P)):S(P,H(";"),ke)}function ke(e){")"!=e&&L(P)}function Se(e,t){return"*"==t?(k.marked="keyword",L(Se)):"variable"==e?(T(t),L(Se)):"("==e?L(O,W(")"),J(Le,")"),D,re,E,N):u&&"<"==t?L(W(">"),J(fe,">"),D,Se):void 0}function Le(e,t){return"@"==t&&L(P,Le),"spread"==e?L(Le):u&&M(t)?(k.marked="keyword",L(Le)):S(pe,ne,me)}function Te(e,t){return"variable"==e?Me(e,t):Ae(e,t)}function Me(e,t){if("variable"==e)return T(t),L(Ae)}function Ae(e,t){return"<"==t?L(W(">"),J(fe,">"),D,Ae):"extends"==t||"implements"==t||u&&","==e?("implements"==t&&(k.marked="keyword"),L(u?oe:P,Ae)):"{"==e?L(W("}"),Oe,D):void 0}function Oe(e,t){return"async"==e||"variable"==e&&("static"==t||"get"==t||"set"==t||u&&M(t))&&k.stream.match(/^\s+[\w$\xa1-\uffff]/,!1)?(k.marked="keyword",L(Oe)):"variable"==e||"keyword"==k.style?(k.marked="property",L(u?Ne:Se,Oe)):"["==e?L(P,ne,H("]"),u?Ne:Se,Oe):"*"==t?(k.marked="keyword",L(Oe)):";"==e?L(Oe):"}"==e?L():"@"==t?L(P,Oe):void 0}function Ne(e,t){return"?"==t?L(Ne):":"==e?L(oe,me):"="==t?L(F):S(Se)}function We(e,t){return"*"==t?(k.marked="keyword",L(Ie,H(";"))):"default"==t?(k.marked="keyword",L(P,H(";"))):"{"==e?L(J(De,"}"),Ie,H(";")):S(E)}function De(e,t){return"as"==t?(k.marked="keyword",L(H("variable"))):"variable"==e?S(F,De):void 0}function He(e){return"string"==e?L():"("==e?S(P):S(Ee,Pe,Ie)}function Ee(e,t){return"{"==e?ee(Ee,"}"):("variable"==e&&T(t),"*"==t&&(k.marked="keyword"),L(Fe))}function Pe(e){if(","==e)return L(Ee,Pe)}function Fe(e,t){if("as"==t)return k.marked="keyword",L(Ee)}function Ie(e,t){if("from"==t)return k.marked="keyword",L(P)}function ze(e){return"]"==e?L():S(J(F,"]"))}function Re(){return S(W("form"),pe,H("{"),W("}"),J(Be,"}"),D,D)}function Be(){return S(pe,me)}function je(e,t,n){return t.tokenize==g&&/^(?:operator|sof|keyword [bcd]|case|new|export|default|spread|[\[{}\(,;:]|=>)$/.test(t.lastType)||"quasi"==t.lastType&&/\{\s*$/.test(e.string.slice(0,e.pos-(n||0)))}return D.lex=!0,{startState:function(e){var t={tokenize:g,lastType:"sof",cc:[],lexical:new w((e||0)-o,0,"block",!1),localVars:n.localVars,context:n.localVars&&{vars:n.localVars},indented:e||0};return n.globalVars&&"object"==typeof n.globalVars&&(t.globalVars=n.globalVars),t},token:function(e,t){if(e.sol()&&(t.lexical.hasOwnProperty("align")||(t.lexical.align=!1),t.indented=e.indentation(),b(e,t)),t.tokenize!=m&&e.eatSpace())return null;var n=t.tokenize(e,t);return"comment"==r?n:(t.lastType="operator"!=r||"++"!=i&&"--"!=i?r:"incdec",function(e,t,n,r,i){var o=e.cc;for(k.state=e,k.stream=i,k.marked=null,k.cc=o,k.style=t,e.lexical.hasOwnProperty("align")||(e.lexical.align=!0);;){var l=o.length?o.pop():s?P:E;if(l(n,r)){for(;o.length&&o[o.length-1].lex;)o.pop()();return k.marked?k.marked:"variable"==n&&C(e,r)?"variable-2":t}}}(t,n,r,i,e))},indent:function(t,r){if(t.tokenize==m)return e.Pass;if(t.tokenize!=g)return 0;var i,a=r&&r.charAt(0),s=t.lexical;if(!/^\s*else\b/.test(r))for(var u=t.cc.length-1;u>=0;--u){var c=t.cc[u];if(c==D)s=s.prev;else if(c!=ye)break}for(;("stat"==s.type||"form"==s.type)&&("}"==a||(i=t.cc[t.cc.length-1])&&(i==B||i==j)&&!/^[,\.=+\-*:?[\(]/.test(r));)s=s.prev;l&&")"==s.type&&"stat"==s.prev.type&&(s=s.prev);var f=s.type,d=a==f;return"vardef"==f?s.indented+("operator"==t.lastType||","==t.lastType?s.info+1:0):"form"==f&&"{"==a?s.indented:"form"==f?s.indented+o:"stat"==f?s.indented+(function(e,t){return"operator"==e.lastType||","==e.lastType||h.test(t.charAt(0))||/[,.]/.test(t.charAt(0))}(t,r)?l||o:0):"switch"!=s.info||d||0==n.doubleIndentSwitch?s.align?s.column+(d?0:1):s.indented+(d?0:o):s.indented+(/^(?:case|default)\b/.test(r)?o:2*o)},electricInput:/^\s*(?:case .*?:|default:|\{|\})$/,blockCommentStart:s?null:"/*",blockCommentEnd:s?null:"*/",blockCommentContinue:s?null:" * ",lineComment:s?null:"//",fold:"brace",closeBrackets:"()[]{}''\"\"``",helperType:s?"json":"javascript",jsonldMode:a,jsonMode:s,expressionAllowed:je,skipExpression:function(e){var t=e.cc[e.cc.length-1];t!=P&&t!=F||e.cc.pop()}}}),e.registerHelper("wordChars","javascript",/[\w$]/),e.defineMIME("text/javascript","javascript"),e.defineMIME("text/ecmascript","javascript"),e.defineMIME("application/javascript","javascript"),e.defineMIME("application/x-javascript","javascript"),e.defineMIME("application/ecmascript","javascript"),e.defineMIME("application/json",{name:"javascript",json:!0}),e.defineMIME("application/x-json",{name:"javascript",json:!0}),e.defineMIME("application/ld+json",{name:"javascript",jsonld:!0}),e.defineMIME("text/typescript",{name:"javascript",typescript:!0}),e.defineMIME("application/typescript",{name:"javascript",typescript:!0})}(CodeMirror)}]); \ No newline at end of file diff --git a/_server/CodeMirror/codemirror.css b/_server/CodeMirror/codemirror.css new file mode 100644 index 00000000..c7a8ae70 --- /dev/null +++ b/_server/CodeMirror/codemirror.css @@ -0,0 +1,346 @@ +/* BASICS */ + +.CodeMirror { + /* Set height, width, borders, and global font properties here */ + font-family: monospace; + height: 300px; + color: black; + direction: ltr; +} + +/* PADDING */ + +.CodeMirror-lines { + padding: 4px 0; /* Vertical padding around content */ +} +.CodeMirror pre { + padding: 0 4px; /* Horizontal padding of content */ +} + +.CodeMirror-scrollbar-filler, .CodeMirror-gutter-filler { + background-color: white; /* The little square between H and V scrollbars */ +} + +/* GUTTER */ + +.CodeMirror-gutters { + border-right: 1px solid #ddd; + background-color: #f7f7f7; + white-space: nowrap; +} +.CodeMirror-linenumbers {} +.CodeMirror-linenumber { + padding: 0 3px 0 5px; + min-width: 20px; + text-align: right; + color: #999; + white-space: nowrap; +} + +.CodeMirror-guttermarker { color: black; } +.CodeMirror-guttermarker-subtle { color: #999; } + +/* CURSOR */ + +.CodeMirror-cursor { + border-left: 1px solid black; + border-right: none; + width: 0; +} +/* Shown when moving in bi-directional text */ +.CodeMirror div.CodeMirror-secondarycursor { + border-left: 1px solid silver; +} +.cm-fat-cursor .CodeMirror-cursor { + width: auto; + border: 0 !important; + background: #7e7; +} +.cm-fat-cursor div.CodeMirror-cursors { + z-index: 1; +} +.cm-fat-cursor-mark { + background-color: rgba(20, 255, 20, 0.5); + -webkit-animation: blink 1.06s steps(1) infinite; + -moz-animation: blink 1.06s steps(1) infinite; + animation: blink 1.06s steps(1) infinite; +} +.cm-animate-fat-cursor { + width: auto; + border: 0; + -webkit-animation: blink 1.06s steps(1) infinite; + -moz-animation: blink 1.06s steps(1) infinite; + animation: blink 1.06s steps(1) infinite; + background-color: #7e7; +} +@-moz-keyframes blink { + 0% {} + 50% { background-color: transparent; } + 100% {} +} +@-webkit-keyframes blink { + 0% {} + 50% { background-color: transparent; } + 100% {} +} +@keyframes blink { + 0% {} + 50% { background-color: transparent; } + 100% {} +} + +/* Can style cursor different in overwrite (non-insert) mode */ +.CodeMirror-overwrite .CodeMirror-cursor {} + +.cm-tab { display: inline-block; text-decoration: inherit; } + +.CodeMirror-rulers { + position: absolute; + left: 0; right: 0; top: -50px; bottom: -20px; + overflow: hidden; +} +.CodeMirror-ruler { + border-left: 1px solid #ccc; + top: 0; bottom: 0; + position: absolute; +} + +/* DEFAULT THEME */ + +.cm-s-default .cm-header {color: blue;} +.cm-s-default .cm-quote {color: #090;} +.cm-negative {color: #d44;} +.cm-positive {color: #292;} +.cm-header, .cm-strong {font-weight: bold;} +.cm-em {font-style: italic;} +.cm-link {text-decoration: underline;} +.cm-strikethrough {text-decoration: line-through;} + +.cm-s-default .cm-keyword {color: #708;} +.cm-s-default .cm-atom {color: #219;} +.cm-s-default .cm-number {color: #164;} +.cm-s-default .cm-def {color: #00f;} +.cm-s-default .cm-variable, +.cm-s-default .cm-punctuation, +.cm-s-default .cm-property, +.cm-s-default .cm-operator {} +.cm-s-default .cm-variable-2 {color: #05a;} +.cm-s-default .cm-variable-3, .cm-s-default .cm-type {color: #085;} +.cm-s-default .cm-comment {color: #a50;} +.cm-s-default .cm-string {color: #a11;} +.cm-s-default .cm-string-2 {color: #f50;} +.cm-s-default .cm-meta {color: #555;} +.cm-s-default .cm-qualifier {color: #555;} +.cm-s-default .cm-builtin {color: #30a;} +.cm-s-default .cm-bracket {color: #997;} +.cm-s-default .cm-tag {color: #170;} +.cm-s-default .cm-attribute {color: #00c;} +.cm-s-default .cm-hr {color: #999;} +.cm-s-default .cm-link {color: #00c;} + +.cm-s-default .cm-error {color: #f00;} +.cm-invalidchar {color: #f00;} + +.CodeMirror-composing { border-bottom: 2px solid; } + +/* Default styles for common addons */ + +div.CodeMirror span.CodeMirror-matchingbracket {color: #0b0;} +div.CodeMirror span.CodeMirror-nonmatchingbracket {color: #a22;} +.CodeMirror-matchingtag { background: rgba(255, 150, 0, .3); } +.CodeMirror-activeline-background {background: #e8f2ff;} + +/* STOP */ + +/* The rest of this file contains styles related to the mechanics of + the editor. You probably shouldn't touch them. */ + +.CodeMirror { + position: relative; + overflow: hidden; + background: white; +} + +.CodeMirror-scroll { + overflow: scroll !important; /* Things will break if this is overridden */ + /* 30px is the magic margin used to hide the element's real scrollbars */ + /* See overflow: hidden in .CodeMirror */ + margin-bottom: -30px; margin-right: -30px; + padding-bottom: 30px; + height: 100%; + outline: none; /* Prevent dragging from highlighting the element */ + position: relative; +} +.CodeMirror-sizer { + position: relative; + border-right: 30px solid transparent; +} + +/* The fake, visible scrollbars. Used to force redraw during scrolling + before actual scrolling happens, thus preventing shaking and + flickering artifacts. */ +.CodeMirror-vscrollbar, .CodeMirror-hscrollbar, .CodeMirror-scrollbar-filler, .CodeMirror-gutter-filler { + position: absolute; + z-index: 6; + display: none; +} +.CodeMirror-vscrollbar { + right: 0; top: 0; + overflow-x: hidden; + overflow-y: scroll; +} +.CodeMirror-hscrollbar { + bottom: 0; left: 0; + overflow-y: hidden; + overflow-x: scroll; +} +.CodeMirror-scrollbar-filler { + right: 0; bottom: 0; +} +.CodeMirror-gutter-filler { + left: 0; bottom: 0; +} + +.CodeMirror-gutters { + position: absolute; left: 0; top: 0; + min-height: 100%; + z-index: 3; +} +.CodeMirror-gutter { + white-space: normal; + height: 100%; + display: inline-block; + vertical-align: top; + margin-bottom: -30px; +} +.CodeMirror-gutter-wrapper { + position: absolute; + z-index: 4; + background: none !important; + border: none !important; +} +.CodeMirror-gutter-background { + position: absolute; + top: 0; bottom: 0; + z-index: 4; +} +.CodeMirror-gutter-elt { + position: absolute; + cursor: default; + z-index: 4; +} +.CodeMirror-gutter-wrapper ::selection { background-color: transparent } +.CodeMirror-gutter-wrapper ::-moz-selection { background-color: transparent } + +.CodeMirror-lines { + cursor: text; + min-height: 1px; /* prevents collapsing before first draw */ +} +.CodeMirror pre { + /* Reset some styles that the rest of the page might have set */ + -moz-border-radius: 0; -webkit-border-radius: 0; border-radius: 0; + border-width: 0; + background: transparent; + font-family: inherit; + font-size: inherit; + margin: 0; + white-space: pre; + word-wrap: normal; + line-height: inherit; + color: inherit; + z-index: 2; + position: relative; + overflow: visible; + -webkit-tap-highlight-color: transparent; + -webkit-font-variant-ligatures: contextual; + font-variant-ligatures: contextual; +} +.CodeMirror-wrap pre { + word-wrap: break-word; + white-space: pre-wrap; + word-break: normal; +} + +.CodeMirror-linebackground { + position: absolute; + left: 0; right: 0; top: 0; bottom: 0; + z-index: 0; +} + +.CodeMirror-linewidget { + position: relative; + z-index: 2; + padding: 0.1px; /* Force widget margins to stay inside of the container */ +} + +.CodeMirror-widget {} + +.CodeMirror-rtl pre { direction: rtl; } + +.CodeMirror-code { + outline: none; +} + +/* Force content-box sizing for the elements where we expect it */ +.CodeMirror-scroll, +.CodeMirror-sizer, +.CodeMirror-gutter, +.CodeMirror-gutters, +.CodeMirror-linenumber { + -moz-box-sizing: content-box; + box-sizing: content-box; +} + +.CodeMirror-measure { + position: absolute; + width: 100%; + height: 0; + overflow: hidden; + visibility: hidden; +} + +.CodeMirror-cursor { + position: absolute; + pointer-events: none; +} +.CodeMirror-measure pre { position: static; } + +div.CodeMirror-cursors { + visibility: hidden; + position: relative; + z-index: 3; +} +div.CodeMirror-dragcursors { + visibility: visible; +} + +.CodeMirror-focused div.CodeMirror-cursors { + visibility: visible; +} + +.CodeMirror-selected { background: #d9d9d9; } +.CodeMirror-focused .CodeMirror-selected { background: #d7d4f0; } +.CodeMirror-crosshair { cursor: crosshair; } +.CodeMirror-line::selection, .CodeMirror-line > span::selection, .CodeMirror-line > span > span::selection { background: #d7d4f0; } +.CodeMirror-line::-moz-selection, .CodeMirror-line > span::-moz-selection, .CodeMirror-line > span > span::-moz-selection { background: #d7d4f0; } + +.cm-searching { + background-color: #ffa; + background-color: rgba(255, 255, 0, .4); +} + +/* Used to force a border model for a node */ +.cm-force-border { padding-right: .1px; } + +@media print { + /* Hide the cursor when printing */ + .CodeMirror div.CodeMirror-cursors { + visibility: hidden; + } +} + +/* See issue #2901 */ +.cm-tab-wrap-hack:after { content: ''; } + +/* Help users use markselection to safely style text background */ +span.CodeMirror-selectedtext { background: none; } diff --git a/_server/css/editor_mode.css b/_server/css/editor_mode.css index 6a107f64..f5ffcdab 100644 --- a/_server/css/editor_mode.css +++ b/_server/css/editor_mode.css @@ -50,6 +50,17 @@ height: 780px; } +#left6 #blocklyDiv {height: 480px; width: 940px;float:left;} +#left6 #codeArea {width: 99.5%; height: 15.4em;overflow:y;/* resize:none; */clear:both;} +#left6 #multiLineDiv {height: 440px; width: 375px;float:left;} +#left6 #multiLineDiv .CodeMirror { + /* border-top: 1px solid black; + border-bottom: 1px solid black; */ + border: 1px solid #eee; + height: 438px; + width: 373px; +} + .etable table, .etable table td { color: #000; diff --git a/_server/editor_blockly.js b/_server/editor_blockly.js index dee70dae..cfde9348 100644 --- a/_server/editor_blockly.js +++ b/_server/editor_blockly.js @@ -340,6 +340,29 @@ editor_blockly.confirm = function (){ setvalue(JSON.stringify(obj)); } +var codeEditor = CodeMirror.fromTextArea(document.getElementById("multiLineCode"), { + lineNumbers: true, + matchBrackets: true, + lineWrapping: true, + continueComments: "Enter", + extraKeys: {"Ctrl-Q": "toggleComment"} +}); + +var multiLineArgs=[null,null,null]; +editor_blockly.multiLineEdit = function(value,b,f,callback){ + document.getElementById("multiLineDiv").style.display=''; + codeEditor.setValue(value.split('\\n').join('\n')||''); + multiLineArgs[0]=b; + multiLineArgs[1]=f; + multiLineArgs[2]=callback; +} +editor_blockly.multiLineDone = function(){ + document.getElementById("multiLineDiv").style.display='none'; + if(!multiLineArgs[0] || !multiLineArgs[1] || !multiLineArgs[2])return; + var newvalue = codeEditor.getValue()||''; + multiLineArgs[2](newvalue,multiLineArgs[0],multiLineArgs[1]) +} + editor_blockly.doubleClickBlock = function (blockId){ var b=editor_blockly.workspace.getBlockById(blockId); console.log(b); @@ -349,11 +372,14 @@ editor_blockly.doubleClickBlock = function (blockId){ 'choices_s':'EvalString_0', 'function_s':'RawEvalString_0', } - var f=textStringDict[b]; + var f=textStringDict[b.type]; if(f){ var value = b.getFieldValue(f); //多行编辑 - //func(value,function(newvalue,b,f){b.setFieldValue(newvalue,f);}) + editor_blockly.multiLineEdit(value,b,f,function(newvalue,b,f){ + if(textStringDict[b.type]!=='RawEvalString_0'){} + b.setFieldValue(newvalue.split('\n').join('\\n'),f); + }); } } diff --git a/editor.html b/editor.html index 7c2c5599..8c1518cc 100644 --- a/editor.html +++ b/editor.html @@ -3,6 +3,7 @@ + @@ -135,8 +136,12 @@
-
- +
+ +
@@ -357,6 +362,7 @@ editor.init(function(){ + From cdff0e8abdd523bfc3b3139fa0919ea0af2a5ba1 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sun, 18 Feb 2018 18:37:39 +0800 Subject: [PATCH 033/102] =?UTF-8?q?=E4=BF=AE=E5=A4=8D=E4=BA=86=E6=B7=BB?= =?UTF-8?q?=E5=8A=A0=E7=89=A9=E5=93=81=E6=80=AA=E7=89=A9=E7=9A=84=E6=96=B0?= =?UTF-8?q?id=E6=97=B6,=E6=B2=A1=E6=9C=89=E6=B7=BB=E5=8A=A0items.js?= =?UTF-8?q?=E6=88=96enemys.js=E4=B8=AD=E6=95=B0=E6=8D=AE=E7=9A=84bug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/editor_file.js | 30 ++++++++++++++++++++++++++++-- _server/editor_mode.js | 4 ++++ project/comment.js | 7 +++++-- 3 files changed, 37 insertions(+), 4 deletions(-) diff --git a/_server/editor_file.js b/_server/editor_file.js index 520fdb7a..01bb0323 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -149,6 +149,12 @@ } saveSetting('maps',[["add","['"+idnum+"']",{'cls': info.images, 'id':id}]],tempcallback); saveSetting('icons',[["add","['"+info.images+"']['"+id+"']",info.y]],tempcallback); + if(info.images==='items'){ + saveSetting('items',[["change"/*其实应该是add*/,"['items']['"+id+"']",editor_file.comment.items_template]],function(err){if(err)throw(err)}); + } + if(info.images==='enemys'){ + saveSetting('enemys',[["change"/*其实应该是add*/,"['enemys']['"+id+"']",editor_file.comment.enemys_template]],function(err){if(err)throw(err)}); + } callback(null); } @@ -169,13 +175,33 @@ }); saveSetting('items',actionList,function (err) { callback([ - {'items':editor.core.items.items[id],'itemEffect':editor.core.items.itemEffect[id],'itemEffectTip':editor.core.items.itemEffectTip[id]}, + {'items':(function(){ + var locObj={}; + Object.keys(editor_file.comment.items.items).forEach(function(v){ + if (isset(editor.core.items.items[id][v])) + locObj[v]=editor.core.items.items[id][v]; + else + locObj[v]=null; + }); + return locObj; + })(), + 'itemEffect':editor.core.items.itemEffect[id],'itemEffectTip':editor.core.items.itemEffectTip[id]}, editor_file.comment.items, err]); }); } else { callback([ - {'items':editor.core.items.items[id],'itemEffect':editor.core.items.itemEffect[id],'itemEffectTip':editor.core.items.itemEffectTip[id]}, + {'items':(function(){ + var locObj={}; + Object.keys(editor_file.comment.items.items).forEach(function(v){ + if (isset(editor.core.items.items[id][v])) + locObj[v]=editor.core.items.items[id][v]; + else + locObj[v]=null; + }); + return locObj; + })(), + 'itemEffect':editor.core.items.itemEffect[id],'itemEffectTip':editor.core.items.itemEffectTip[id]}, editor_file.comment.items, null]); } diff --git a/_server/editor_mode.js b/_server/editor_mode.js index f21f93b2..101dba81 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -59,6 +59,10 @@ editor_mode.prototype.objToTable = function(obj,commentObj){ editor_mode.onmode(editor_mode._ids[node.getAttribute('id')]); editor_mode.addAction(['change',field,JSON.parse(input.value)]); //尚未完成,不完善,目前还没做$range的检查 + + /*临时*/editor_mode.onmode('');/*临时*/ + //临时改为立刻写入文件,删去此句的时,切换模式才会真正写入 + //现阶段这样会更实用,20180218 } input.ondblclick = function(){ editor_blockly.import(guid); diff --git a/project/comment.js b/project/comment.js index af33e2bd..545b6af8 100644 --- a/project/comment.js +++ b/project/comment.js @@ -10,6 +10,7 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = 'itemEffect':'cls为items的即捡即用类物品的效果,执行时会对这里的字符串执行eval()', 'itemEffectTip':'cls为items的即捡即用类物品,在获得时左上角额外显示的文字,执行时会对这里的字符串执行eval()得到字符串' }, + "items_template" : {'cls': 'items', 'name': '新物品'}, "enemys" : { 'name': '名称', 'hp': '生命值', @@ -25,6 +26,7 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = 'point': 'point可以在打败怪物后进行加点,详见文档说明\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', 'n': '多连击需要在后面指定n代表是几连击\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', }, + "enemys_template" : {'name': '新敌人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, "floors" : { 'floor' : { "floorId": "文件名和floorId需要保持完全一致 \n楼层唯一标识符仅能由字母、数字、下划线组成,且不能由数字开头 \n推荐用法:第20层就用MT20,第38层就用MT38,地下6层就用MT_6(用下划线代替负号),隐藏3层用MT3h(h表示隐藏),等等 \n楼层唯一标识符,需要和名字完全一致 \n这里不能更改floorId,请通过另存为来实现\n$range(false)$end", @@ -44,11 +46,12 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "changeFloor": "楼层转换事件;该事件不能和上面的events有冲突(同位置点),否则会被覆盖 \n$leaf(true)$end", "afterBattle": "战斗后可能触发的事件列表 \n$leaf(true)$end", "afterGetItem": "获得道具后可能触发的事件列表 \n$leaf(true)$end", - "afterOpenDoor": "开完门后可能触发的事件列表 \n$leaf(true)$end" + "afterOpenDoor": "开完门后可能触发的事件列表 \n$leaf(true)$end", + "cannotMove": "每个图块不可通行的方向 \n 可以在这里定义每个点不能前往哪个方向,例如悬崖边不能跳下去 \n'x,y': ['up', 'left'], // (x,y)点不能往上和左走\n$leaf(true)$end", } }, /* - 'template' : { + 'floors_template' : { "floorId": "tempfloor", "title": "主塔 0 层", "name": "0", From d003dbf84bad5a2a5978360fa5d99f74622db8aa Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Mon, 19 Feb 2018 10:26:23 +0800 Subject: [PATCH 034/102] =?UTF-8?q?editor:=E4=BF=AE=E6=94=B9=E6=88=90?= =?UTF-8?q?=E5=8A=9F=E6=88=96=E5=A4=B1=E8=B4=A5=E4=BC=9A=E6=9C=89=E7=9B=B8?= =?UTF-8?q?=E5=BA=94=E7=9A=84=E6=8F=90=E7=A4=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 不再时只是throw错误 --- _server/editor_blockly.js | 6 +++--- _server/editor_file.js | 26 +++++++++++++------------- _server/editor_mode.js | 22 ++++++++++++---------- _server/vm.js | 12 ++++++++++++ editor.html | 2 +- 5 files changed, 41 insertions(+), 27 deletions(-) diff --git a/_server/editor_blockly.js b/_server/editor_blockly.js index cfde9348..38938295 100644 --- a/_server/editor_blockly.js +++ b/_server/editor_blockly.js @@ -226,15 +226,15 @@ initscript=String.raw` var input_=''; editor_blockly.runOne = function (){ //var printf = console.log; - var printf = function(){}; + //var printf = function(){}; var grammerFile = input_; converter = new Converter().init(); converter.generBlocks(grammerFile,[]); - printf(converter.blocks); + //printf(converter.blocks); converter.renderGrammerName(); converter.generToolbox(); converter.generMainFile(); - printf(converter.mainFile.join('')); + //printf(converter.mainFile.join('')); console.log(converter); diff --git a/_server/editor_file.js b/_server/editor_file.js index 01bb0323..e66c722f 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -29,7 +29,7 @@ editor_file.getFloorFileList = function(editor,callback){ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; /* var fs = editor.fs; fs.readdir('project/floors',function(err, data){ callback([data,err]); @@ -39,7 +39,7 @@ //callback([Array,err:String]) editor_file.loadFloorFile = function(editor,filename,callback){ //filename不含'/'不含'.js' - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; /* var fs = editor.fs; fs.readFile('project/floors/'+filename+'.js','utf-8',function(err, data){ if (err!=null){callback(err);return;} @@ -64,7 +64,7 @@ } //callback(err:String) editor_file.saveFloorFile = function(editor,callback){ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; /* if (!isset(editor.currentFloorId) || !isset(editor.currentFloorData)) { callback('未选中文件或无数据'); } */ @@ -87,7 +87,7 @@ //callback(err:String) editor_file.saveFloorFileAs = function(editor,saveAsFilename,callback){ //saveAsFilename不含'/'不含'.js' - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; if (!isset(editor.currentFloorData)) { callback('无数据'); } @@ -102,7 +102,7 @@ //////////////////////////////////////////////////////////////////// editor_file.changeIdAndIdnum = function(editor,id,idnum,info,callback){ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; //检查maps中是否有重复的idnum或id var change = -1; for(var ii in editor.core.maps.blocksInfo){ @@ -150,10 +150,10 @@ saveSetting('maps',[["add","['"+idnum+"']",{'cls': info.images, 'id':id}]],tempcallback); saveSetting('icons',[["add","['"+info.images+"']['"+id+"']",info.y]],tempcallback); if(info.images==='items'){ - saveSetting('items',[["change"/*其实应该是add*/,"['items']['"+id+"']",editor_file.comment.items_template]],function(err){if(err)throw(err)}); + saveSetting('items',[["change"/*其实应该是add*/,"['items']['"+id+"']",editor_file.comment.items_template]],function(err){if(err){printe(err);throw(err)}}); } if(info.images==='enemys'){ - saveSetting('enemys',[["change"/*其实应该是add*/,"['enemys']['"+id+"']",editor_file.comment.enemys_template]],function(err){if(err)throw(err)}); + saveSetting('enemys',[["change"/*其实应该是add*/,"['enemys']['"+id+"']",editor_file.comment.enemys_template]],function(err){if(err){printe(err);throw(err)}}); } callback(null); @@ -167,7 +167,7 @@ ] 为[]时只查询不修改 */ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; if (isset(actionList) && actionList.length > 0){ actionList.forEach(function (value) { var tempindex = value[1].indexOf(']')+1; @@ -216,7 +216,7 @@ ] 为[]时只查询不修改 */ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; if (isset(actionList) && actionList.length > 0){ actionList.forEach(function (value) { value[1] = "['"+id+"']"+value[1]; @@ -263,7 +263,7 @@ ] 为[]时只查询不修改 */ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; if (isset(actionList) && actionList.length > 0){ actionList.forEach(function (value) { value[1] = value[1]+"['"+x+","+y+"']"; @@ -311,7 +311,7 @@ ] 为[]时只查询不修改 */ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; if (isset(actionList) && actionList.length > 0){ saveSetting('floors',actionList,function (err) { callback([ @@ -355,7 +355,7 @@ ] 为[]时只查询不修改 */ - if (!isset(callback)) throw('未设置callback'); + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; if (isset(actionList) && actionList.length > 0){ saveSetting('data',actionList,function (err) { callback([ @@ -421,7 +421,7 @@ console.log(file); console.log(actionList); actionList.forEach(function (value) { - if (value[0]!='change' && file!='icons' && file!='maps') throw('目前只支持change'); + if (value[0]!='change' && file!='icons' && file!='maps') {printe('目前只支持change');throw('目前只支持change')}; }); if (file=='icons') { diff --git a/_server/editor_mode.js b/_server/editor_mode.js index 101dba81..4bbe60af 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -145,23 +145,23 @@ editor_mode.prototype.doActionList = function(mode,actionList){ switch (mode) { case 'loc': - editor_file.editLoc(editor,editor_mode.pos.x,editor_mode.pos.y,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + editor_file.editLoc(editor,editor_mode.pos.x,editor_mode.pos.y,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])};printf('修改成功')}); break; case 'emenyitem': if (editor_mode.info.images=='enemys'){ - editor_file.editEnemy(editor,editor_mode.info.id,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + editor_file.editEnemy(editor,editor_mode.info.id,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])};printf('修改成功')}); } else if (editor_mode.info.images=='items'){ - editor_file.editItem(editor,editor_mode.info.id,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + editor_file.editItem(editor,editor_mode.info.id,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])};printf('修改成功')}); } break; case 'floor': - editor_file.editFloor(editor,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + editor_file.editFloor(editor,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])};printf('修改成功')}); break; case 'tower': - editor.file.editTower(editor,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + editor.file.editTower(editor,actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])};printf('修改成功')}); break; default: break; @@ -249,10 +249,12 @@ editor_mode.prototype.listen = function(callback){ if (newIdIdnum.children[0].value && newIdIdnum.children[1].value){ var id = newIdIdnum.children[0].value; var idnum = parseInt(newIdIdnum.children[1].value); - editor_file.changeIdAndIdnum(editor,id,idnum,editor_mode.info,function(err){if(err)throw(err)}); + editor_file.changeIdAndIdnum(editor,id,idnum,editor_mode.info,function(err){ + if(err){printe(err);throw(err)} + printf('添加id的idnum成功'); + }); } } - //尚未完成,不完善,新物品需要手动改items,新地形的支持不错 var selectFloor = document.getElementById('selectFloor'); editor_file.getFloorFileList(editor,function(floors){ @@ -271,7 +273,7 @@ editor_mode.prototype.listen = function(callback){ var saveFloor = document.getElementById('saveFloor'); saveFloor.onclick = function(){ editor_mode.onmode(''); - editor_file.saveFloorFile(editor,function(err){if(err)throw(err)}); + editor_file.saveFloorFile(editor,function(err){if(err){printe(err);throw(err)}}); } var saveFloorAs = document.getElementById('saveFloorAs'); @@ -280,9 +282,9 @@ editor_mode.prototype.listen = function(callback){ if (!saveAsName.value)return; editor_mode.onmode(''); editor_file.saveFloorFileAs(editor,saveAsName.value,function(err){ - if(err)throw(err); + if(err){printe(err);throw(err)} core.floorIds.push(saveAsName.value); - editor.file.editTower(editor,[['change',"['main']['floorIds']",core.floorIds]],function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null)throw(objs_.slice(-1)[0])}); + editor.file.editTower(editor,[['change',"['main']['floorIds']",core.floorIds]],function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])}}); }); } diff --git a/_server/vm.js b/_server/vm.js index 8b227a19..a034eaf6 100644 --- a/_server/vm.js +++ b/_server/vm.js @@ -184,6 +184,16 @@ var clear = new Vue({ } } }) +printf = function(str_,type) { + if(!type){ + tip.msgs[11]=String(str_); + tip.whichShow=12; + } else { + tip.msgs[10]=String(str_); + tip.whichShow=11; + } +} +printe = function(str_){printf(str_,'error')} var tip = new Vue({ el: '#tip', data: { @@ -205,6 +215,8 @@ var tip = new Vue({ "修改成功!可点击复制按钮复制地图数组到剪切板", "选择背景图片失败!文件名格式错误或图片不存在!", "更新背景图片成功!", + "11:警告", + "12:成功" ], mapMsg: '', whichShow: 0, diff --git a/editor.html b/editor.html index 8c1518cc..e408332d 100644 --- a/editor.html +++ b/editor.html @@ -327,7 +327,7 @@ diff --git a/libs/core.js b/libs/core.js index 30de90c1..fc595cc4 100644 --- a/libs/core.js +++ b/libs/core.js @@ -151,7 +151,7 @@ function core() { /////////// 系统事件相关 /////////// ////// 初始化 ////// -core.prototype.init = function (coreData) { +core.prototype.init = function (coreData, callback) { for (var key in coreData) { core[key] = coreData[key]; } @@ -281,6 +281,9 @@ core.prototype.init = function (coreData) { core.material.icons.hero.height = core.material.images.hero.height/4; core.setRequestAnimationFrame(); core.showStartAnimate(); + + if (core.isset(callback)) callback(); + }); } diff --git a/libs/items.js b/libs/items.js index df582f25..cc16999a 100644 --- a/libs/items.js +++ b/libs/items.js @@ -41,6 +41,7 @@ items.prototype.getItemEffect = function(itemId, itemNum) { var itemCls = core.material.items[itemId].cls; // 消耗品 if (itemCls === 'items') { + var ratio = parseInt(core.floors[core.status.floorId].item_ratio) || 1; if (itemId in this.itemEffect)eval(this.itemEffect[itemId]); } else { @@ -50,6 +51,7 @@ items.prototype.getItemEffect = function(itemId, itemNum) { ////// “即捡即用类”道具的文字提示 ////// items.prototype.getItemEffectTip = function(itemId) { + var ratio = parseInt(core.floors[core.status.floorId].item_ratio) || 1; if (itemId in this.itemEffectTip && (!this.items[itemId].isEquipment || !core.flags.equipment)) { return eval(this.itemEffectTip[itemId]); } diff --git a/main.js b/main.js index 06887014..693472b1 100644 --- a/main.js +++ b/main.js @@ -109,7 +109,7 @@ function main() { this.canvas = {}; } -main.prototype.init = function (mode) { +main.prototype.init = function (mode, callback) { for (var i = 0; i < main.dom.gameCanvas.length; i++) { main.canvas[main.dom.gameCanvas[i].id] = main.dom.gameCanvas[i].getContext('2d'); } @@ -155,7 +155,7 @@ main.prototype.init = function (mode) { "animates", "bgms", "sounds", "floorIds", "floors"].forEach(function (t) { coreData[t] = main[t]; }) - main.core.init(coreData); + main.core.init(coreData, callback); main.core.resize(main.dom.body.clientWidth, main.dom.body.clientHeight); }); }); diff --git a/project/comment.js b/project/comment.js index 12267989..4bf4c47e 100644 --- a/project/comment.js +++ b/project/comment.js @@ -43,6 +43,7 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "weather": "该层的默认天气。本项可忽略表示晴天,如果写则第一项为\"rain\"或\"snow\"代表雨雪,第二项为1-10之间的数代表强度。 \n$leaf(true)$end", "bgm": "到达该层后默认播放的BGM。本项可忽略。 ", //"map": "地图数据,需要是13x13,建议使用地图生成器来生成 ", + "item_ratio": "每一层的宝石/血瓶效果,即获得宝石和血瓶时框内\"ratio\"的值。", "firstArrive": "第一次到该楼层触发的事件 \n$leaf(true)$end", }, 'loc' : { diff --git a/project/floors/MT0.js b/project/floors/MT0.js index 1c51393b..dc4996fe 100644 --- a/project/floors/MT0.js +++ b/project/floors/MT0.js @@ -13,6 +13,7 @@ main.floors.MT0 = // "color": [0,0,0,0.3], // 该层的默认画面色调。本项可不写(代表无色调),如果写需要是一个RGBA数组。 // "weather": ["snow",5], // 该层的默认天气。本项可忽略表示晴天,如果写则第一项为"rain"或"snow"代表雨雪,第二项为1-10之间的数代表强度。 // "bgm": "bgm.mp3", // 到达该层后默认播放的BGM。本项可忽略。 + "item_ratio": 1, // 该层的宝石/血瓶倍率 "map": [ // 地图数据,需要是13x13,建议使用地图生成器来生成 ], diff --git a/project/floors/sample0.js b/project/floors/sample0.js index 3cbd4a72..d5815cc9 100644 --- a/project/floors/sample0.js +++ b/project/floors/sample0.js @@ -13,6 +13,7 @@ main.floors.sample0 = // "color": [0,0,0,0.3] // 该层的默认画面色调。本项可不写(代表无色调),如果写需要是一个RGBA数组。 // "weather": ["snow",5], // 该层的默认天气。本项可忽略表示晴天,如果写则第一项为"rain"或"snow"代表雨雪,第二项为1-10之间的数代表强度。 "bgm": "bgm.mp3", // 到达该层后默认播放的BGM。本项可忽略。 + "item_ratio": 2, // 该层的宝石/血瓶倍率 "map": [ // 地图数据,需要是13x13,建议使用地图生成器来生成 [0, 0, 220, 0, 0, 20, 87, 3, 65, 64, 44, 43, 42], [0, 246, 0, 246, 0, 20, 0, 3, 58, 59, 60, 61, 41], diff --git a/project/floors/sample1.js b/project/floors/sample1.js index 8764489d..08ce590e 100644 --- a/project/floors/sample1.js +++ b/project/floors/sample1.js @@ -13,6 +13,7 @@ main.floors.sample1 = // "color": [0,0,0,0.3] // 该层的默认画面色调。本项可不写(代表无色调),如果写需要是一个RGBA数组。 "weather": ["snow",6], // 该层的默认天气。本项可忽略表示晴天,如果写则第一项为"rain"或"snow"代表雨雪,第二项为1-10之间的数代表强度。 // "bgm": "bgm.mp3", // 到达该层后默认播放的BGM。本项可忽略。 + "item_ratio": 1, // 该层的宝石/血瓶倍率 "map": [ // 地图数据,需要是13x13,建议使用地图生成器来生成 [7, 131, 8, 152, 9, 130, 10, 152, 166, 165, 132, 165, 166], [0, 0, 0, 0, 0, 0, 0, 152, 165, 164, 0, 162, 165], diff --git a/project/floors/sample2.js b/project/floors/sample2.js index 4b496b83..233473a0 100644 --- a/project/floors/sample2.js +++ b/project/floors/sample2.js @@ -13,6 +13,7 @@ main.floors.sample2 = "color": [255,0,0,0.3], // 该层的默认画面色调。本项可不写(代表无色调),如果写需要是一个RGBA数组。 "weather": ["rain",10], // 该层的默认天气。本项可忽略表示晴天,如果写则第一项为"rain"或"snow"代表雨雪,第二项为1-10之间的数代表强度。 "bgm": "qianjin.mid", // 到达该层后默认播放的BGM。本项可忽略。 + "item_ratio": 1, // 该层的宝石/血瓶倍率 "map": [ // 地图数据,需要是13x13,建议使用地图生成器来生成 [5, 5, 5, 5, 5, 5, 87, 5, 5, 5, 5, 5, 5], [5, 4, 4, 4, 4, 1, 0, 1, 4, 4, 4, 4, 5], diff --git a/project/floors/test.js b/project/floors/test.js deleted file mode 100644 index e2452d33..00000000 --- a/project/floors/test.js +++ /dev/null @@ -1,46 +0,0 @@ -main.floors.test = -{ - "floorId": "test", // 这里需要改楼层名,请和文件名及下面的floorId保持完全一致 - // 楼层唯一标识符仅能由字母、数字、下划线组成,且不能由数字开头 - // 推荐用法:第20层就用MT20,第38层就用MT38,地下6层就用MT_6(用下划线代替负号),隐藏3层用MT3h(h表示隐藏),等等 - // 楼层唯一标识符,需要和名字完全一致 - "title": "test", // 楼层中文名 - "name": "", // 显示在状态栏中的层数 - "canFlyTo": true, // 该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) - "canUseQuickShop": true, // 该层是否允许使用快捷商店 - "defaultGround": "ground", // 默认地面的图块ID(terrains中) - "map": [ // 地图数据,需要是13x13,建议使用地图生成器来生成 - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201,201,201,201,201,201,201,201], - [201,201,201,201,201,201, 45,201,201,201,201,201,201], - [201,201,201,201,201,201, 0,201,201,201,201,201,201] - ], - "firstArrive": [ // 第一次到该楼层触发的事件 - - ], - "events": { // 该楼的所有可能事件列表 - - }, - "changeFloor": { // 楼层转换事件;该事件不能和上面的events有冲突(同位置点),否则会被覆盖 - - }, - "afterBattle": { // 战斗后可能触发的事件列表 - - }, - "afterGetItem": { // 获得道具后可能触发的事件列表 - - }, - "afterOpenDoor": { // 开完门后可能触发的事件列表 - - } -} - diff --git a/project/items.js b/project/items.js index 84bbcbf7..b68555f5 100644 --- a/project/items.js +++ b/project/items.js @@ -62,16 +62,16 @@ items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a = "itemEffect" : { - "redJewel":"core.status.hero.atk += core.values.redJewel", - "blueJewel":"core.status.hero.def += core.values.blueJewel", - "greenJewel":"core.status.hero.mdef += core.values.greenJewel", + "redJewel":"core.status.hero.atk += core.values.redJewel * ratio", + "blueJewel":"core.status.hero.def += core.values.blueJewel * ratio", + "greenJewel":"core.status.hero.mdef += core.values.greenJewel * ratio", "yellowJewel":"core.status.hero.hp+=1000;core.status.hero.atk+=6;core.status.hero.def+=6;core.status.hero.mdef+=10;", // 黄宝石属性:需自己定义 - "redPotion":"core.status.hero.hp += core.values.redPotion", - "bluePotion":"core.status.hero.hp += core.values.bluePotion", - "yellowPotion":"core.status.hero.hp += core.values.yellowPotion", - "greenPotion":"core.status.hero.hp += core.values.greenPotion", + "redPotion":"core.status.hero.hp += core.values.redPotion * ratio", + "bluePotion":"core.status.hero.hp += core.values.bluePotion * ratio", + "yellowPotion":"core.status.hero.hp += core.values.yellowPotion * ratio", + "greenPotion":"core.status.hero.hp += core.values.greenPotion * ratio", "sword1":"core.status.hero.atk += core.values.sword1", "sword2":"core.status.hero.atk += core.values.sword2", "sword3":"core.status.hero.atk += core.values.sword3", @@ -91,14 +91,14 @@ items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a = "itemEffectTip" : { - "redJewel":"',攻击+'+core.values.redJewel", - "blueJewel":"',防御+'+core.values.blueJewel", - "greenJewel":"',魔防+'+core.values.greenJewel", + "redJewel":"',攻击+'+core.values.redJewel * ratio", + "blueJewel":"',防御+'+core.values.blueJewel * ratio", + "greenJewel":"',魔防+'+core.values.greenJewel * ratio", "yellowJewel":"',全属性提升'", - "redPotion":"',生命+'+core.values.redPotion", - "bluePotion":"',生命+'+core.values.bluePotion", - "yellowPotion":"',生命+'+core.values.yellowPotion", - "greenPotion":"',生命+'+core.values.greenPotion", + "redPotion":"',生命+'+core.values.redPotion * ratio", + "bluePotion":"',生命+'+core.values.bluePotion * ratio", + "yellowPotion":"',生命+'+core.values.yellowPotion * ratio", + "greenPotion":"',生命+'+core.values.greenPotion * ratio", "sword1":"',攻击+'+core.values.sword1", "sword2":"',攻击+'+core.values.sword2", "sword3":"',攻击+'+core.values.sword3", From 39db1cd2352b70179cef817220365e403aac0f5f Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Wed, 7 Mar 2018 17:35:15 +0800 Subject: [PATCH 060/102] =?UTF-8?q?blockly=E6=94=B9=E4=B8=BA=E5=BC=B9?= =?UTF-8?q?=E7=AA=97?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/README.md | 91 +++++++++++++++++++++++++++++++++++++ _server/css/editor_mode.css | 6 ++- _server/editor_blockly.js | 19 ++++++-- _server/editor_mode.js | 1 + editor.html | 6 ++- 5 files changed, 117 insertions(+), 6 deletions(-) create mode 100644 _server/README.md diff --git a/_server/README.md b/_server/README.md new file mode 100644 index 00000000..9f9a2475 --- /dev/null +++ b/_server/README.md @@ -0,0 +1,91 @@ +# editor + +本目录下所有文件,以及`../editor.html`和`../启动服务.exe`([源码](http://github.com/ckcz123/mota-js-server/))是地图编辑器的所有组件. + +`editor.js`,`editor_file.js`和`editor_mode.js`耦合较强,`editor_blockly.js`和`fs.js`基本可以独立使用. + +## 各组件功能 + +### editor.js + +暂略 + +### editor_file.js +提供了以下函数进行楼层`map`数组相关的操作 +```javascript +editor.file.getFloorFileList +editor.file.loadFloorFile +editor.file.saveFloorFile +editor.file.saveFloorFileAs +``` +5个编辑模式有关的查询 +```javascript +editor.file.editItem('redJewel',[],function(a){console.log(a)}); +editor.file.editEnemy('redBat',[],function(a){console.log(a)}); +editor.file.editLoc(2,0,[],function(a){console.log(a)}); +editor.file.editFloor([],function(a){console.log(a)}); +editor.file.editTower([],function(a){console.log(a)}); +``` +5个编辑模式有关的编辑 +```javascript +editor.info={images: "terrains", y: 9}; +editor.file.changeIdAndIdnum('yellowWall2',16,editor.info,function(a){console.log(a)}); +editor.file.editItem('book',[["change","['items']['name']","怪物手册的新名字"]],function(a){console.log(a)}); +editor.file.editEnemy('redBat',[['change',"['atk']",20]],function(a){console.log(a)}); +editor.file.editLoc(2,6,[["change","['afterBattle']",null]],function(a){console.log(a)}); +editor.file.editFloor([["change","['title']",'样板 33 层']],function(a){console.log(a)}); +editor.file.editTower([["change","['values']['lavaDamage']",200]],function(a){console.log(a)}); +``` + +### editor_mode.js +4个生成表格并绑定事件的函数 +```javascript +editor.mode.loc(); +editor.mode.emenyitem(); +editor.mode.floor(); +editor.mode.tower(); +``` +切换模式 +```javascript +editor.mode.onmode(''); +editor.mode.onmode('loc'); +editor.mode.onmode('emenyitem'); +editor.mode.onmode('floor'); +editor.mode.onmode('tower'); +``` +在切换模式时,改动才会保存到文件,并且需要刷新页面使得`editor`能看到改动 + +表格的`onchange`的实现中,获得当前模式的方式.不注意的话,修改`index.html`中页面的结构,会被坑 +```javascript +var node = thisTr.parentNode; +while (!editor_mode._ids.hasOwnProperty(node.getAttribute('id'))) { + node = node.parentNode; +} +editor_mode.onmode(editor_mode._ids[node.getAttribute('id')]); +``` +### editor_blockly.js +把选定`id_`的事件用blockly编辑 +``` js +editor_blockly.import(id_); +``` +把文本区域的代码转换成图块 +``` js +editor_blockly.parse(); +``` +把当前图块对应的事件返回给调用blockly的`id_` +``` js +editor_blockly.confirm(); +``` + +### 待调整 + +多行文本编辑器独立作为组件 +editor_multi.js + +## z-index + +目前主体部分使用了 0,75,100 + +暂定blockly使用 200 ,多行文本编辑器使用 300 + +完成后再调整 \ No newline at end of file diff --git a/_server/css/editor_mode.css b/_server/css/editor_mode.css index a3c232c9..724bb347 100644 --- a/_server/css/editor_mode.css +++ b/_server/css/editor_mode.css @@ -45,7 +45,11 @@ #left6 { left: 5px; - top: 1930px; + /* top: 1930px; */ + top: 5px; + z-index: 200; + position: fixed; + background-color: rgb(245, 245, 245); width: 1335px; height: 780px; } diff --git a/_server/editor_blockly.js b/_server/editor_blockly.js index 91a15c61..dbe164d4 100644 --- a/_server/editor_blockly.js +++ b/_server/editor_blockly.js @@ -327,7 +327,13 @@ editor_blockly.import = function(id_){ editor_blockly.show(); } -editor_blockly.show = function(){} +editor_blockly.show = function(){document.getElementById('left6').style='';} +editor_blockly.hide = function(){document.getElementById('left6').style='z-index:-1;opacity: 0;';} + +editor_blockly.cancel = function(){ + editor_blockly.id=''; + editor_blockly.hide(); +} editor_blockly.confirm = function (){ if(!editor_blockly.id){ @@ -339,6 +345,7 @@ editor_blockly.confirm = function (){ editor_blockly.id=''; var input = thisTr.children[2].children[0].children[0]; input.value = value; + editor_blockly.hide(); input.onchange(); } if(document.getElementById('codeArea').value===''){ @@ -357,21 +364,27 @@ var codeEditor = CodeMirror.fromTextArea(document.getElementById("multiLineCode" continueComments: "Enter", extraKeys: {"Ctrl-Q": "toggleComment"} }); +editor_blockly.showCodeEditor = function(){document.getElementById("multiLineDiv").style='';} +editor_blockly.hideCodeEditor = function(){document.getElementById("multiLineDiv").style='z-index:-1;opacity: 0;';} var multiLineArgs=[null,null,null]; editor_blockly.multiLineEdit = function(value,b,f,callback){ - document.getElementById("multiLineDiv").style.display=''; + editor_blockly.showCodeEditor(); codeEditor.setValue(value.split('\\n').join('\n')||''); multiLineArgs[0]=b; multiLineArgs[1]=f; multiLineArgs[2]=callback; } editor_blockly.multiLineDone = function(){ - document.getElementById("multiLineDiv").style.display='none'; + editor_blockly.hideCodeEditor(); if(!multiLineArgs[0] || !multiLineArgs[1] || !multiLineArgs[2])return; var newvalue = codeEditor.getValue()||''; multiLineArgs[2](newvalue,multiLineArgs[0],multiLineArgs[1]) } +editor_blockly.multiLineCancel = function(){ + multiLineArgs=[null,null,null]; + editor_blockly.hideCodeEditor(); +} editor_blockly.doubleClickBlock = function (blockId){ var b=editor_blockly.workspace.getBlockById(blockId); diff --git a/_server/editor_mode.js b/_server/editor_mode.js index 5ef6852d..a0092c85 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -1,4 +1,5 @@ editor_mode = function(editor){ +var core = editor.core; function editor_mode(){ this.ids={ diff --git a/editor.html b/editor.html index 6cde4cea..854ab8cb 100644 --- a/editor.html +++ b/editor.html @@ -99,7 +99,7 @@
-
+

事件编辑器    @@ -115,6 +115,7 @@ +

- From 05982bfaf486e8f129e565921a2648d2f2a1932c Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Wed, 7 Mar 2018 22:44:57 +0800 Subject: [PATCH 061/102] issue #57 #57 --- _server/README.md | 10 ++- _server/css/editor_mode.css | 24 +++++-- _server/editor.js | 2 + _server/editor_blockly.js | 31 +-------- _server/editor_file.js | 119 ++++++++++++++++++++++++++--------- _server/editor_mode.js | 18 +++++- _server/editor_multi.js | 76 ++++++++++++++++++++++ editor.html | 24 +++++-- project/data.comment.js | 2 +- project/functions.comment.js | 2 +- project/functions.js | 13 ++++ 11 files changed, 247 insertions(+), 74 deletions(-) create mode 100644 _server/editor_multi.js diff --git a/_server/README.md b/_server/README.md index 9f9a2475..ec9d1981 100644 --- a/_server/README.md +++ b/_server/README.md @@ -18,15 +18,16 @@ editor.file.loadFloorFile editor.file.saveFloorFile editor.file.saveFloorFileAs ``` -5个编辑模式有关的查询 +6个编辑模式有关的查询 ```javascript editor.file.editItem('redJewel',[],function(a){console.log(a)}); editor.file.editEnemy('redBat',[],function(a){console.log(a)}); editor.file.editLoc(2,0,[],function(a){console.log(a)}); editor.file.editFloor([],function(a){console.log(a)}); editor.file.editTower([],function(a){console.log(a)}); +editor.file.editFunctions([],function(a){console.log(a)}); ``` -5个编辑模式有关的编辑 +6个编辑模式有关的编辑 ```javascript editor.info={images: "terrains", y: 9}; editor.file.changeIdAndIdnum('yellowWall2',16,editor.info,function(a){console.log(a)}); @@ -35,15 +36,17 @@ editor.file.editEnemy('redBat',[['change',"['atk']",20]],function(a){console.log editor.file.editLoc(2,6,[["change","['afterBattle']",null]],function(a){console.log(a)}); editor.file.editFloor([["change","['title']",'样板 33 层']],function(a){console.log(a)}); editor.file.editTower([["change","['values']['lavaDamage']",200]],function(a){console.log(a)}); +editor.file.editFunctions(["change","['events']['afterChangeLight']","function(x,y){console.log(x,y)}"],function(a){console.log(a)}); ``` ### editor_mode.js -4个生成表格并绑定事件的函数 +5个生成表格并绑定事件的函数 ```javascript editor.mode.loc(); editor.mode.emenyitem(); editor.mode.floor(); editor.mode.tower(); +editor.mode.functions(); ``` 切换模式 ```javascript @@ -52,6 +55,7 @@ editor.mode.onmode('loc'); editor.mode.onmode('emenyitem'); editor.mode.onmode('floor'); editor.mode.onmode('tower'); +editor.mode.onmode('functions'); ``` 在切换模式时,改动才会保存到文件,并且需要刷新页面使得`editor`能看到改动 diff --git a/_server/css/editor_mode.css b/_server/css/editor_mode.css index 724bb347..3a6a86cc 100644 --- a/_server/css/editor_mode.css +++ b/_server/css/editor_mode.css @@ -56,13 +56,29 @@ #left6 #blocklyDiv {height: 480px; width: 940px;float:left;} #left6 #codeArea {width: 99.5%; height: 15.4em;overflow:y;/* resize:none; */clear:both;} -#left6 #multiLineDiv {height: 440px; width: 375px;float:left;} -#left6 #multiLineDiv .CodeMirror { + +#left7 { + /* height: 440px; width: 375px;float:left; */ + left: 5px; + top: 5px; + z-index: 200; + position: fixed; + background-color: rgb(245, 245, 245); + width: 1335px; + height: 780px; +} +#left7 .CodeMirror { /* border-top: 1px solid black; border-bottom: 1px solid black; */ border: 1px solid #eee; - height: 438px; - width: 373px; + height: 700px; + width: 940px; +} + +#left8 { + left: 900px; + top: 1290px; + width: 440px; } .etable table, diff --git a/_server/editor.js b/_server/editor.js index d6130e83..718199a7 100644 --- a/_server/editor.js +++ b/_server/editor.js @@ -22,6 +22,7 @@ editor.prototype.init = function(callback){ } var afterMainInit = function(){ + core.floors=JSON.parse(JSON.stringify(core.floors,function(k,v){if(v instanceof Function){return v.toString()}else return v})); editor.main=main; editor.core=core; editor.fs=fs; @@ -154,6 +155,7 @@ editor.prototype.mapInit = function(){ editor.currentFloorData.afterBattle={}; editor.currentFloorData.afterGetItem={}; editor.currentFloorData.afterOpenDoor={}; + editor.currentFloorData.cannotMove={}; } editor.prototype.drawMapBg = function(img){ var bgc = bg.getContext('2d'); diff --git a/_server/editor_blockly.js b/_server/editor_blockly.js index dbe164d4..214fbb36 100644 --- a/_server/editor_blockly.js +++ b/_server/editor_blockly.js @@ -357,35 +357,6 @@ editor_blockly.confirm = function (){ setvalue(JSON.stringify(obj)); } -var codeEditor = CodeMirror.fromTextArea(document.getElementById("multiLineCode"), { - lineNumbers: true, - matchBrackets: true, - lineWrapping: true, - continueComments: "Enter", - extraKeys: {"Ctrl-Q": "toggleComment"} -}); -editor_blockly.showCodeEditor = function(){document.getElementById("multiLineDiv").style='';} -editor_blockly.hideCodeEditor = function(){document.getElementById("multiLineDiv").style='z-index:-1;opacity: 0;';} - -var multiLineArgs=[null,null,null]; -editor_blockly.multiLineEdit = function(value,b,f,callback){ - editor_blockly.showCodeEditor(); - codeEditor.setValue(value.split('\\n').join('\n')||''); - multiLineArgs[0]=b; - multiLineArgs[1]=f; - multiLineArgs[2]=callback; -} -editor_blockly.multiLineDone = function(){ - editor_blockly.hideCodeEditor(); - if(!multiLineArgs[0] || !multiLineArgs[1] || !multiLineArgs[2])return; - var newvalue = codeEditor.getValue()||''; - multiLineArgs[2](newvalue,multiLineArgs[0],multiLineArgs[1]) -} -editor_blockly.multiLineCancel = function(){ - multiLineArgs=[null,null,null]; - editor_blockly.hideCodeEditor(); -} - editor_blockly.doubleClickBlock = function (blockId){ var b=editor_blockly.workspace.getBlockById(blockId); console.log(b); @@ -400,7 +371,7 @@ editor_blockly.doubleClickBlock = function (blockId){ if(f){ var value = b.getFieldValue(f); //多行编辑 - editor_blockly.multiLineEdit(value,b,f,function(newvalue,b,f){ + editor_multi.multiLineEdit(value,b,f,function(newvalue,b,f){ if(textStringDict[b.type]!=='RawEvalString_0'){} b.setFieldValue(newvalue.split('\n').join('\\n'),f); }); diff --git a/_server/editor_file.js b/_server/editor_file.js index ce340d8a..2667ec0c 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -3,35 +3,28 @@ editor_file = function(editor, callback){ var editor_file = {}; - - (function(){ - var script = document.createElement('script'); - if (window.location.href.indexOf('_server')!==-1) - script.src = '../project/comment.js'; - else - script.src = 'project/comment.js'; - document.body.appendChild(script); - script.onload = function () { - editor_file.comment=comment_c456ea59_6018_45ef_8bcc_211a24c627dc; - delete(comment_c456ea59_6018_45ef_8bcc_211a24c627dc); - if (editor_file.comment && editor_file.dataComment && callback) - callback(); - } - })(); - (function(){ - var script = document.createElement('script'); - if (window.location.href.indexOf('_server')!==-1) - script.src = '../project/data.comment.js'; - else - script.src = 'project/data.comment.js'; - document.body.appendChild(script); - script.onload = function () { - editor_file.dataComment=data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d; - delete(data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d); - if (editor_file.comment && editor_file.dataComment && callback) - callback(); - } - })(); + var commentjs={ + 'comment':'comment', + 'data.comment':'dataComment', + 'functions.comment':'functionsComment', + } + for(var key in commentjs){ + (function(key){ + var value = commentjs[key]; + var script = document.createElement('script'); + if (window.location.href.indexOf('_server')!==-1) + script.src = '../project/'+key+'.js'; + else + script.src = 'project/'+key+'.js'; + document.body.appendChild(script); + script.onload = function () { + editor_file[value]=eval(key.replace('.','_')+'_c456ea59_6018_45ef_8bcc_211a24c627dc'); + var loaded = Boolean(callback); + for(var key_ in commentjs){loaded = loaded && editor_file[commentjs[key_]]} + if (loaded)callback(); + } + })(key); + } editor_file.getFloorFileList = function(callback){ @@ -396,6 +389,52 @@ editor_file = function(editor, callback){ } //callback([obj,commentObj,err:String]) + //////////////////////////////////////////////////////////////////// + + var fmap = {}; + var fjson = JSON.stringify(functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a,function(k,v){if(v instanceof Function){var id_ = editor.guid();fmap[id_]=v.toString();return id_;}else return v},4); + var fobj = JSON.parse(fjson); + editor_file.functionsMap = fmap; + editor_file.functionsJSON = fjson; + var buildlocobj = function(locObj){ + for(var key in locObj){ + if(typeof(locObj[key])!==typeof(''))buildlocobj(locObj[key]); + else locObj[key]=fmap[locObj[key]]; + } + }; + + editor_file.editFunctions = function(actionList,callback){ + /*actionList:[ + ["change","['events']['afterChangeLight']","function(x,y){console.log(x,y)}"], + ["change","['ui']['drawAbout']","function(){...}"], + ] + 为[]时只查询不修改 + */ + if (!isset(callback)) {printe('未设置callback');throw('未设置callback')}; + if (isset(actionList) && actionList.length > 0){ + saveSetting('functions',actionList,function (err) { + callback([ + (function(){ + var locObj=JSON.parse(fjson); + buildlocobj(locObj); + return locObj; + })(), + editor_file.functionsComment, + err]); + }); + } else { + callback([ + (function(){ + var locObj=JSON.parse(fjson); + buildlocobj(locObj); + return locObj; + })(), + editor_file.functionsComment, + null]); + } + } + //callback([obj,commentObj,err:String]) + //////////////////////////////////////////////////////////////////// var isset = function (val) { @@ -422,6 +461,12 @@ editor_file = function(editor, callback){ } return formatArrStr; } + + var encode = function (str) { + return btoa(encodeURIComponent(str).replace(/%([0-9A-F]{2})/g, function(match, p1) { + return String.fromCharCode(parseInt(p1, 16)) + })) + } var saveSetting = function(file,actionList,callback) { console.log(file); @@ -490,6 +535,22 @@ editor_file = function(editor, callback){ }); return; } + if (file=='functions') { + actionList.forEach(function (value) { + if (value[0]!='change')return; + eval("fmap[fobj"+value[1]+']='+JSON.stringify(value[2])); + }); + var fraw = fjson; + for(var id_ in fmap){ + fraw = fraw.replace('"'+id_+'"',fmap[id_]) + } + var datastr='functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = \n'; + datastr+=fraw; + fs.writeFile('project/functions.js',encode(datastr),'base64',function(err, data){ + callback(err); + }); + return; + } if (file=='floors') { actionList.forEach(function (value) { if (value[0]!='change')return; diff --git a/_server/editor_mode.js b/_server/editor_mode.js index a0092c85..9ad234e8 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -6,7 +6,8 @@ function editor_mode(){ 'loc':'left2', 'emenyitem':'left3', 'floor':'left4', - 'tower':'left5' + 'tower':'left5', + 'functions':'left8' } this._ids={} this.dom={} @@ -74,6 +75,7 @@ editor_mode.prototype.objToTable = function(obj,commentObj){ } input.ondblclick = function(){ editor_blockly.import(guid); + editor_multi.import(guid); } }); } @@ -164,6 +166,10 @@ editor_mode.prototype.doActionList = function(mode,actionList){ editor.file.editTower(actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])};printf('修改成功')}); break; + case 'functions': + + editor.file.editFunctions(actionList,function(objs_){console.log(objs_);if(objs_.slice(-1)[0]!=null){printe(objs_.slice(-1)[0]);throw(objs_.slice(-1)[0])};printf('修改成功')}); + break; default: break; } @@ -243,6 +249,16 @@ editor_mode.prototype.tower = function(callback){ if (Boolean(callback))callback(); } +editor_mode.prototype.functions = function(callback){ + var objs=[]; + editor.file.editFunctions([],function(objs_){objs=objs_;console.log(objs_)}); + //只查询不修改时,内部实现不是异步的,所以可以这么写 + var tableinfo=editor_mode.objToTable(objs[0],objs[1]); + document.getElementById('table_e260a2be_5690_476a_b04e_dacddede78b3').innerHTML=tableinfo.HTML; + tableinfo.listen(tableinfo.guids); + if (Boolean(callback))callback(); +} + ///////////////////////////////////////////////////////////////////////////// editor_mode.prototype.listen = function(callback){ diff --git a/_server/editor_multi.js b/_server/editor_multi.js new file mode 100644 index 00000000..3a620b8d --- /dev/null +++ b/_server/editor_multi.js @@ -0,0 +1,76 @@ +editor_multi = function(){ + +var editor_multi = {}; + +var codeEditor = CodeMirror.fromTextArea(document.getElementById("multiLineCode"), { + lineNumbers: true, + matchBrackets: true, + lineWrapping: true, + continueComments: "Enter", + extraKeys: {"Ctrl-Q": "toggleComment"} +}); + +editor_multi.id=''; + +editor_multi.show = function(){document.getElementById('left7').style='';} +editor_multi.hide = function(){document.getElementById('left7').style='z-index:-1;opacity: 0;';} + + +editor_multi.import = function(id_){ + var thisTr = document.getElementById(id_); + if(!thisTr)return; + var input = thisTr.children[2].children[0].children[0]; + var field = thisTr.children[0].getAttribute('title'); + var type = input.value && (input.value.slice(0,11)==='"function ('); + if(!type)return; + editor_multi.id=id_; + codeEditor.setValue(JSON.parse(input.value)||''); + editor_multi.show(); +} + +editor_multi.cancel = function(){ + editor_multi.hide(); + editor_multi.id=''; + multiLineArgs=[null,null,null]; +} + +editor_multi.confirm = function (){ + if(!editor_multi.id){ + editor_multi.id=''; + return; + } + if(editor_multi.id==='callFromBlockly'){ + editor_multi.id=''; + editor_multi.multiLineDone(); + return; + } + var setvalue = function(value){ + var thisTr = document.getElementById(editor_multi.id); + editor_multi.id=''; + var input = thisTr.children[2].children[0].children[0]; + input.value = JSON.stringify(value); + editor_multi.hide(); + input.onchange(); + } + setvalue(codeEditor.getValue()||''); +} + +var multiLineArgs=[null,null,null]; +editor_multi.multiLineEdit = function(value,b,f,callback){ + editor_multi.id='callFromBlockly'; + codeEditor.setValue(value.split('\\n').join('\n')||''); + multiLineArgs[0]=b; + multiLineArgs[1]=f; + multiLineArgs[2]=callback; + editor_multi.show(); +} +editor_multi.multiLineDone = function(){ + editor_multi.hide(); + if(!multiLineArgs[0] || !multiLineArgs[1] || !multiLineArgs[2])return; + var newvalue = codeEditor.getValue()||''; + multiLineArgs[2](newvalue,multiLineArgs[0],multiLineArgs[1]) +} + +return editor_multi; +} +//editor_multi=editor_multi(); \ No newline at end of file diff --git a/editor.html b/editor.html index 854ab8cb..73320236 100644 --- a/editor.html +++ b/editor.html @@ -125,14 +125,24 @@
-
- - - -
+
+ + + +
+
+

脚本编辑

+
+ + + + +
条目注释
+
+
@@ -331,7 +341,9 @@ main.init('editor', function() { editor.mode.emenyitem(); editor.mode.floor(); editor.mode.tower(); + editor.mode.functions(); editor.mode.listen(); + editor_multi=editor_multi(); editor_blockly=editor_blockly(); }); }); @@ -341,6 +353,8 @@ main.init('editor', function() { //main.listen(); + + diff --git a/project/data.comment.js b/project/data.comment.js index 7a901303..00531642 100644 --- a/project/data.comment.js +++ b/project/data.comment.js @@ -1,4 +1,4 @@ -data_comment_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = +data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = { "main": { "useCompress": " 是否使用压缩文件 \n 当你即将发布你的塔时,请使用“JS代码压缩工具”将所有js代码进行压缩,然后将这里的useCompress改为true。 \n 请注意,只有useCompress是false时才会读取floors目录下的文件,为true时会直接读取libs目录下的floors.min.js文件。 \n 如果要进行剧本的修改请务必将其改成false。 \n$select({\"values\":[false]})$end", diff --git a/project/functions.comment.js b/project/functions.comment.js index 1540f623..8093f009 100644 --- a/project/functions.comment.js +++ b/project/functions.comment.js @@ -1,4 +1,4 @@ -functions_comment_d6ad677b_427a_4623_b50f_a445a3b0ef8a = +functions_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = { "events" : { "setInitData" : "不同难度分别设置初始属性", diff --git a/project/functions.js b/project/functions.js index eb97fffe..20059376 100644 --- a/project/functions.js +++ b/project/functions.js @@ -3,6 +3,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = "events":{ ////// 不同难度分别设置初始属性 ////// "setInitData":function (hard) { + // 不同难度分别设置初始属性 if (hard=='Easy') { // 简单难度 core.setFlag('hard', 1); // 可以用flag:hard来获得当前难度 // 可以在此设置一些初始福利,比如设置初始生命值可以调用: @@ -23,6 +24,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 游戏获胜事件 ////// "win" : function(reason) { + // 游戏获胜事件 core.ui.closePanel(); var replaying = core.status.replay.replaying; core.stopReplay(); @@ -38,6 +40,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 游戏失败事件 ////// "lose" : function(reason) { + // 游戏失败事件 core.ui.closePanel(); var replaying = core.status.replay.replaying; core.stopReplay(); @@ -51,6 +54,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 转换楼层结束的事件 ////// "afterChangeFloor" : function (floorId) { + // 转换楼层结束的事件 if (core.isset(core.status.event.id)) return; // 当前存在事件 if (!core.hasFlag("visited_"+floorId)) { @@ -66,6 +70,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 加点事件 ////// "addPoint" : function (enemy) { + // 加点事件 var point = enemy.point; if (!core.isset(point) || point<=0) return []; @@ -88,6 +93,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 战斗结束后触发的事件 ////// "afterBattle" : function(enemyId,x,y,callback) { + // 战斗结束后触发的事件 var enemy = core.material.enemys[enemyId]; @@ -189,6 +195,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 开一个门后触发的事件 ////// "afterOpenDoor" : function(doorId,x,y,callback) { + // 开一个门后触发的事件 var todo = []; if (core.isset(x) && core.isset(y)) { @@ -212,10 +219,12 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 改变亮灯之后,可以触发的事件 ////// "afterChangeLight" : function(x,y) { + // 改变亮灯之后,可以触发的事件 }, ////// 推箱子后的事件 ////// "afterPushBox" : function () { + // 推箱子后的事件 var noBoxLeft = function () { // 地图上是否还存在未推到的箱子,如果不存在则返回true,存在则返回false @@ -239,6 +248,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 使用炸弹/圣锤后的事件 ////// "afterUseBomb" : function () { + // 使用炸弹/圣锤后的事件 // 这是一个使用炸弹也能开门的例子 /* @@ -254,10 +264,12 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = }, ////// 即将存档前可以执行的操作 ////// "beforeSaveData" : function(data) { + // 即将存档前可以执行的操作 }, ////// 读档事件后,载入事件前,可以执行的操作 ////// "afterLoadData" : function(data) { + // 读档事件后,载入事件前,可以执行的操作 } @@ -266,6 +278,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = "ui":{ ////// 绘制“关于”界面 ////// "drawAbout" : function() { + // 绘制“关于”界面 if (!core.isPlaying()) { core.status.event = {'id': null, 'data': null}; From a695dcd6cffcbdfca18cf0abaea91a3dc5a34301 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Thu, 8 Mar 2018 19:00:20 +0800 Subject: [PATCH 062/102] =?UTF-8?q?editor=E5=89=8D=E7=AB=AF=E4=B8=8A?= =?UTF-8?q?=E5=88=87=E6=8D=A2=E6=A8=A1=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/css/editor_mode.css | 13 ++++++++++--- _server/editor.js | 4 ++-- _server/editor_mode.js | 20 +++++++++++++++++++- _server/vm.js | 15 ++++++++++++++- editor.html | 30 +++++++++++++++++++++--------- 5 files changed, 66 insertions(+), 16 deletions(-) diff --git a/_server/css/editor_mode.css b/_server/css/editor_mode.css index 3a6a86cc..1985bd23 100644 --- a/_server/css/editor_mode.css +++ b/_server/css/editor_mode.css @@ -13,6 +13,13 @@ .leftTab > :first-child{margin-top:5px;} .leftTab > :last-child{margin-bottom:5px;} +.leftTab { + left: 5px; + top: 10px; + width: 435px; +} + +/* #left1 { left: 5px; top: 650px; @@ -42,7 +49,7 @@ top: 1290px; width: 440px; } - + */ #left6 { left: 5px; /* top: 1930px; */ @@ -74,13 +81,13 @@ height: 700px; width: 940px; } - +/* #left8 { left: 900px; top: 1290px; width: 440px; } - + */ .etable table, .etable table td { color: #000; diff --git a/_server/editor.js b/_server/editor.js index 718199a7..72aee983 100644 --- a/_server/editor.js +++ b/_server/editor.js @@ -363,7 +363,7 @@ editor.prototype.listen = function() { if(!selectBox.isSelected) { var loc = eToLoc(e); var pos = locToPos(loc); - editor_mode.onmode('');//为了强制触发doAction + editor_mode.onmode('nextChange');//为了强制触发doAction editor_mode.onmode('loc'); editor_mode.loc(); tip.whichShow = 1; @@ -521,7 +521,7 @@ editor.prototype.listen = function() { } } tip.infos = JSON.parse(JSON.stringify(editor.info)); - editor_mode.onmode('');//为了强制触发doAction + editor_mode.onmode('nextChange');//为了强制触发doAction editor_mode.onmode('emenyitem'); editor_mode.emenyitem(); } diff --git a/_server/editor_mode.js b/_server/editor_mode.js index 9ad234e8..fa06fda7 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -7,7 +7,10 @@ function editor_mode(){ 'emenyitem':'left3', 'floor':'left4', 'tower':'left5', - 'functions':'left8' + 'functions':'left8', + + 'map':'left', + 'appendpic':'left1', } this._ids={} this.dom={} @@ -179,11 +182,20 @@ editor_mode.prototype.onmode = function (mode) { if (editor_mode.mode!=mode) { console.log('change mode into : '+mode); editor_mode.doActionList(editor_mode.mode,editor_mode.actionList); + if(editor_mode.mode==='nextChange' && mode)editor_mode.showMode(mode); editor_mode.mode=mode; editor_mode.actionList=[]; } } +editor_mode.prototype.showMode = function (mode) { + for(var name in this.dom){ + editor_mode.dom[name].style='z-index:-1;opacity: 0;'; + } + editor_mode.dom[mode].style=''; + document.getElementById('editModeSelect').value=mode; +} + editor_mode.prototype.loc = function(callback){ //editor.pos={x: 0, y: 0}; if (!core.isset(editor.pos))return; @@ -448,6 +460,12 @@ editor_mode.prototype.listen = function(callback){ }); } + var editModeSelect = document.getElementById('editModeSelect'); + editModeSelect.onchange = function(){ + editor_mode.onmode('nextChange'); + editor_mode.onmode(editModeSelect.value); + } + if (Boolean(callback))callback(); } diff --git a/_server/vm.js b/_server/vm.js index a034eaf6..de416fed 100644 --- a/_server/vm.js +++ b/_server/vm.js @@ -1,7 +1,20 @@ // vue 相关处理 document.body.onmousedown = function(e){ - selectBox.isSelected = false; + console.log(e); + var eid=[]; + e.path.forEach(function(node){ + if(!node.getAttribute)return; + var id_ = node.getAttribute('id'); + if (id_){ + if(['left','left1','left2','left3','left4','left5','left8'].indexOf(id_)!==-1)eid.push('edit'); + eid.push(id_); + } + }); + console.log(eid); + if(eid.indexOf('edit')===-1){ + if(eid.indexOf('tip')===-1)selectBox.isSelected = false; + } editor_mode.onmode(''); editor.info = {}; } diff --git a/editor.html b/editor.html index 73320236..2b59da98 100644 --- a/editor.html +++ b/editor.html @@ -8,7 +8,7 @@
-
+
@@ -32,7 +32,7 @@
-
+

追加素材

@@ -52,7 +52,7 @@

-
+

地图选点

0,0

@@ -63,7 +63,7 @@
-
+

图块属性

@@ -79,7 +79,7 @@
-
+

楼层属性

@@ -89,7 +89,7 @@
-
+

全塔属性

@@ -128,12 +128,12 @@ -
+
-
+

脚本编辑

@@ -170,7 +170,17 @@ -
+ + +
+ ', '', - '\n', + '\n', ]; return [outstr.join(''),guid]; } diff --git a/_server/editor_multi.js b/_server/editor_multi.js index 3a620b8d..289a5971 100644 --- a/_server/editor_multi.js +++ b/_server/editor_multi.js @@ -11,6 +11,7 @@ var codeEditor = CodeMirror.fromTextArea(document.getElementById("multiLineCode" }); editor_multi.id=''; +editor_multi.isString=false; editor_multi.show = function(){document.getElementById('left7').style='';} editor_multi.hide = function(){document.getElementById('left7').style='z-index:-1;opacity: 0;';} @@ -18,14 +19,20 @@ editor_multi.hide = function(){document.getElementById('left7').style='z-index:- editor_multi.import = function(id_){ var thisTr = document.getElementById(id_); - if(!thisTr)return; + if(!thisTr)return false; var input = thisTr.children[2].children[0].children[0]; var field = thisTr.children[0].getAttribute('title'); - var type = input.value && (input.value.slice(0,11)==='"function ('); - if(!type)return; + if(!input.type || input.type!=='textarea')return false; editor_multi.id=id_; - codeEditor.setValue(JSON.parse(input.value)||''); + editor_multi.isString=false; + if(input.value.slice(0,1)==='"'){ + editor_multi.isString=true; + codeEditor.setValue(JSON.parse(input.value)||''); + } else { + codeEditor.setValue(input.value||''); + } editor_multi.show(); + return true; } editor_multi.cancel = function(){ @@ -48,7 +55,11 @@ editor_multi.confirm = function (){ var thisTr = document.getElementById(editor_multi.id); editor_multi.id=''; var input = thisTr.children[2].children[0].children[0]; - input.value = JSON.stringify(value); + if(editor_multi.isString){ + input.value = JSON.stringify(value); + } else { + input.value = value; + } editor_multi.hide(); input.onchange(); } From 93ee7f04150f1ad4913b342b093be6eaaa94d446 Mon Sep 17 00:00:00 2001 From: oc Date: Fri, 9 Mar 2018 21:11:58 +0800 Subject: [PATCH 067/102] Remove Storage --- libs/actions.js | 78 +++++++++++++++++++++++++++++++++++++++++++------ libs/enemys.js | 4 +++ libs/events.js | 2 +- libs/ui.js | 8 +++++ main.js | 6 ++-- 5 files changed, 85 insertions(+), 13 deletions(-) diff --git a/libs/actions.js b/libs/actions.js index 1a815548..aca775d9 100644 --- a/libs/actions.js +++ b/libs/actions.js @@ -128,6 +128,10 @@ actions.prototype.keyDown = function(keyCode) { this.keyDownLocalSaveSelect(keyCode); return; } + if (core.status.event.id=='storageRemove') { + this.keyDownStorageRemove(keyCode); + return; + } if (core.status.event.id=='cursor') { this.keyDownCursor(keyCode); return; @@ -255,7 +259,10 @@ actions.prototype.keyUp = function(keyCode) { this.keyUpLocalSaveSelect(keyCode); return; } - + if (core.status.event.id=='storageRemove') { + this.keyUpStorageRemove(keyCode); + return; + } if (core.status.event.id=='cursor') { this.keyUpCursor(keyCode); return; @@ -649,6 +656,10 @@ actions.prototype.onclick = function (x, y, stepPostfix) { this.clickLocalSaveSelect(x,y); return; } + if (core.status.event.id=='storageRemove') { + this.clickStorageRemove(x,y); + return; + } if (core.status.event.id == 'cursor') { this.clickCursor(x,y); @@ -1628,14 +1639,8 @@ actions.prototype.clickSyncSave = function (x,y) { })); break; case 5: - core.status.event.selection=1; - core.ui.drawConfirmBox("你确定要清空所有存档吗?", function() { - localStorage.clear(); - core.drawText("\t[操作成功]你的所有存档已被清空。"); - }, function() { - core.status.event.selection=5; - core.ui.drawSyncSave(); - }) + core.status.event.selection=0; + core.ui.drawStorageRemove(); break; case 6: core.status.event.selection=3; @@ -1793,6 +1798,61 @@ actions.prototype.keyUpLocalSaveSelect = function (keycode) { } } +////// 存档删除界面时的点击操作 ////// +actions.prototype.clickStorageRemove = function (x, y) { + if (x<5 || x>7) return; + var choices = core.status.event.ui.choices; + + var topIndex = 6 - parseInt((choices.length - 1) / 2); + + if (y>=topIndex && y=1 && x<=11) { diff --git a/libs/enemys.js b/libs/enemys.js index cf284486..7a744b53 100644 --- a/libs/enemys.js +++ b/libs/enemys.js @@ -170,6 +170,10 @@ enemys.prototype.getDefDamage = function (monsterId) { enemys.prototype.calDamage = function (monster, hero_hp, hero_atk, hero_def, hero_mdef) { var mon_hp = monster.hp, mon_atk = monster.atk, mon_def = monster.def, mon_special = monster.special; + hero_hp=Math.max(0, hero_hp); + hero_atk=Math.max(0, hero_atk); + hero_def=Math.max(0, hero_def); + hero_mdef=Math.max(0, hero_mdef); if (this.hasSpecial(mon_special, 20) && !core.hasItem("cross")) // 如果是无敌属性,且勇士未持有十字架 return 999999999; // 返回无限大 diff --git a/libs/events.js b/libs/events.js index 76415798..91a81d5a 100644 --- a/libs/events.js +++ b/libs/events.js @@ -224,9 +224,9 @@ events.prototype.doAction = function() { // 事件处理完毕 if (core.status.event.data.list.length==0) { + core.ui.closePanel(); if (core.isset(core.status.event.data.callback)) core.status.event.data.callback(); - core.ui.closePanel(); core.replay(); return; } diff --git a/libs/ui.js b/libs/ui.js index 47676211..b100b309 100644 --- a/libs/ui.js +++ b/libs/ui.js @@ -1068,6 +1068,14 @@ ui.prototype.drawLocalSaveSelect = function () { ]); } +////// 绘制存档删除页面 ////// +ui.prototype.drawStorageRemove = function () { + core.status.event.id = 'storageRemove'; + this.drawChoices(null, [ + "清空全部塔的存档", "只清空当前塔的存档", "返回上级菜单" + ]); +} + ////// 绘制分页 ////// ui.prototype.drawPagination = function (page, totalPage) { diff --git a/main.js b/main.js index 693472b1..fee0d1aa 100644 --- a/main.js +++ b/main.js @@ -442,8 +442,9 @@ main.dom.replayGame.onclick = function () { return; } if (core.isset(obj.version) && obj.version!=core.firstData.version) { - alert("游戏版本不一致!"); - return; + // alert("游戏版本不一致!"); + if (!confirm("游戏版本不一致!\n你仍然想播放录像吗?")) + return; } if (!core.isset(obj.route) || !core.isset(obj.hard)) { alert("无效的录像!"); @@ -454,7 +455,6 @@ main.dom.replayGame.onclick = function () { core.resetStatus(core.firstData.hero, obj.hard, core.firstData.floorId, null, core.initStatus.maps); core.events.setInitData(obj.hard); core.changeFloor(core.status.floorId, null, core.firstData.hero.loc, null, function() { - //core.setHeroMoveTriggerInterval(); core.startReplay(core.decodeRoute(obj.route)); }, true); }, function () { From 38842a7200a7c855a658508a2a2dfbf20a255533 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Fri, 9 Mar 2018 22:50:59 +0800 Subject: [PATCH 068/102] =?UTF-8?q?editor=E7=BB=86=E8=8A=82=E4=BC=98?= =?UTF-8?q?=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/editor.js | 4 ++-- _server/editor_mode.js | 13 +++++++++---- _server/vm.js | 18 +++++++++++++----- editor.html | 20 ++++++++++++-------- project/data.comment.js | 8 ++++---- 5 files changed, 40 insertions(+), 23 deletions(-) diff --git a/_server/editor.js b/_server/editor.js index 72aee983..34903d52 100644 --- a/_server/editor.js +++ b/_server/editor.js @@ -363,7 +363,7 @@ editor.prototype.listen = function() { if(!selectBox.isSelected) { var loc = eToLoc(e); var pos = locToPos(loc); - editor_mode.onmode('nextChange');//为了强制触发doAction + editor_mode.onmode('nextChange'); editor_mode.onmode('loc'); editor_mode.loc(); tip.whichShow = 1; @@ -521,7 +521,7 @@ editor.prototype.listen = function() { } } tip.infos = JSON.parse(JSON.stringify(editor.info)); - editor_mode.onmode('nextChange');//为了强制触发doAction + editor_mode.onmode('nextChange'); editor_mode.onmode('emenyitem'); editor_mode.emenyitem(); } diff --git a/_server/editor_mode.js b/_server/editor_mode.js index 22201e19..c3f23bc9 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -72,7 +72,7 @@ editor_mode.prototype.objToTable = function(obj,commentObj){ editor_mode.addAction(['change',field,JSON.parse(input.value)]); //尚未完成,不完善,目前还没做$range的检查 - /*临时*/editor_mode.onmode('');/*临时*/ + // /*临时*/editor_mode.onmode('');/*临时*/ //临时改为立刻写入文件,删去此句的时,切换模式才会真正写入 //现阶段这样会更实用,20180218 } @@ -149,6 +149,7 @@ editor_mode.prototype.addAction = function(action){ editor_mode.prototype.doActionList = function(mode,actionList){ if (actionList.length==0)return; + printf('修改中...'); switch (mode) { case 'loc': @@ -182,7 +183,7 @@ editor_mode.prototype.doActionList = function(mode,actionList){ editor_mode.prototype.onmode = function (mode) { if (editor_mode.mode!=mode) { console.log('change mode into : '+mode); - editor_mode.doActionList(editor_mode.mode,editor_mode.actionList); + if(mode==='save')editor_mode.doActionList(editor_mode.mode,editor_mode.actionList); if(editor_mode.mode==='nextChange' && mode)editor_mode.showMode(mode); editor_mode.mode=mode; editor_mode.actionList=[]; @@ -194,6 +195,7 @@ editor_mode.prototype.showMode = function (mode) { editor_mode.dom[name].style='z-index:-1;opacity: 0;'; } editor_mode.dom[mode].style=''; + if(editor_mode[mode])editor_mode[mode](); document.getElementById('editModeSelect').value=mode; } @@ -216,7 +218,8 @@ editor_mode.prototype.loc = function(callback){ editor_mode.prototype.emenyitem = function(callback){ //editor.info=editor.ids[editor.indexs[201]]; if (!core.isset(editor.info))return; - editor_mode.info=editor.info;//避免editor.info被清空导致无法获得是物品还是怪物 + + if(Object.keys(editor.info).length!==0)editor_mode.info=editor.info;//避免editor.info被清空导致无法获得是物品还是怪物 if (!core.isset(editor_mode.info.id)){ document.getElementById('table_a3f03d4c_55b8_4ef6_b362_b345783acd72').innerHTML=''; @@ -277,7 +280,7 @@ editor_mode.prototype.functions = function(callback){ editor_mode.prototype.listen = function(callback){ var newIdIdnum = document.getElementById('newIdIdnum'); - newIdIdnum.children[0].onchange = newIdIdnum.children[1].onchange = function(){ + newIdIdnum.children[2].onclick = function(){ if (newIdIdnum.children[0].value && newIdIdnum.children[1].value){ var id = newIdIdnum.children[0].value; var idnum = parseInt(newIdIdnum.children[1].value); @@ -285,6 +288,8 @@ editor_mode.prototype.listen = function(callback){ if(err){printe(err);throw(err)} printe('添加id的idnum成功,请F5刷新编辑器'); }); + } else { + printe('请输入id和idnum'); } } diff --git a/_server/vm.js b/_server/vm.js index de416fed..c5b1286e 100644 --- a/_server/vm.js +++ b/_server/vm.js @@ -15,7 +15,7 @@ document.body.onmousedown = function(e){ if(eid.indexOf('edit')===-1){ if(eid.indexOf('tip')===-1)selectBox.isSelected = false; } - editor_mode.onmode(''); + //editor.mode.onmode(''); editor.info = {}; } iconLib.onmousedown = function(e){ @@ -198,13 +198,21 @@ var clear = new Vue({ } }) printf = function(str_,type) { + selectBox.isSelected = false; if(!type){ - tip.msgs[11]=String(str_); - tip.whichShow=12; - } else { - tip.msgs[10]=String(str_); tip.whichShow=11; + } else { + tip.whichShow=12; } + setTimeout(function(){ + if(!type){ + tip.msgs[11]=String(str_); + tip.whichShow=12; + } else { + tip.msgs[10]=String(str_); + tip.whichShow=11; + } + },1); } printe = function(str_){printf(str_,'error')} var tip = new Vue({ diff --git a/editor.html b/editor.html index 2b59da98..494ac186 100644 --- a/editor.html +++ b/editor.html @@ -23,6 +23,10 @@ +
+ + +
@@ -53,7 +57,7 @@
-

地图选点

+

地图选点  

0,0

',shortField,'',shortCommentHTMLescape,'
',editor_mode.objToTd(thiseval,comment),'
',editor_mode.objToTd(thiseval,comment),'
@@ -64,10 +68,11 @@
-

图块属性

+

图块属性  

+
@@ -80,7 +85,7 @@
-

楼层属性

+

楼层属性  

@@ -90,7 +95,7 @@
-

全塔属性

+

全塔属性  

@@ -134,7 +139,7 @@
-

脚本编辑

+

脚本编辑  

@@ -167,16 +172,15 @@

{{ mapMsg }}

- - + diff --git a/project/data.comment.js b/project/data.comment.js index 00531642..9fb6f4da 100644 --- a/project/data.comment.js +++ b/project/data.comment.js @@ -27,11 +27,11 @@ data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "money": " 初始金币 ", "experience": " 初始经验 ", "items": { - "keys": { + "keys": " 初始道具个数 \n$leaf(true)$end"/* { "yellowKey": " 初始道具个数 ", "blueKey": "", "redKey": "" - }, + } */, "constants": "\n$leaf(true)$end", "tools": "\n$leaf(true)$end" }, @@ -41,11 +41,11 @@ data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "x": "", "y": "" }, - "flags": { + "flags": " 游戏过程中的变量或flags \n$leaf(true)$end"/* { "poison": " 游戏过程中的变量或flags \n 毒 ", "weak": " 衰 ", "curse": " 咒 " - }, + } */, "steps": " 行走步数统计 ", }, "startText": " 游戏开始前剧情。如果无剧情直接留一个空数组即可。 \n$leaf(true)$end", From c9ba70fa9c24f332a527330c5967908680490c70 Mon Sep 17 00:00:00 2001 From: oc Date: Sat, 10 Mar 2018 01:09:07 +0800 Subject: [PATCH 069/102] Replay use full name --- libs/actions.js | 4 ++-- libs/control.js | 9 +++++++-- libs/events.js | 5 +++-- libs/utils.js | 49 ++++++++++++++++++++++++++----------------------- 4 files changed, 38 insertions(+), 29 deletions(-) diff --git a/libs/actions.js b/libs/actions.js index aca775d9..e93d5238 100644 --- a/libs/actions.js +++ b/libs/actions.js @@ -185,8 +185,8 @@ actions.prototype.keyDown = function(keyCode) { } ////// 根据放开键的code来执行一系列操作 ////// -actions.prototype.keyUp = function(keyCode) { - if (core.isset(core.status.replay)&&core.status.replay.replaying) return; +actions.prototype.keyUp = function(keyCode, fromReplay) { + if (!fromReplay&&core.isset(core.status.replay)&&core.status.replay.replaying) return; if (core.status.lockControl) { core.status.holdingKeys = []; diff --git a/libs/control.js b/libs/control.js index 8e7a992e..ba257bbe 100644 --- a/libs/control.js +++ b/libs/control.js @@ -1485,7 +1485,7 @@ control.prototype.replay = function () { core.events.openShop(shopId, false); var shopInterval = setInterval(function () { - if (!core.events.clickShop(6, topIndex+core.status.event.selection)) { + if (!core.actions.clickShop(6, topIndex+core.status.event.selection)) { clearInterval(shopInterval); core.stopReplay(); core.drawTip("录像文件出错"); @@ -1493,7 +1493,7 @@ control.prototype.replay = function () { } if (selections.length==0) { clearInterval(shopInterval); - core.events.clickShop(6, topIndex+choices.length); + core.actions.clickShop(6, topIndex+choices.length); core.replay(); return; } @@ -1535,6 +1535,11 @@ control.prototype.replay = function () { return; } } + else if (action.indexOf('key:')==0) { + core.actions.keyUp(parseInt(action.substring(4)), true); + core.replay(); + return; + } core.stopReplay(); core.insertAction("录像文件出错"); diff --git a/libs/events.js b/libs/events.js index 91a81d5a..58dae299 100644 --- a/libs/events.js +++ b/libs/events.js @@ -224,9 +224,10 @@ events.prototype.doAction = function() { // 事件处理完毕 if (core.status.event.data.list.length==0) { + var callback = core.status.event.data.callback; core.ui.closePanel(); - if (core.isset(core.status.event.data.callback)) - core.status.event.data.callback(); + if (core.isset(callback)) + callback(); core.replay(); return; } diff --git a/libs/utils.js b/libs/utils.js index 5ad4a9de..56929077 100644 --- a/libs/utils.js +++ b/libs/utils.js @@ -158,8 +158,6 @@ utils.prototype.encodeRoute = function (route) { var ans=""; var lastMove = "", cnt=0; - var items=Object.keys(core.material.items).sort(); - var shops=Object.keys(core.initStatus.shops).sort(); route.forEach(function (t) { if (t=='up' || t=='down' || t=='left' || t=='right') { if (t!=lastMove && cnt>0) { @@ -177,15 +175,13 @@ utils.prototype.encodeRoute = function (route) { cnt=0; } if (t.indexOf('item:')==0) - ans+="I"+items.indexOf(t.substring(5)); + ans+="I"+t.substring(5)+":"; else if (t.indexOf('fly:')==0) - ans+="F"+core.floorIds.indexOf(t.substring(4)); + ans+="F"+t.substring(4)+":"; else if (t.indexOf('choices:')==0) ans+="C"+t.substring(8); - else if (t.indexOf('shop:')==0) { - var sp=t.substring(5).split(":"); - ans+="S"+shops.indexOf(sp[0])+":"+sp[1]; - } + else if (t.indexOf('shop:')==0) + ans+="S"+t.substring(5); else if (t=='turn') ans+='T'; else if (t=='getNext') @@ -194,9 +190,10 @@ utils.prototype.encodeRoute = function (route) { ans+="P"+t.substring(6); else if (t=='no') ans+='N'; - else if (t.indexOf('move:')==0) { + else if (t.indexOf('move:')==0) ans+="M"+t.substring(5); - } + else if (t=='key:') + ans+='K'+t.substring(4); } }); if (cnt>0) { @@ -221,27 +218,33 @@ utils.prototype.decodeRoute = function (route) { if (num.length==0) num="1"; return core.isset(noparse)?num:parseInt(num); } + var getString = function () { + var str=""; + while (index Date: Sat, 10 Mar 2018 13:27:13 +0800 Subject: [PATCH 070/102] =?UTF-8?q?editor=E5=AE=9E=E7=8E=B0$range=E4=BB=A5?= =?UTF-8?q?=E5=8F=8A=E7=BB=86=E8=8A=82=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- 2.0diff.md | 11 +++----- _server/README.md | 17 ++++++++---- _server/editor_blockly.js | 3 +- _server/editor_mode.js | 58 +++++++++++++++++++++++---------------- project/comment.js | 4 +-- 5 files changed, 54 insertions(+), 39 deletions(-) diff --git a/2.0diff.md b/2.0diff.md index ebc3c1c3..2eb12662 100644 --- a/2.0diff.md +++ b/2.0diff.md @@ -139,14 +139,11 @@ $textarea(evalstr)$end # todo & 目前的bug + `event`,`after...`在地图上没有标记,可以在右下角加类似于无`id`的红问号类似的绿色星号小标记 -+ 添加新图块只对地形好使,添加的新物品还是需要手动在`project/items.js`中加东西 -+ 目前未做$range(evalstr:thiseval)$end的检查 ++ [x] 添加新图块只对地形好使,添加的新物品还是需要手动在`project/items.js`中加东西 ++ [x] 目前未做$range(evalstr:thiseval)$end的检查 + 通过`core.values.redJewel`的方式设置物品加的数值,在全GUI下反而会不直观 + `idnum`上限改到`999`,不需要在`.js`中手动设置`idnum`的话,根据数字范围来约定类型意义不大,而且`400`内随便输个数就发现已经被占了,体验极差 + `editor.html`中独立换背景的功能不再需要,待移除 + 全GUI下编辑要经常保存修改后F5 -+ 目前的报错只是throw,如果不开F12注意不到有错误发生,修改没有生效 -+ 有待美化,以及做成标签页式的模式切换 -+ replay模式,这个功能对于魔塔网站以及贴吧活动很有意义 - -前三条我会尽快修复(添加) \ No newline at end of file ++ [x] 目前的报错只是throw,如果不开F12注意不到有错误发生,修改没有生效 ++ [x] 有待美化,以及做成标签页式的模式切换 \ No newline at end of file diff --git a/_server/README.md b/_server/README.md index ec9d1981..e75cf35d 100644 --- a/_server/README.md +++ b/_server/README.md @@ -18,7 +18,7 @@ editor.file.loadFloorFile editor.file.saveFloorFile editor.file.saveFloorFileAs ``` -6个编辑模式有关的查询 +编辑模式有关的查询 ```javascript editor.file.editItem('redJewel',[],function(a){console.log(a)}); editor.file.editEnemy('redBat',[],function(a){console.log(a)}); @@ -27,7 +27,7 @@ editor.file.editFloor([],function(a){console.log(a)}); editor.file.editTower([],function(a){console.log(a)}); editor.file.editFunctions([],function(a){console.log(a)}); ``` -6个编辑模式有关的编辑 +编辑模式有关的编辑 ```javascript editor.info={images: "terrains", y: 9}; editor.file.changeIdAndIdnum('yellowWall2',16,editor.info,function(a){console.log(a)}); @@ -50,14 +50,19 @@ editor.mode.functions(); ``` 切换模式 ```javascript -editor.mode.onmode(''); +editor.mode.onmode('');//清空 +editor.mode.onmode('save');//保存 +editor.mode.onmode('nextChange');//下次onmode时前端进行切换 + editor.mode.onmode('loc'); editor.mode.onmode('emenyitem'); editor.mode.onmode('floor'); editor.mode.onmode('tower'); editor.mode.onmode('functions'); +editor.mode.onmode('map'); +editor.mode.onmode('appendpic'); ``` -在切换模式时,改动才会保存到文件,并且需要刷新页面使得`editor`能看到改动 +在`onmode('save')`时,改动才会保存到文件,涉及到图片的改动需要刷新页面使得`editor`能看到 表格的`onchange`的实现中,获得当前模式的方式.不注意的话,修改`index.html`中页面的结构,会被坑 ```javascript @@ -83,8 +88,8 @@ editor_blockly.confirm(); ### 待调整 -多行文本编辑器独立作为组件 -editor_multi.js ++ [x] 多行文本编辑器独立作为组件 ++ [x] editor_multi.js ## z-index diff --git a/_server/editor_blockly.js b/_server/editor_blockly.js index 5348669e..86dbe348 100644 --- a/_server/editor_blockly.js +++ b/_server/editor_blockly.js @@ -312,7 +312,8 @@ editor_blockly.import = function(id_){ "['afterGetItem']":'afterGetItem', "['afterOpenDoor']":'afterOpenDoor', - "['firstData']['shops']":'shop', + //"['firstData']['shops']":'shop', + "--shop--未完成数组的处理":'shop', "['firstArrive']":'firstArrive', "['firstData']['startText']":'firstArrive', diff --git a/_server/editor_mode.js b/_server/editor_mode.js index c3f23bc9..6fffe579 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -38,11 +38,25 @@ editor_mode.prototype.init_dom_ids = function(callback){ editor_mode.prototype.objToTable = function(obj,commentObj){ var outstr=["\n
\n"]; var guids=[]; + var checkIsLeaf = function(obj,commentObj,field){ + var thiseval = eval('obj'+field); + if (thiseval == null || thiseval == undefined)return true;//null,undefined + if (typeof(thiseval) == typeof(''))return true;//字符串 + if (Object.keys(thiseval).length == 0)return true;//数字,true,false,空数组,空对象 + try { + var comment = eval('commentObj'+field); + if( comment.indexOf('$leaf') != -1){ + evalstr = comment.split('$leaf')[1].split('$end')[0]; + if(eval(evalstr) === true)return true; + } + } catch (error) {} + return false; + } //深度优先遍历 var recursionParse = function(tfield) { for(var ii in eval("obj"+tfield)){ var field = tfield+"['"+ii+"']"; - var isleaf = editor_mode.checkIsLeaf(obj,commentObj,field); + var isleaf = checkIsLeaf(obj,commentObj,field); if (isleaf) { var leafnode = editor_mode.objToTr(obj,commentObj,field); outstr.push(leafnode[0]); @@ -54,6 +68,13 @@ editor_mode.prototype.objToTable = function(obj,commentObj){ } } recursionParse(""); + var checkRange = function(comment,thiseval){ + if( comment.indexOf('$range') !== -1){ + var evalstr = comment.split('$range')[1].split('$end')[0]; + return eval(evalstr); + } + return true; + } var listen = function(guids) { guids.forEach(function(guid){ // tr>td[title=field] @@ -69,12 +90,12 @@ editor_mode.prototype.objToTable = function(obj,commentObj){ node = node.parentNode; } editor_mode.onmode(editor_mode._ids[node.getAttribute('id')]); - editor_mode.addAction(['change',field,JSON.parse(input.value)]); - //尚未完成,不完善,目前还没做$range的检查 - - // /*临时*/editor_mode.onmode('');/*临时*/ - //临时改为立刻写入文件,删去此句的时,切换模式才会真正写入 - //现阶段这样会更实用,20180218 + var thiseval = JSON.parse(input.value); + if(checkRange(comment,thiseval)){ + editor_mode.addAction(['change',field,thiseval]); + } else { + printe('输入的值不合要求,请鼠标放置在注释上查看说明'); + } } input.ondblclick = function(){ if(!editor_blockly.import(guid)) @@ -86,21 +107,6 @@ editor_mode.prototype.objToTable = function(obj,commentObj){ return {"HTML":outstr.join(''),"guids":guids,"listen":listen}; } -editor_mode.prototype.checkIsLeaf = function(obj,commentObj,field){ - var thiseval = eval('obj'+field); - if (thiseval == null || thiseval == undefined)return true;//null,undefined - if (typeof(thiseval) == typeof(''))return true;//字符串 - if (Object.keys(thiseval).length == 0)return true;//数字,true,false,空数组,空对象 - try { - var comment = eval('commentObj'+field); - if( comment.indexOf('$leaf') != -1){ - evalstr = comment.split('$leaf')[1].split('$end')[0]; - if(eval(evalstr) === true)return true; - } - } catch (error) {} - return false; -} - editor_mode.prototype.objToTr = function(obj,commentObj,field){ var guid = editor.guid(); var thiseval = eval('obj'+field); @@ -197,6 +203,12 @@ editor_mode.prototype.showMode = function (mode) { editor_mode.dom[mode].style=''; if(editor_mode[mode])editor_mode[mode](); document.getElementById('editModeSelect').value=mode; + var tips = [ + '涉及图片的更改需要F5刷新浏览器来生效', + '文本域可以通过双击,在文本编辑器或事件编辑器中编辑', + '事件编辑器中的显示文本和自定义脚本的方块也可以双击', + ]; + if(!selectBox.isSelected)printf('tips: '+tips[~~(tips.length*Math.random())]); } editor_mode.prototype.loc = function(callback){ @@ -462,7 +474,7 @@ editor_mode.prototype.listen = function(callback){ var imgbase64 = sprite.toDataURL().split(',')[1]; fs.writeFile('./project/images/'+editor_mode.appendPic.imageName+'.png',imgbase64,'base64',function(err,data){ if(err){printe(err);throw(err)} - printe('追加素材成功,请刷新编辑器'); + printe('追加素材成功,请F5刷新编辑器'); }); } diff --git a/project/comment.js b/project/comment.js index 4bf4c47e..dfd1aed8 100644 --- a/project/comment.js +++ b/project/comment.js @@ -37,13 +37,13 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "name": "显示在状态栏中的层数 ", "canFlyTo": "该楼能否被楼传器飞到(不能的话在该楼也不允许使用楼传器) \n$select({\"values\":[true,false]})$end", "canUseQuickShop": "该层是否允许使用快捷商店 \n$select({\"values\":[true,false]})$end", - "defaultGround": "默认地面的图块ID(terrains中) ", + "defaultGround": "默认地面的图块ID(terrains中) \n$select({\"values\":Object.keys(editor.core.icons.icons.terrains)})$end", "png": "背景图;你可以选择一张png图片来作为背景素材。详细用法请参见文档“自定义素材”中的说明。 \n$leaf(true)$end", "color": "该层的默认画面色调。本项可不写(代表无色调),如果写需要是一个RGBA数组。 \n$leaf(true)$end", "weather": "该层的默认天气。本项可忽略表示晴天,如果写则第一项为\"rain\"或\"snow\"代表雨雪,第二项为1-10之间的数代表强度。 \n$leaf(true)$end", "bgm": "到达该层后默认播放的BGM。本项可忽略。 ", //"map": "地图数据,需要是13x13,建议使用地图生成器来生成 ", - "item_ratio": "每一层的宝石/血瓶效果,即获得宝石和血瓶时框内\"ratio\"的值。", + "item_ratio": "每一层的宝石/血瓶效果,即获得宝石和血瓶时框内\"ratio\"的值。$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end", "firstArrive": "第一次到该楼层触发的事件 \n$leaf(true)$end", }, 'loc' : { From 15cdfa0f23555d40c7da25157ad7aa85e71c0b1c Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 10 Mar 2018 14:10:42 +0800 Subject: [PATCH 071/102] =?UTF-8?q?function=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/editor.js | 2 ++ _server/editor_file.js | 12 ++++++------ project/data.comment.js | 4 ++-- project/data.js | 4 ++-- 4 files changed, 12 insertions(+), 10 deletions(-) diff --git a/_server/editor.js b/_server/editor.js index 34903d52..515a6f73 100644 --- a/_server/editor.js +++ b/_server/editor.js @@ -23,6 +23,8 @@ editor.prototype.init = function(callback){ var afterMainInit = function(){ core.floors=JSON.parse(JSON.stringify(core.floors,function(k,v){if(v instanceof Function){return v.toString()}else return v})); + core.data=JSON.parse(JSON.stringify(core.data,function(k,v){if(v instanceof Function){return v.toString()}else return v})); + data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d=JSON.parse(JSON.stringify(data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d,function(k,v){if(v instanceof Function){return v.toString()}else return v})); editor.main=main; editor.core=core; editor.fs=fs; diff --git a/_server/editor_file.js b/_server/editor_file.js index 2667ec0c..966b3b00 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -79,7 +79,7 @@ editor_file = function(editor, callback){ } datastr=datastr.concat(['\n}']); datastr=datastr.join(''); - fs.writeFile(filename,datastr,'utf-8',function(err, data){ + fs.writeFile(filename,encode(datastr),'base64',function(err, data){ callback(err); }); } @@ -482,7 +482,7 @@ editor_file = function(editor, callback){ }); var datastr='icons_4665ee12_3a1f_44a4_bea3_0fccba634dc1 = \n'; datastr+=JSON.stringify(icons_4665ee12_3a1f_44a4_bea3_0fccba634dc1,null,4); - fs.writeFile('project/icons.js',datastr,'utf-8',function(err, data){ + fs.writeFile('project/icons.js',encode(datastr),'base64',function(err, data){ callback(err); }); return; @@ -494,7 +494,7 @@ editor_file = function(editor, callback){ }); var datastr='maps_90f36752_8815_4be8_b32b_d7fad1d0542e = \n'; datastr+=JSON.stringify(maps_90f36752_8815_4be8_b32b_d7fad1d0542e,null,4); - fs.writeFile('project/maps.js',datastr,'utf-8',function(err, data){ + fs.writeFile('project/maps.js',encode(datastr),'base64',function(err, data){ callback(err); }); return; @@ -506,7 +506,7 @@ editor_file = function(editor, callback){ }); var datastr='items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a = \n'; datastr+=JSON.stringify(items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a,null,4); - fs.writeFile('project/items.js',datastr,'utf-8',function(err, data){ + fs.writeFile('project/items.js',encode(datastr),'base64',function(err, data){ callback(err); }); return; @@ -518,7 +518,7 @@ editor_file = function(editor, callback){ }); var datastr='enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80 = \n'; datastr+=JSON.stringify(enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80,null,4); - fs.writeFile('project/enemys.js',datastr,'utf-8',function(err, data){ + fs.writeFile('project/enemys.js',encode(datastr),'base64',function(err, data){ callback(err); }); return; @@ -530,7 +530,7 @@ editor_file = function(editor, callback){ }); var datastr='data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = \n'; datastr+=JSON.stringify(data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d,null,4); - fs.writeFile('project/data.js',datastr,'utf-8',function(err, data){ + fs.writeFile('project/data.js',encode(datastr),'base64',function(err, data){ callback(err); }); return; diff --git a/project/data.comment.js b/project/data.comment.js index 9fb6f4da..8afb46af 100644 --- a/project/data.comment.js +++ b/project/data.comment.js @@ -102,7 +102,7 @@ data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = ] } },*/ - "levelUp": [ + "levelUp": " 经验升级所需要的数值,是一个数组 \n 第一项为初始等级,可以简单留空,也可以写name \n 每一个里面可以含有三个参数 need, name, effect \n need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 \n name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 \n effect为本次升级所执行的操作,可由若干项组成,由分号分开 \n 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 \n$leaf(true)$end"/* [ " 经验升级所需要的数值,是一个数组 \n 第一项为初始等级,可以简单留空,也可以写name \n 每一个里面可以含有三个参数 need, name, effect \n need为所需要的经验数值,是一个正整数。请确保need所需的依次递增 \n name为该等级的名称,也可以省略代表使用系统默认值;本项将显示在状态栏中 \n effect为本次升级所执行的操作,可由若干项组成,由分号分开 \n 其中每一项写法和上面的商店完全相同,同样必须是X+=Y的形式,Y是一个表达式,同样可以使用status:xxx或item:xxx代表勇士的某项数值/道具个数 \n$leaf(true)$end", { "need": "", @@ -113,7 +113,7 @@ data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "need": "", "effect": " effect也允许写一个function,代表本次升级将会执行的操作 \n 依次往下写需要的数值即可 " } - ] + ] */ }, "values": { "HPMAX": " 各种数值;一些数值可以在这里设置\n /****** 角色相关 ******/ \n HP上限;-1则无上限 ", diff --git a/project/data.js b/project/data.js index 7aefac99..52d5d324 100644 --- a/project/data.js +++ b/project/data.js @@ -134,12 +134,12 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = {"need": 20, "name": "第二级", "effect": "status:hp+=2*(status:atk+status:def);status:atk+=10;status:def+=10"}, // 先将生命提升攻防和的2倍;再将攻击+10,防御+10 - {"need": 40, "effect": `function () { + {"need": 40, "effect": function () { core.drawText("恭喜升级!"); core.status.hero.hp *= 2; core.status.hero.atk += 100; core.status.hero.def += 100; - }`}, // effect也允许写一个function,代表本次升级将会执行的操作 + }}, // effect也允许写一个function,代表本次升级将会执行的操作 // 依次往下写需要的数值即可 ] From cbaf94e6462b6add0c35acb5a239718786117966 Mon Sep 17 00:00:00 2001 From: ckcz123 Date: Sat, 10 Mar 2018 15:11:27 +0800 Subject: [PATCH 072/102] =?UTF-8?q?=E5=90=AF=E5=8A=A8=E6=9C=8D=E5=8A=A1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- 启动服务.exe | Bin 53760 -> 53760 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/启动服务.exe b/启动服务.exe index 2ec60d8847cd11fef47d1f63c249f6055dfff041..2c84bd69c04a56c4aaaddc21c6d4847eb135f2c9 100644 GIT binary patch delta 1584 zcmY+^TTB#J7zgnG+;(TTuw6O>?z&Q>7#q2`+_sBcT4k5o7OEsbCp(P=LeQ7DiD8$}EYQH&iUVJ&bzwdu$ z&NpW+y(3cZh&0$QJzRa^(($80()d(Gy=ly+Tm zVw#P=Xs-xP2)a4?^)$(aMm?lEv0tx#%!vV3Kh4H*ec9o{4ZTft;Wsv}82*q?isWXQ ztH-ca+JsSREn@v|jxN9uwPrHD_KCWcdT6LFLj(Yf;UW zA)iD#+VaeqeaMy1U>%P0^=92O(t4-`wA0o#eTAoSu7C+GvI`sFE@V#*!2 zrE?vnEE5~JKBO!Y`CLPkWuchsJY`u3ag9=zjmkop>qk|C!fe#?a8jN`4w|^85fHew&woP3?sV~O1uKSr3YVUd>b;}}y6mD-HtM_s_WB$sW1HgE@t){m;GHXm^> z53?!ELpxU)WqCNrH7XYg`G{~Cav7BsJhm^ljyfXwuvPO@~J276DYxRTxab*(hFP{?W<6VYOZhW`J^UG_|YB_%FrJ) zTkFHm_NeeIX1RVRZAMQKYdgXgEJrWnFsjs3LOK3uWFgB!_1{cT0M`d{FTC38BF`=DCJ;6mAP@?rHt-`C?A+c4s z?0%2_@6!g92C-WkQnrZZliDYq&_1ThuqM-ZUOOesh-Pc%{L9LW__a2r+@^{T3!?c< zB(dlFKC6UrSG%SBBf9lPWevtMh5L#_8WR*-5{)i+rO)&#n^*c)ud`jCwi<1DRBy3u zksL;S^>#TiB^el}eKSAW0mG=R*VL+xj?UM2?S9K}v}B1!;LW*OxA(z7cW5ai^yNoN z^X=tN-Nw4fal859kI!B6uKx3>p_SCk@$%8qirDlg2Y05>xtfccc6WBhz2E&6%e5Qs I@9#PO2j;d*=>Px# delta 1538 zcmY+^ZA=_R7zgnGzTE9{h3l1FSW}wSK#B?d&=>qrHL=E^2GG=`zND#8W3`F;?CgB$m%01x ze|Dak*`4hjlX}Ob!K2dZ4|^^gJ0h&QwF|hD00aOl0eiQRCwd&h-DD{Bplxjwa3nuT zJz$ilE&5AZGJyPs&b_gY7xz(j)D{7YjdZQ40p2*^qHFmzO^-+Dcass?a$2l=S9{j( zz@&Cva^Mncztoxq2kx=9K+ln!cv`R09f;}mD;!AZW_paZ=k?_jC$8x2q7(D1T{a5C z9w{CyHmeVzMv5W>_qeu`9>S>C%GyYoc&@}$!aXTC;YK^t2)d;mq%p1mrnv`t{`i3I zTEZpi1-fq{UTT$?m)enqfihMCze}C);4P*h{3-QdHEweKEA=89YPs3-vLMU-$bpMX zC*`7Y#dhET1|NoClz-dd8=K8v2yy+So+CxLZmSnawM-*wddd|cf*4c6{iJ!CBWPf>N<`ph2go|< z5#(CJ!m0yu1R<^^(xZ6YIx%cAk72;*-ggMcin%V!NZBCp>-mlA6e%9t~ ze~U^or#>_5j9zQclBV<~`&p{B)9#Zdg*N+E2}WIgot&1I0Zh@>nBQWr@loS;%~;V^ zBpQ`3EjGGt-2U#HcdiviKdv|!4eov4Ypj`>Qq0eIa^Y%L-pay`-lolKqbGlTOZA$C`_Jilj8OV>VsxzC?WzxJ2mn!S_qKl*Dvz5oCK From 68fa560b0ce427fd165e9f1ba8e176a4f8824300 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 10 Mar 2018 16:41:50 +0800 Subject: [PATCH 073/102] =?UTF-8?q?=E5=AF=B9function=E6=9B=B4=E5=A5=BD?= =?UTF-8?q?=E7=9A=84=E6=94=AF=E6=8C=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/editor_multi.js | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/_server/editor_multi.js b/_server/editor_multi.js index 289a5971..556096f7 100644 --- a/_server/editor_multi.js +++ b/_server/editor_multi.js @@ -29,7 +29,13 @@ editor_multi.import = function(id_){ editor_multi.isString=true; codeEditor.setValue(JSON.parse(input.value)||''); } else { - codeEditor.setValue(input.value||''); + eval('var tobj='+input.value); + var tmap={}; + var tstr = JSON.stringify(tobj,function(k,v){if(typeof(v)===typeof('') && v.slice(0,8)==='function'){var id_ = editor.guid();tmap[id_]=v.toString();return id_;}else return v},4); + for(var id_ in tmap){ + tstr = tstr.replace('"'+id_+'"',tmap[id_]) + } + codeEditor.setValue(tstr||''); } editor_multi.show(); return true; @@ -58,7 +64,13 @@ editor_multi.confirm = function (){ if(editor_multi.isString){ input.value = JSON.stringify(value); } else { - input.value = value; + eval('var tobj='+value); + var tmap={}; + var tstr = JSON.stringify(tobj,function(k,v){if(v instanceof Function){var id_ = editor.guid();tmap[id_]=v.toString();return id_;}else return v},4); + for(var id_ in tmap){ + tstr = tstr.replace('"'+id_+'"',JSON.stringify(tmap[id_])) + } + input.value = tstr; } editor_multi.hide(); input.onchange(); From 3b9e03efeea3eae8a59f60773f9cd3af9ae902b4 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 10 Mar 2018 17:11:38 +0800 Subject: [PATCH 074/102] =?UTF-8?q?editor=E7=9A=84tips=E7=9A=84=E6=A0=B7?= =?UTF-8?q?=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/css/editor.css | 4 +++- _server/editor_mode.js | 6 +----- _server/vm.js | 5 +++++ 3 files changed, 9 insertions(+), 6 deletions(-) diff --git a/_server/css/editor.css b/_server/css/editor.css index b878cc2f..190607a1 100644 --- a/_server/css/editor.css +++ b/_server/css/editor.css @@ -210,12 +210,14 @@ body{ color: #D50000; font-weight: 700; font-size: 14px; + line-height: 1.2em; } .infoText{ color: #2196F3; } .successText{ - color: #00897B + color: #00897B; + line-height: 1.2em; } table, td { diff --git a/_server/editor_mode.js b/_server/editor_mode.js index 6fffe579..83c51823 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -203,11 +203,7 @@ editor_mode.prototype.showMode = function (mode) { editor_mode.dom[mode].style=''; if(editor_mode[mode])editor_mode[mode](); document.getElementById('editModeSelect').value=mode; - var tips = [ - '涉及图片的更改需要F5刷新浏览器来生效', - '文本域可以通过双击,在文本编辑器或事件编辑器中编辑', - '事件编辑器中的显示文本和自定义脚本的方块也可以双击', - ]; + var tips = tip_in_showMode; if(!selectBox.isSelected)printf('tips: '+tips[~~(tips.length*Math.random())]); } diff --git a/_server/vm.js b/_server/vm.js index c5b1286e..97d3602d 100644 --- a/_server/vm.js +++ b/_server/vm.js @@ -215,6 +215,11 @@ printf = function(str_,type) { },1); } printe = function(str_){printf(str_,'error')} +tip_in_showMode = [ + '涉及图片的更改需要F5刷新浏览器来生效', + '文本域可以通过双击,在文本编辑器或事件编辑器中编辑', + '事件编辑器中的显示文本和自定义脚本的方块也可以双击', +]; var tip = new Vue({ el: '#tip', data: { From 184740e3cf3db52a767f691db75068ca6f3992c0 Mon Sep 17 00:00:00 2001 From: ckcz123 Date: Sat, 10 Mar 2018 18:36:25 +0800 Subject: [PATCH 075/102] Add Point --- libs/enemys.js | 5 +- libs/ui.js | 23 +++++++- libs/utils.js | 7 ++- project/comment.js | 6 +- project/data.comment.js | 3 +- project/data.js | 45 ++++++--------- project/enemys.js | 120 ++++++++++++++++++++-------------------- project/functions.js | 2 +- 8 files changed, 110 insertions(+), 101 deletions(-) diff --git a/libs/enemys.js b/libs/enemys.js index 7a744b53..7f6156ed 100644 --- a/libs/enemys.js +++ b/libs/enemys.js @@ -252,13 +252,12 @@ enemys.prototype.getCurrentEnemys = function (floorId) { var monster = core.material.enemys[monsterId]; var mon_hp = monster.hp, mon_atk = monster.atk, mon_def = monster.def; - // 坚固 - if (this.hasSpecial(monster.special, 3) && mon_def < core.status.hero.atk - 1) - mon_def = core.status.hero.atk - 1; if (this.hasSpecial(monster.special, 10)) { mon_atk=core.status.hero.atk; mon_def=core.status.hero.def; } + if (this.hasSpecial(monster.special, 3) && mon_def < core.status.hero.atk - 1) + mon_def = core.status.hero.atk - 1; var specialText = core.enemys.getSpecialText(monsterId); if (specialText.length>=3) specialText = "多属性..."; diff --git a/libs/ui.js b/libs/ui.js index b100b309..658d42a5 100644 --- a/libs/ui.js +++ b/libs/ui.js @@ -1193,24 +1193,41 @@ ui.prototype.drawBook = function (index) { core.fillText('ui', '防御', 335, 62 * i + 32, '#DDDDDD', '13px Verdana'); core.fillText('ui', enemy.def, 365, 62 * i + 32, '#DDDDDD', 'bold 13px Verdana'); - var expOffset = 165; + var expOffset = 165, line_cnt=0; if (core.flags.enableMoney) { core.fillText('ui', '金币', 165, 62 * i + 50, '#DDDDDD', '13px Verdana'); core.fillText('ui', enemy.money, 195, 62 * i + 50, '#DDDDDD', 'bold 13px Verdana'); expOffset = 255; + line_cnt++; } - if (core.flags.enableExperience) { + // 加点 + if (core.flags.enableAddPoint) { + core.canvas.ui.textAlign = "left"; + core.fillText('ui', '加点', expOffset, 62 * i + 50, '#DDDDDD', '13px Verdana'); + core.fillText('ui', enemy.point, expOffset + 30, 62 * i + 50, '#DDDDDD', 'bold 13px Verdana'); + expOffset = 255; + line_cnt++; + } + + if (core.flags.enableExperience && line_cnt<2) { core.canvas.ui.textAlign = "left"; core.fillText('ui', '经验', expOffset, 62 * i + 50, '#DDDDDD', '13px Verdana'); core.fillText('ui', enemy.experience, expOffset + 30, 62 * i + 50, '#DDDDDD', 'bold 13px Verdana'); + line_cnt++; } + var damageOffset = 281; + if (line_cnt==1) damageOffset=326; + if (line_cnt==2) damageOffset=361; + + /* var damageOffet = 281; if (core.flags.enableMoney && core.flags.enableExperience) damageOffet = 361; else if (core.flags.enableMoney || core.flags.enableExperience) damageOffet = 326; + */ core.canvas.ui.textAlign = "center"; @@ -1219,7 +1236,7 @@ ui.prototype.drawBook = function (index) { if (damage >= core.status.hero.hp) color = '#FF0000'; if (damage <= 0) color = '#00FF00'; if (damage >= 999999999) damage = '无法战斗'; - core.fillText('ui', damage, damageOffet, 62 * i + 50, color, 'bold 13px Verdana'); + core.fillText('ui', damage, damageOffset, 62 * i + 50, color, 'bold 13px Verdana'); core.canvas.ui.textAlign = "left"; diff --git a/libs/utils.js b/libs/utils.js index 56929077..29adb15a 100644 --- a/libs/utils.js +++ b/libs/utils.js @@ -223,6 +223,7 @@ utils.prototype.decodeRoute = function (route) { while (index0)||thiseval==null)$end', 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉\n$select({\"values\":[true,false]})$end', - 'point': 'point可以在打败怪物后进行加点,详见文档说明\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', 'n': '多连击需要在后面指定n代表是几连击\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', 'atkValue':'退化时勇士下降的攻击力点数\n$range(thiseval==~~thiseval||thiseval==null)$end', 'defValue':'退化时勇士下降的防御力点数\n$range(thiseval==~~thiseval||thiseval==null)$end', diff --git a/project/data.comment.js b/project/data.comment.js index 8afb46af..5fc22fd5 100644 --- a/project/data.comment.js +++ b/project/data.comment.js @@ -160,7 +160,8 @@ data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = "bigKeyIsBox": " 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 \n$select({\"values\":[true,false]})$end", "equipment": " 剑和盾是否直接作为装备。如果此项为true,则作为装备,需要在道具栏使用,否则将直接加属性。 \n$select({\"values\":[true,false]})$end", "enableDeleteItem": " 是否允许删除(丢弃)道具 \n$select({\"values\":[true,false]})$end", - "enableNegativeDamage": " /****** 怪物相关 ******/ \n 是否支持负伤害(回血) \n$select({\"values\":[true,false]})$end", + "enableAddPoint": " /****** 怪物相关 ******/ \n 是否支持加点 \n$select({\"values\":[true,false]})$end", + "enableNegativeDamage": "是否支持负伤害(回血) \n$select({\"values\":[true,false]})$end", "hatredDecrease": " 是否在和仇恨怪战斗后减一半的仇恨值,此项为false则和仇恨怪不会扣减仇恨值。 \n$select({\"values\":[true,false]})$end", "betweenAttackCeil": " 夹击方式是向上取整还是向下取整。如果此项为true则为向上取整,为false则为向下取整 \n$select({\"values\":[true,false]})$end", "startDirectly": " /****** 系统相关 ******/ \n 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 \n$select({\"values\":[true,false]})$end", diff --git a/project/data.js b/project/data.js index 52d5d324..b63f74fc 100644 --- a/project/data.js +++ b/project/data.js @@ -145,17 +145,14 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = ] }, - "values" : { - - "HPMAX": 999999, // 各种数值;一些数值可以在这里设置 + "values" : { // 各种数值;一些数值可以在这里设置 /****** 角色相关 ******/ - // HP上限;-1则无上限 + "HPMAX": 999999, // HP上限;-1则无上限 "lavaDamage": 100, // 经过血网受到的伤害 "poisonDamage": 10, // 中毒后每步受到的伤害 "weakValue": 20, // 衰弱状态下攻防减少的数值 - - "redJewel": 3, /****** 道具相关 ******/ - // 红宝石加攻击的数值 + /****** 道具相关 ******/ + "redJewel": 3, // 红宝石加攻击的数值 "blueJewel": 3, // 蓝宝石加防御的数值 "greenJewel": 5, // 绿宝石加魔防的数值 "redPotion": 100, // 红血瓶加血数值 @@ -175,22 +172,18 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "sword5": 160, // 神圣剑加攻数值 "shield5": 160, // 神圣盾加防数值 "moneyPocket": 500, // 金钱袋加金币的数值 - - 'breakArmor': 0.9, /****** 怪物相关 ******/ - // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) + /****** 怪物相关 ******/ + 'breakArmor': 0.9, // 破甲的比例(战斗前,怪物附加角色防御的x%作为伤害) 'counterAttack': 0.1, // 反击的比例(战斗时,怪物每回合附加角色攻击的x%作为伤害,无视角色防御) 'purify': 3, // 净化的比例(战斗前,怪物附加勇士魔防的x倍作为伤害) 'hatred': 2, // 仇恨属性中,每杀死一个怪物获得的仇恨值 - - 'animateSpeed': 500, /****** 系统相关 ******/ - // 动画时间 + /****** 系统相关 ******/ + 'animateSpeed': 500, // 动画时间 }, - "flags" : { - - "enableFloor": true, // 系统FLAG,在游戏运行中中请不要修改它。 + "flags" : { // 系统FLAG,在游戏运行中中请不要修改它。 /****** 状态栏相关 ******/ - // 是否在状态栏显示当前楼层 + "enableFloor": true, // 是否在状态栏显示当前楼层 "enableLv": true, // 是否在状态栏显示当前等级 "enableMDef": true, // 是否在状态栏及战斗界面显示魔防(护盾) "enableMoney": true, // 是否在状态栏、怪物手册及战斗界面显示金币 @@ -198,22 +191,20 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "enableLevelUp": true, // 是否允许等级提升(进阶);如果上面enableExperience为false,则此项恒视为false "enableDebuff": true, // 是否涉及毒衰咒;如果此项为false则不会在状态栏中显示毒衰咒的debuff ////// 上述的几个开关将直接影响状态栏的显示效果 ////// - - "flyNearStair": true, /****** 道具相关 ******/ - // 是否需要在楼梯边使用传送器 + /****** 道具相关 ******/ + "flyNearStair": true, // 是否需要在楼梯边使用传送器 "pickaxeFourDirections": true, // 使用破墙镐是否四个方向都破坏;如果false则只破坏面前的墙壁 "bombFourDirections": true, // 使用炸弹是否四个方向都会炸;如果false则只炸面前的怪物(即和圣锤等价) "bigKeyIsBox": false, // 如果此项为true,则视为钥匙盒,红黄蓝钥匙+1;若为false,则视为大黄门钥匙 "equipment": false, // 剑和盾是否直接作为装备。如果此项为true,则作为装备,需要在道具栏使用,否则将直接加属性。 "enableDeleteItem": true, // 是否允许删除(丢弃)道具 - - "enableNegativeDamage": true, /****** 怪物相关 ******/ - // 是否支持负伤害(回血) + /****** 怪物相关 ******/ + "enableAddPoint": false, // 是否支持加点 + "enableNegativeDamage": true, // 是否支持负伤害(回血) "hatredDecrease": true, // 是否在和仇恨怪战斗后减一半的仇恨值,此项为false则和仇恨怪不会扣减仇恨值。 "betweenAttackCeil": false, // 夹击方式是向上取整还是向下取整。如果此项为true则为向上取整,为false则为向下取整 - - "startDirectly": false, /****** 系统相关 ******/ - // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 + /****** 系统相关 ******/ + "startDirectly": false, // 点击“开始游戏”后是否立刻开始游戏而不显示难度选择界面 "canOpenBattleAnimate": true, // 是否允许用户开启战斗过程;如果此项为false,则下面两项均强制视为false "showBattleAnimateConfirm": true, // 是否在游戏开始时提供“是否开启战斗动画”的选项 "battleAnimate": true, // 是否默认显示战斗动画;用户可以手动在菜单栏中开关 @@ -222,7 +213,7 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = "enableGentleClick": true, // 是否允许轻触(获得面前物品) "potionWhileRouting": false, // 寻路算法是否经过血瓶;如果该项为false,则寻路算法会自动尽量绕过血瓶 "enableViewMaps": true, // 是否支持在菜单栏中查看所有楼层的地图 - "portalWithoutTrigger": true, // 经过楼梯、传送门时是否能“穿透”。穿透的意思是,自动寻路得到的的路径中间经过了楼梯,行走时是否触发楼层转换事件 + "portalWithoutTrigger": true, // 是否支持穿透。所谓穿透,即当自动寻路经过楼梯时,不触发楼层转换事件而是穿过它。 "enableMoveDirectly": true, // 是否允许瞬间移动 } } \ No newline at end of file diff --git a/project/enemys.js b/project/enemys.js index fdc50724..1ee04c40 100644 --- a/project/enemys.js +++ b/project/enemys.js @@ -1,63 +1,63 @@ enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80 = { - 'greenSlime': {'name': '绿头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 1, 'experience': 1, 'special': [1,5,7,8]}, - 'redSlime': {'name': '红头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'blackSlime': {'name': '青头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'slimelord': {'name': '怪王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'special': [1,9]}, - 'bat': {'name': '小蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 2, 'experience': 0, 'special': 1}, - 'bigBat': {'name': '大蝙蝠', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redBat': {'name': '红蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 5, 'experience': 0, 'special': 4}, - 'vampire': {'name': '冥灵魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeleton': {'name': '骷髅人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonSoilder': {'name': '骷髅士兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonCaptain': {'name': '骷髅队长', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'ghostSkeleton': {'name': '冥队长', 'hp': 100, 'atk': 120, 'def': 0, 'money': 8, 'experience': 0, 'special': 7}, - 'zombie': {'name': '兽人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'zombieKnight': {'name': '兽人武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'rock': {'name': '石头人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 4, 'experience': 0, 'special': 3}, - 'slimeMan': {'name': '影子战士', 'hp': 100, 'atk': 0, 'def': 0, 'money': 11, 'experience': 0, 'special': [10,21], 'atkValue': 2, 'defValue': 3}, // 退化怪可以在后面写atkValue和defValue表示退化的数值 - 'bluePriest': {'name': '初级法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 3, 'experience': 0, 'special': 2, 'point': 1}, // 'point'可以在打败怪物后进行加点,详见文档说明。 - 'redPriest': {'name': '高级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'brownWizard': {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'special': 15, 'value': 100, 'range': 2}, // 领域怪需要加value表示领域伤害的数值;range可选,代表领域伤害的范围;不加默认为1 - 'redWizard': {'name': '高级巫师', 'hp': 1000, 'atk': 1200, 'def': 0, 'money': 160, 'experience': 0, 'special': 15, 'value': 200, 'zoneSquare': true}, // zoneSquare可选,代表是否九宫格伤害,true为是九宫格伤害,false或不设置为十字伤害 - 'yellowGuard': {'name': '初级卫兵', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'special': 0}, - 'blueGuard': {'name': '中级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redGuard': {'name': '高级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'swordsman': {'name': '双手剑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 6, 'experience': 0, 'special': [5,23]}, - 'soldier': {'name': '冥战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'yellowKnight': {'name': '金骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redKnight': {'name': '红骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'darkKnight': {'name': '黑骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'blackKing': {'name': '黑衣魔王', 'hp': 1000, 'atk': 500, 'def': 0, 'money': 1000, 'experience': 1000, 'special': 0, 'bomb': false}, // 加入 'bomb': false 代表该怪物不可被炸弹或圣锤炸掉 - 'yellowKing': {'name': '黄衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'greenKing': {'name': '青衣武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'blueKnight': {'name': '蓝骑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 9, 'experience': 0, 'special': 8}, - 'goldSlime': {'name': '黄头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'poisonSkeleton': {'name': '紫骷髅', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'poisonBat': {'name': '紫蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 14, 'experience': 0, 'special': 13}, - 'steelRock': {'name': '铁面人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonPriest': {'name': '骷髅法师', 'hp': 100, 'atk': 100, 'def': 0, 'money': 0, 'experience': 0, 'special': 18, 'value': 20}, - 'skeletonKing': {'name': '骷髅王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'skeletonWizard': {'name': '骷髅巫师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redSkeletonCaption': {'name': '骷髅武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'badHero': {'name': '迷失勇者', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'demon': {'name': '魔神武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'demonPriest': {'name': '魔神法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'goldHornSlime': {'name': '金角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redKing': {'name': '红衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'whiteKing': {'name': '白衣武士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 17, 'experience': 0, 'special': 16}, - 'blackMagician': {'name': '黑暗大法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 12, 'experience': 0, 'special': 11, 'value': 1/3, 'add': true, 'bomb': false}, // 吸血怪需要在后面添加value代表吸血比例;添加add: true可以将吸血的伤害加到自身 - 'silverSlime': {'name': '银头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 15, 'experience': 0, 'special': 14}, - 'swordEmperor': {'name': '剑圣', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'whiteHornSlime': {'name': '尖角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'badPrincess': {'name': '痛苦魔女', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'badFairy': {'name': '黑暗仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'grayPriest': {'name': '中级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'redSwordsman': {'name': '剑王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 7, 'experience': 0, 'special': 6, 'n': 8}, // 多连击需要在后面指定n代表是几连击 - 'whiteGhost': {'name': '水银战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'poisonZombie': {'name': '绿兽人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 13, 'experience': 0, 'special': 12}, - 'magicDragon': {'name': '魔龙', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'octopus': {'name': '血影', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'darkFairy': {'name': '仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, - 'greenKnight': {'name': '强盾骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'special': 0}, + 'greenSlime': {'name': '绿头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 1, 'experience': 1, 'point': 0, 'special': [1,5,7,8]}, + 'redSlime': {'name': '红头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'blackSlime': {'name': '青头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'slimelord': {'name': '怪王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'point': 0, 'special': [1,9]}, + 'bat': {'name': '小蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 2, 'experience': 0, 'point': 0, 'special': 1}, + 'bigBat': {'name': '大蝙蝠', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'redBat': {'name': '红蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 5, 'experience': 0, 'point': 0, 'special': 4}, + 'vampire': {'name': '冥灵魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'skeleton': {'name': '骷髅人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'skeletonSoilder': {'name': '骷髅士兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'skeletonCaptain': {'name': '骷髅队长', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'ghostSkeleton': {'name': '冥队长', 'hp': 100, 'atk': 120, 'def': 0, 'money': 8, 'experience': 0, 'point': 0, 'special': 7}, + 'zombie': {'name': '兽人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'zombieKnight': {'name': '兽人武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'rock': {'name': '石头人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 4, 'experience': 0, 'point': 0, 'special': 3}, + 'slimeMan': {'name': '影子战士', 'hp': 100, 'atk': 0, 'def': 0, 'money': 11, 'experience': 0, 'point': 0, 'special': [10,21], 'atkValue': 2, 'defValue': 3}, // 退化怪可以在后面写atkValue和defValue表示退化的数值 + 'bluePriest': {'name': '初级法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 3, 'experience': 0, 'point': 1, 'special': 2}, + 'redPriest': {'name': '高级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'brownWizard': {'name': '初级巫师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 16, 'experience': 0, 'point': 0, 'special': 15, 'value': 100, 'range': 2}, // 领域怪需要加value表示领域伤害的数值;range可选,代表领域伤害的范围;不加默认为1 + 'redWizard': {'name': '高级巫师', 'hp': 1000, 'atk': 1200, 'def': 0, 'money': 160, 'experience': 0, 'point': 0, 'special': 15, 'value': 200, 'zoneSquare': true}, // zoneSquare可选,代表是否九宫格伤害,true为是九宫格伤害,false或不设置为十字伤害 + 'yellowGuard': {'name': '初级卫兵', 'hp': 100, 'atk': 120, 'def': 0, 'money': 10, 'experience': 0, 'point': 0, 'special': 0}, + 'blueGuard': {'name': '中级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'redGuard': {'name': '高级卫兵', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'swordsman': {'name': '双手剑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 6, 'experience': 0, 'point': 0, 'special': [5,23]}, + 'soldier': {'name': '冥战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'yellowKnight': {'name': '金骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'redKnight': {'name': '红骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'darkKnight': {'name': '黑骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'blackKing': {'name': '黑衣魔王', 'hp': 1000, 'atk': 500, 'def': 0, 'money': 1000, 'experience': 1000, 'point': 0, 'special': 0, 'bomb': false}, // 加入 'bomb': false 代表该怪物不可被炸弹或圣锤炸掉 + 'yellowKing': {'name': '黄衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'greenKing': {'name': '青衣武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'blueKnight': {'name': '蓝骑士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 9, 'experience': 0, 'point': 0, 'special': 8}, + 'goldSlime': {'name': '黄头怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'poisonSkeleton': {'name': '紫骷髅', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'poisonBat': {'name': '紫蝙蝠', 'hp': 100, 'atk': 120, 'def': 0, 'money': 14, 'experience': 0, 'point': 0, 'special': 13}, + 'steelRock': {'name': '铁面人', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'skeletonPriest': {'name': '骷髅法师', 'hp': 100, 'atk': 100, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 18, 'value': 20}, + 'skeletonKing': {'name': '骷髅王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'skeletonWizard': {'name': '骷髅巫师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'redSkeletonCaption': {'name': '骷髅武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'badHero': {'name': '迷失勇者', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'demon': {'name': '魔神武士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'demonPriest': {'name': '魔神法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'goldHornSlime': {'name': '金角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'redKing': {'name': '红衣魔王', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'whiteKing': {'name': '白衣武士', 'hp': 100, 'atk': 120, 'def': 0, 'money': 17, 'experience': 0, 'point': 0, 'special': 16}, + 'blackMagician': {'name': '黑暗大法师', 'hp': 100, 'atk': 120, 'def': 0, 'money': 12, 'experience': 0, 'point': 0, 'special': 11, 'value': 1/3, 'add': true, 'bomb': false}, // 吸血怪需要在后面添加value代表吸血比例;添加add: true可以将吸血的伤害加到自身 + 'silverSlime': {'name': '银头怪', 'hp': 100, 'atk': 120, 'def': 0, 'money': 15, 'experience': 0, 'point': 0, 'special': 14}, + 'swordEmperor': {'name': '剑圣', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'whiteHornSlime': {'name': '尖角怪', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'badPrincess': {'name': '痛苦魔女', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'badFairy': {'name': '黑暗仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'grayPriest': {'name': '中级法师', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'redSwordsman': {'name': '剑王', 'hp': 100, 'atk': 120, 'def': 0, 'money': 7, 'experience': 0, 'point': 0, 'special': 6, 'n': 8}, // 多连击需要在后面指定n代表是几连击 + 'whiteGhost': {'name': '水银战士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'poisonZombie': {'name': '绿兽人', 'hp': 100, 'atk': 120, 'def': 0, 'money': 13, 'experience': 0, 'point': 0, 'special': 12}, + 'magicDragon': {'name': '魔龙', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'octopus': {'name': '血影', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'darkFairy': {'name': '仙子', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, + 'greenKnight': {'name': '强盾骑士', 'hp': 0, 'atk': 0, 'def': 0, 'money': 0, 'experience': 0, 'point': 0, 'special': 0}, } \ No newline at end of file diff --git a/project/functions.js b/project/functions.js index 20059376..e57a38d7 100644 --- a/project/functions.js +++ b/project/functions.js @@ -72,7 +72,7 @@ functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = "addPoint" : function (enemy) { // 加点事件 var point = enemy.point; - if (!core.isset(point) || point<=0) return []; + if (!core.flags.enableAddPoint || !core.isset(point) || point<=0) return []; // 加点,返回一个choices事件 return [ From ce0e80c4fa6170522028b747026f92411fe872bb Mon Sep 17 00:00:00 2001 From: ckcz123 Date: Sat, 10 Mar 2018 18:48:31 +0800 Subject: [PATCH 076/102] drawText & replay --- libs/ui.js | 2 +- project/data.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/libs/ui.js b/libs/ui.js index 658d42a5..7160ebf4 100644 --- a/libs/ui.js +++ b/libs/ui.js @@ -219,7 +219,7 @@ ui.prototype.drawText = function (contents, callback) { if (core.isset(contents)) { // 合并 - if (core.isset(core.status.event)&&core.status.event.id=='action') { + if ((core.isset(core.status.event)&&core.status.event.id=='action') || (core.isset(core.status.replay)&&core.status.replay.replaying)) { core.insertAction(contents,null,null,callback); return; } diff --git a/project/data.js b/project/data.js index b63f74fc..f1ffcbc6 100644 --- a/project/data.js +++ b/project/data.js @@ -135,7 +135,7 @@ data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d = {"need": 40, "effect": function () { - core.drawText("恭喜升级!"); + core.insertAction("恭喜升级!"); core.status.hero.hp *= 2; core.status.hero.atk += 100; core.status.hero.def += 100; From 46d4d77bde27463188ce2fd22e978c101772ac6d Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 10 Mar 2018 19:36:53 +0800 Subject: [PATCH 077/102] =?UTF-8?q?fix=20bug=20=E4=BB=A5=E5=8F=8A=E8=B0=83?= =?UTF-8?q?=E6=95=B4=E8=BF=BD=E5=8A=A0=E7=B4=A0=E6=9D=90=E7=9A=84=E5=AD=97?= =?UTF-8?q?=E4=BD=93?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- _server/README.md | 64 ++++++++++++++++++++++++++++++++----- _server/css/editor_mode.css | 6 ++++ _server/editor_file.js | 48 ++++++++++++++-------------- _server/editor_mode.js | 1 - _server/editor_multi.js | 4 +-- editor.html | 8 ++--- project/comment.js | 1 + 7 files changed, 93 insertions(+), 39 deletions(-) diff --git a/_server/README.md b/_server/README.md index e75cf35d..d074b9d5 100644 --- a/_server/README.md +++ b/_server/README.md @@ -2,15 +2,20 @@ 本目录下所有文件,以及`../editor.html`和`../启动服务.exe`([源码](http://github.com/ckcz123/mota-js-server/))是地图编辑器的所有组件. -`editor.js`,`editor_file.js`和`editor_mode.js`耦合较强,`editor_blockly.js`和`fs.js`基本可以独立使用. +`editor.js`,`editor_file.js`和`editor_mode.js`耦合较强,`editor_blockly.js`和`editor_multi.js`和`fs.js`基本可以独立使用. ## 各组件功能 ### editor.js -暂略 +``` js +editor.mapInit();//清空地图 +editor.changeFloor('MT2')//切换地图 +editor.guid()//产生一个可以作为id的长随机字符串 +``` ### editor_file.js + 提供了以下函数进行楼层`map`数组相关的操作 ```javascript editor.file.getFloorFileList @@ -18,6 +23,7 @@ editor.file.loadFloorFile editor.file.saveFloorFile editor.file.saveFloorFileAs ``` + 编辑模式有关的查询 ```javascript editor.file.editItem('redJewel',[],function(a){console.log(a)}); @@ -27,6 +33,7 @@ editor.file.editFloor([],function(a){console.log(a)}); editor.file.editTower([],function(a){console.log(a)}); editor.file.editFunctions([],function(a){console.log(a)}); ``` + 编辑模式有关的编辑 ```javascript editor.info={images: "terrains", y: 9}; @@ -40,7 +47,7 @@ editor.file.editFunctions(["change","['events']['afterChangeLight']","function(x ``` ### editor_mode.js -5个生成表格并绑定事件的函数 +生成表格并绑定事件的函数 ```javascript editor.mode.loc(); editor.mode.emenyitem(); @@ -48,6 +55,7 @@ editor.mode.floor(); editor.mode.tower(); editor.mode.functions(); ``` + 切换模式 ```javascript editor.mode.onmode('');//清空 @@ -72,24 +80,64 @@ while (!editor_mode._ids.hasOwnProperty(node.getAttribute('id'))) { } editor_mode.onmode(editor_mode._ids[node.getAttribute('id')]); ``` + +`editor.mode.listen`中提供了追加素材的支持. + ### editor_blockly.js + 把选定`id_`的事件用blockly编辑 ``` js editor_blockly.import(id_); ``` + 把文本区域的代码转换成图块 ``` js editor_blockly.parse(); ``` -把当前图块对应的事件返回给调用blockly的`id_` + +### editor_multi.js + +用[CodeMirror](https://github.com/codemirror/CodeMirror) 实现有高亮的多行文本编辑 + +编辑选定`id_`的文本域 ``` js -editor_blockly.confirm(); +editor_multi.import(id_) ``` -### 待调整 +编辑blockly方块的特定域 +``` js +editor_multi.multiLineEdit(value,b,f,callback) +``` -+ [x] 多行文本编辑器独立作为组件 -+ [x] editor_multi.js +### fs.js + +模仿node的fs模块提供如下api,与`启动服务.exe`配合为js提供文件读写功能 +``` js +fs.readFile('file.in','utf-8',callback) +//读文本文件 +//callback:function(err, data) +//data:字符串 +fs.readFile('file.in','base64',callback) +//读二进制文件 +//callback:function(err, data) +//data:base64字符串 + +fs.writeFile('file.out', data ,'utf-8', callback) +//写文本文件 +//callback:function(err) +//data:字符串 +fs.writeFile('file.out', data ,'base64', callback) +//写二进制文件 +//callback:function(err) +//data:base64字符串 + +fs.readdir(path, callback) +//callback:function(err, data) +//path:支持"/"做分隔符 +//data:[filename1,filename2,..] filename是字符串,只包含文件不包含目录 + +//所有参数不允许缺省 +``` ## z-index diff --git a/_server/css/editor_mode.css b/_server/css/editor_mode.css index e260377c..9dc1d587 100644 --- a/_server/css/editor_mode.css +++ b/_server/css/editor_mode.css @@ -19,6 +19,11 @@ width: 435px; } +#appendPicSelection span { + font-size:11px; + -webkit-text-stroke: 1px black; +} + #left6 { left: 5px; /* top: 1930px; */ @@ -87,6 +92,7 @@ background-color: #f6f8fa; } /* copy end --------------------------------------------- */ + .etable tr {width:100%} .etable tr > :nth-child(1) {width:20%} .etable tr > :nth-child(2) {width:20%} diff --git a/_server/editor_file.js b/_server/editor_file.js index 966b3b00..b5a853b4 100644 --- a/_server/editor_file.js +++ b/_server/editor_file.js @@ -175,11 +175,11 @@ editor_file = function(editor, callback){ saveSetting('items',actionList,function (err) { callback([ {'items':(function(){ - var locObj={}; + var locObj=Object.assign({},editor.core.items.items[id]); Object.keys(editor_file.comment.items.items).forEach(function(v){ - if (isset(editor.core.items.items[id][v])) - locObj[v]=editor.core.items.items[id][v]; - else + if (!isset(editor.core.items.items[id][v])) + /* locObj[v]=editor.core.items.items[id][v]; + else */ locObj[v]=null; }); return locObj; @@ -191,11 +191,11 @@ editor_file = function(editor, callback){ } else { callback([ {'items':(function(){ - var locObj={}; + var locObj=Object.assign({},editor.core.items.items[id]); Object.keys(editor_file.comment.items.items).forEach(function(v){ - if (isset(editor.core.items.items[id][v])) - locObj[v]=editor.core.items.items[id][v]; - else + if (!isset(editor.core.items.items[id][v])) + /* locObj[v]=editor.core.items.items[id][v]; + else */ locObj[v]=null; }); return locObj; @@ -223,11 +223,11 @@ editor_file = function(editor, callback){ saveSetting('enemys',actionList,function (err) { callback([ (function(){ - var locObj={}; + var locObj=Object.assign({},editor.core.enemys.enemys[id]); Object.keys(editor_file.comment.enemys).forEach(function(v){ - if (isset(editor.core.enemys.enemys[id][v])) - locObj[v]=editor.core.enemys.enemys[id][v]; - else + if (!isset(editor.core.enemys.enemys[id][v])) + /* locObj[v]=editor.core.enemys.enemys[id][v]; + else */ locObj[v]=null; }); return locObj; @@ -238,11 +238,11 @@ editor_file = function(editor, callback){ } else { callback([ (function(){ - var locObj={}; + var locObj=Object.assign({},editor.core.enemys.enemys[id]); Object.keys(editor_file.comment.enemys).forEach(function(v){ - if (isset(editor.core.enemys.enemys[id][v])) - locObj[v]=editor.core.enemys.enemys[id][v]; - else + if (!isset(editor.core.enemys.enemys[id][v])) + /* locObj[v]=editor.core.enemys.enemys[id][v]; + else */ locObj[v]=null; }); return locObj; @@ -315,11 +315,11 @@ editor_file = function(editor, callback){ saveSetting('floors',actionList,function (err) { callback([ (function(){ - var locObj={}; + var locObj=Object.assign({},editor.currentFloorData); Object.keys(editor_file.comment.floors.floor).forEach(function(v){ - if (isset(editor.currentFloorData[v])) - locObj[v]=editor.currentFloorData[v]; - else + if (!isset(editor.currentFloorData[v])) + /* locObj[v]=editor.currentFloorData[v]; + else */ locObj[v]=null; }); return locObj; @@ -330,11 +330,11 @@ editor_file = function(editor, callback){ } else { callback([ (function(){ - var locObj={}; + var locObj=Object.assign({},editor.currentFloorData); Object.keys(editor_file.comment.floors.floor).forEach(function(v){ - if (isset(editor.currentFloorData[v])) - locObj[v]=editor.currentFloorData[v]; - else + if (!isset(editor.currentFloorData[v])) + /* locObj[v]=editor.currentFloorData[v]; + else */ locObj[v]=null; }); return locObj; diff --git a/_server/editor_mode.js b/_server/editor_mode.js index 83c51823..d48e222e 100644 --- a/_server/editor_mode.js +++ b/_server/editor_mode.js @@ -371,7 +371,6 @@ editor_mode.prototype.listen = function(callback){ selectAppend.onchange(); var selectFileBtn = document.getElementById('selectFileBtn'); - var selectFileStr = document.getElementById('selectFileStr'); selectFileBtn.onclick = function(){ var loadImage = function (content, callback) { var image = new Image(); diff --git a/_server/editor_multi.js b/_server/editor_multi.js index 556096f7..e536d17e 100644 --- a/_server/editor_multi.js +++ b/_server/editor_multi.js @@ -29,7 +29,7 @@ editor_multi.import = function(id_){ editor_multi.isString=true; codeEditor.setValue(JSON.parse(input.value)||''); } else { - eval('var tobj='+input.value); + eval('var tobj='+(input.value||'null')); var tmap={}; var tstr = JSON.stringify(tobj,function(k,v){if(typeof(v)===typeof('') && v.slice(0,8)==='function'){var id_ = editor.guid();tmap[id_]=v.toString();return id_;}else return v},4); for(var id_ in tmap){ @@ -64,7 +64,7 @@ editor_multi.confirm = function (){ if(editor_multi.isString){ input.value = JSON.stringify(value); } else { - eval('var tobj='+value); + eval('var tobj='+(value||'null')); var tmap={}; var tstr = JSON.stringify(tobj,function(k,v){if(v instanceof Function){var id_ = editor.guid();tmap[id_]=v.toString();return id_;}else return v},4); for(var id_ in tmap){ diff --git a/editor.html b/editor.html index 494ac186..243bb2e8 100644 --- a/editor.html +++ b/editor.html @@ -49,10 +49,10 @@
-
1
-
  2
-
    3
-
      4
+
1
+
  2
+
    3
+
      4
diff --git a/project/comment.js b/project/comment.js index dfd1aed8..5ca2803e 100644 --- a/project/comment.js +++ b/project/comment.js @@ -25,6 +25,7 @@ comment_c456ea59_6018_45ef_8bcc_211a24c627dc = 'bomb':' 加入 "bomb": false 代表该怪物不可被炸弹或圣锤炸掉\n$select({\"values\":[true,false]})$end', 'point': 'point可以在打败怪物后进行加点,详见文档说明\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', 'n': '多连击需要在后面指定n代表是几连击\n$range((thiseval==~~thiseval && thiseval>0)||thiseval==null)$end', + 'add': '代表吸血后是否加到自身\n$select({\"values\":[true,false]})$end', 'atkValue':'退化时勇士下降的攻击力点数\n$range(thiseval==~~thiseval||thiseval==null)$end', 'defValue':'退化时勇士下降的防御力点数\n$range(thiseval==~~thiseval||thiseval==null)$end', 'damage':'战前扣血的点数\n$range(thiseval==~~thiseval||thiseval==null)$end' From 628d7eeafadc281961b055546c7b4735de9fb8a5 Mon Sep 17 00:00:00 2001 From: YouWei Zhao Date: Sat, 10 Mar 2018 20:07:16 +0800 Subject: [PATCH 078/102] =?UTF-8?q?=E5=88=A0=E9=99=A4=E8=BF=87=E6=97=B6?= =?UTF-8?q?=E7=9A=84=E6=96=87=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 已经无法工作的editor_file_test.html 旧版的blockly 已经无效的2.0diff --- 2.0diff.md | 149 --- _server/README.md | 38 + _server/blockly/motaActionBlocks.js | 1129 --------------------- _server/blockly/motaActionBlockyDemo.html | 557 ---------- _server/editor_file_test.html | 46 - main.js | 2 +- test_main_init_mode.html | 152 --- 7 files changed, 39 insertions(+), 2034 deletions(-) delete mode 100644 2.0diff.md delete mode 100644 _server/blockly/motaActionBlocks.js delete mode 100644 _server/blockly/motaActionBlockyDemo.html delete mode 100644 _server/editor_file_test.html delete mode 100644 test_main_init_mode.html diff --git a/2.0diff.md b/2.0diff.md deleted file mode 100644 index 2eb12662..00000000 --- a/2.0diff.md +++ /dev/null @@ -1,149 +0,0 @@ -# v2.0目前的改动 - -## 总体上: - -部分重构了运行时 -+ 把`libs`中的数据分离出来保存为类似json的js文件,分离后的数据进一步分离为纯数据和注释两部分 -+ 更改目录结构,分离后的`libs`一般无需修改,把数据楼层文件声音图片放入`project`目录中 - * 需要相应的修改地图生成器和js压缩工具 -+ 设置了三个模式`play|editor|replay`在`editor`模式关闭了部分动画,并且角色无法行动 - -重构editor -+ 重命名为`editor.html` - * 需要相应的修改本地服务的按钮打开的网址,为了兼容,临时加了个内容为``的`drawMapGUI.html` -+ 不再独立的导入数据和画图,尽可能的通过`main.init('editor')`复用代码 -+ 能够在本地服务器环境中直接修改`project`中的数据,即全GUI下做塔 -+ 把`editor`的代码拆到了`_server/editor.js`中 -+ 添加了`_server/css/editor_mode.css`存放编辑模式有关的样式 -+ 添加了`_server/editor_mode.js`存放编辑模式的实现 - -## 具体: - -### main.js -用户修改内容转移到了`project/data.js`中 - -把事件监听打包成了`main.prototype.listen` - -`main.listen`和`main.init`改为在`index.html`中执行 - -添加了`main.prototype.loadPureData`,在`main.init`中先加载纯数据再加载`libs` - -### core.js -`core.drawMap`中`editor`模式下不再画图,而是生成画图的函数提供给`editor` - -`editor`模式下`GlobalAnimate`可以独立的选择是否播放 - -`core.playBgm`和`core.playSound`中非`play`模式不再播放声音 - -`core.show`和`core.hide`中非`play`模式不再进行动画而是立刻完成并执行回调 - -`editor`模式不执行`core.resize` - -### data.js -数据转移到了`project/data.js`中 - -注释转移到了`project/data.comment.js`中 - -### enemy.js,items.js,maps.js,icons.js -数据转移到了`project`下的同名文件中 - -注释转移到了`project/comment.js`中 - -### editor_file.js -提供了以下函数进行楼层`map`数组相关的操作 -```javascript -editor.file.getFloorFileList -editor.file.loadFloorFile -editor.file.saveFloorFile -editor.file.saveFloorFileAs -``` -5个编辑模式有关的查询 -```javascript -editor.file.editItem('redJewel',[],function(a){console.log(a)}); -editor.file.editEnemy('redBat',[],function(a){console.log(a)}); -editor.file.editLoc(2,0,[],function(a){console.log(a)}); -editor.file.editFloor([],function(a){console.log(a)}); -editor.file.editTower([],function(a){console.log(a)}); -``` -5个编辑模式有关的编辑 -```javascript -editor.info={images: "terrains", y: 9}; -editor.file.changeIdAndIdnum('yellowWall2',16,editor.info,function(a){console.log(a)}); -editor.file.editItem('book',[["change","['items']['name']","怪物手册的新名字"]],function(a){console.log(a)}); -editor.file.editEnemy('redBat',[['change',"['atk']",20]],function(a){console.log(a)}); -editor.file.editLoc(2,6,[["change","['afterBattle']",null]],function(a){console.log(a)}); -editor.file.editFloor([["change","['title']",'样板 33 层']],function(a){console.log(a)}); -editor.file.editTower([["change","['values']['lavaDamage']",200]],function(a){console.log(a)}); -``` - -### editor_mode.js -4个生成表格并绑定事件的函数 -```javascript -editor.mode.loc(); -editor.mode.emenyitem(); -editor.mode.floor(); -editor.mode.tower(); -``` -切换模式 -```javascript -editor.mode.onmode(''); -editor.mode.onmode('loc'); -editor.mode.onmode('emenyitem'); -editor.mode.onmode('floor'); -editor.mode.onmode('tower'); -``` -在切换模式时,改动才会保存到文件,并且需要刷新页面使得`editor`能看到改动 - -表格的`onchange`的实现中,获得当前模式的方式.不注意的话,修改`index.html`中页面的结构,会被坑 -```javascript -var node = thisTr.parentNode; -while (!editor_mode._ids.hasOwnProperty(node.getAttribute('id'))) { - node = node.parentNode; -} -editor_mode.onmode(editor_mode._ids[node.getAttribute('id')]); -``` -### drawMapGUI.html -重命名为`editor.html` - -把`editor`的代码拆到了`_server/editor.js`中 - -以`display:none`的形式引入了`index.html`的`dom`,修改了原来的`.gameCanvas #ui #data`等的名字以避免冲突 - -通过`main.init('editor')`加载数据,移除了原有的`editor.loadjs`等 - -背景层如果未设置`editor.bgY`则通过运行时中的代码画背景 - -`editor.updateMap`中只画未定义快的报错,其他的由运行时中的代码完成 - -`editor.ids[0] = 0; editor.indexs[0]=[0];` - -添加了`editor.changeFloor`用于切换楼层 - -### 注释的特殊指令 -``` -$range(evalstr:thiseval)$end - 限制取值范围,要求修改后的eval(evalstr)为true -$leaf(evalstr:thiseval)$end - 强制指定为叶节点,如果eval(evalstr)为true - -//以下几个中选一个 [ -$select(evalstr)$end - 渲染成 -$textarea(evalstr)$end - 渲染成 @@ -183,6 +182,9 @@ +



+ +
条目注释