Merge pull request #5 from ckcz123/v2.x

V2.x
This commit is contained in:
AutumnOrange51 2020-06-04 16:39:55 +08:00 committed by GitHub
commit 19b7067f3c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
60 changed files with 2707 additions and 1566 deletions

3
.gitignore vendored
View File

@ -54,4 +54,5 @@ crashlytics-build.properties
fabric.properties
node_modules
package-lock.json

View File

@ -4,4 +4,5 @@
- [事件](event)
- [个性化](personalization)
- [脚本](script)
- [修改编辑器](editor)
- [附录API列表](api)

55
_docs/blocksdemo.md Normal file
View File

@ -0,0 +1,55 @@
http://127.0.0.1:1055/_docs/#/blocksdemo
方便测试用
这种写法不会生成按钮
```js
'run';
return bg.parseList(['行内']);
// return bg.parse(['asdasd','df'],'event')+'<br>'+bg.parseList(['asfewg','sty']);
```
并且是行内的
这种写法之后的版本会补一个按钮'添加到常用事件', 目前先这样吧
``` MotaAction.event
[
'显示文章',
'...'
]
```
``` MotaAction.shop
[{
"id": "shop1",
"text": "\t[贪婪之神,moneyShop]勇敢的武士啊, 给我${20+2*flag:shop1}金币就可以:",
"textInList": "1F金币商店",
"choices": [
{"text": "生命+800", "need": "status:money>=20+2*flag:shop1", "action": [
{"type": "setValue", "name": "status:money", "operator": "-=", "value": "20+2*flag:shop1"},
{"type": "setValue", "name": "flag:shop1", "operator": "+=", "value": "1"},
{"type": "setValue", "name": "status:hp", "operator": "+=", "value": "800"}
]}
]
},{
"id": "itemShop",
"item": true,
"textInList": "道具商店",
"choices": [
{"id": "yellowKey", "number": 10, "money": 10}
]
},{
"id": "keyShop1",
"textInList": "回收钥匙商店",
"commonEvent": "回收钥匙商店",
"args": ""
}]
```
``` MotaAction.action
'显示文章'
```
``` MotaAction
['MotaAction.action的anction可以省略','只写MotaAction']
```

314
_docs/editor.md Normal file
View File

@ -0,0 +1,314 @@
# 修改编辑器
在改动core时, 有时会相应的更改project中存储数据的结构, 而表格和事件编辑器不做相应更改的话就无法顺畅的编辑改动了结构的数据了, 此文档帮助造塔者进行`配置表格`的修改, 以及修改_server/MotaAction.g4和其他相关文件来调整事件编辑器的图块.
## 修改表格
### demo - 给怪物增加 _速度_ 属性
点击素材区的怪物后点击配置表格, 或者直接打开_server/table/comment.js
拉到`【怪物】相关的表格配置`的部分
``` js
// --------------------------- 【怪物】相关的表格配置 --------------------------- //
"enemys": {
"_type": "object",
"_data": {
"id": {
"_leaf": true,
"_type": "disable",
"_docs": "怪物ID",
"_data": "怪物ID可于页面底部修改"
},
"name": {
"_leaf": true,
"_type": "textarea",
"_string": true,
"_data": "名称"
},
"displayIdInBook": {
"_leaf": true,
"_type": "textarea",
"_string": true,
"_docs": "手册映射ID",
"_data": "在怪物手册中映射到的怪物ID。如果此项不为null则在怪物手册中将用目标ID来替换该怪物原本的ID。常被运用在同一个怪物的多朝向上。"
},
"hp": {
"_leaf": true,
"_type": "textarea",
"_data": "生命值"
},
"atk": {
"_leaf": true,
"_type": "textarea",
"_data": "攻击力"
},
```
可以看到, project/enemys.js 中怪物的属性
```js
"greenSlime": {"name":"绿头怪","hp":100,"atk":120,"def":0,"money":1,"exp":1,"point":0,"special":[1,5,7,8]},
```
被逐条列出并解释
把hp的部分复制一份并修改
```js
"speed": {
"_leaf": true,
"_type": "textarea",
"_data": "速度"
},
```
刷新之后, 怪物的表格在hp下面就多出了speed一项, 编辑后出现在了怪物属性中
```js
"greenSlime": {"name":"绿头怪","hp":100,"atk":120,"def":0,"money":1,"exp":1,"point":0,"special":[1,5,7,8],"speed":123123},
```
### 表格配置项含义
可以看出表格配置中的对象是一层套一层的结构, `_`开头的和数据的名字间隔着展开, 忽略所有`_`的层级的话, 这个对象和project中的对象是有相同的结构
**_leaf** 为真的项对应的数据将作为表格的编辑的内容, 数字/字符串/空对象和数组会被自动计算为true, 非空的对象和数组会被计算为false, 手动填写_leaf的值可以强制不展开对象和数组来进行编辑
**_type** 决定了表格如何展示该数据
+ select 使用下拉菜单展示
+ checkbox 使用勾选框展示
+ checkboxSet 使用勾选框组展示
+ 其他 使用文本框展示, 根据类型区分, 双击或点编辑会有以下行为
- textarea 文本编辑器(_type的默认值)
- event 事件编辑器
- material 素材选取
- color 取色器
- point 地图选点
- disable 不允许编辑
- popCheckBoxSet 以弹窗形式多选框
当某个event例如 门信息编辑 无法适应修改后的数据结构, 可以修改事件编辑器, 也可以把_type改成textarea
以上类型的格式要如何写请搜索例如`"_type": "checkboxSet"`来查找例子, 此处不展示
**_range** 被编辑的值会作为`thiseval`来进行检测, 当字符串为真时才接收这个值, 同时当删除表格时会判定_range是否接收null
**拓展性**
注意这是js文件, 可以使用表达式, 如下例子引用了别处的数据作为下拉菜单
```js
"bgm": {
"_leaf": true,
"_type": "select",
"_select": {
"values": [null].concat(Object.keys(editor.core.material.bgms))
},
"_docs": "背景音乐",
"_data": "到达该层后默认播放的BGM"
},
```
同时`_`开头的项可以使用函数. 同一级中`_data`最先被计算. 复杂的结构的注释可以利用函数动态生成
`_data`的参数`key`是各子项的名字, 其他`_`开头的参数是`args`详见editor_table.prototype.objToTable的注释
例如: 自动事件数组, `"_leaf": false`强制展开, 通过`_action`函数即使为空也显示两个空白的项, 同时`_data`函数给自动事件的每一项标记为event
```js
"autoEvent": {
"_type": "object",
"_leaf": false,
"_action": function (args) {
args.vobj = args.vobj || {};
for (var ii = 0; ii < 2; ii++) {
args.vobj[ii] = args.vobj[ii] || null;
}
},
"_data": function (key) {
return {
"_leaf": true,
"_type": "event",
"_event": "autoEvent",
"_data": "自动事件"
}
}
},
```
## 修改事件编辑器
_type为event的表格项, 在双击时会进入事件编辑器. 是由[antlr-blockly](https://github.com/zhaouv/antlr-blockly)生成的图块式的可视化编辑器
_event的内容例如autoEvent则是使用的入口图块的类型
请先查看[antlr-blockly的文档](https://zhaouv.github.io/antlr-blockly/docs/#/README)来了解.g4语法文件和可视化编辑器blockly以及库antlr-blockly的基础知识
### 事件编辑器的运行机制简介
事件编辑器编辑一个表格项的流程有以下几步
+ 加载表格中的json, 将其根据类别转化成图块
+ 通过拖拽填写图块编辑内容
+ 将图块转化回json置入表格
其中图块到json 是由_server/MotaAction.g4完成的
json到图块 是由_server/MotaActionParser.js完成的, 并依赖图块在g4中的定义
图块到json首先由入口方块出发, 入口方块又依次去获取了嵌入在其中的方块和域, 嵌入的方块再递归访问其嵌入的内容, 从而访问了所有方块上域中的信息.
例如 event_m 通过 action_0 获取了其中嵌入的所有语句生成的json, 插入到其自身的键'data'中
```antlr
//事件 事件编辑器入口之一
event_m
: '事件' BGNL? Newline '覆盖触发器' Bool '启用' Bool '通行状态' B_0_List '显伤' Bool BGNL? Newline action+ BEND
/* event_m
tooltip : 编辑魔塔的事件
helpUrl : https://h5mota.com/games/template/_docs/#/event
default : [false,null,null,null,null]
B_0_List_0=eval(B_0_List_0);
var code = {
'trigger': Bool_0?'action':null,
'enable': Bool_1,
'noPass': B_0_List_0,
'displayDamage': Bool_2,
'data': 'data_asdfefw'
}
if (!Bool_0 && Bool_1 && (B_0_List_0===null) && Bool_2) code = 'data_asdfefw';
code=JSON.stringify(code,null,2).split('"data_asdfefw"').join('[\n'+action_0+']\n');
return code;
*/;
```
值得注意的是shoplist和action这样的语句集合, 语句集合会选择其中的最后一项作为父方块的默认块, 所以在希望其允许空时, 要制作一个空项放在语句集合定义的末尾, 例如
```antlr
shoplist
: shopsub
| shopitem
| shopcommonevent
| emptyshop
;
emptyshop
: Newline
/* emptyshop
var code = ' \n';
return code;
*/;
```
json到图块则是从ActionParser.prototype.parse出发, 递归的将js对象变为图块, 例如event类型的json, 使用event_m入口图块, 将obj.trigger/enable/noPass/displayDamage填到域中, obj.data交给this.parseList转化为语句的图块, 与g4中注入的语句做相反的事情
```js
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([
obj.trigger==='action',obj.enable,obj.noPass,obj.displayDamage,this.parseList(obj.data)
]);
```
### demo - 给已有图块添加新域
例如给'播放背景音乐'图块再额外加一个参数列表
不熟悉时, 对任意图块来说这都算是最简单粗暴的修改方式了, 复杂的修改需求也只需要改这一下, 只是填图块时没那么方便
编辑g4时推荐使用vscode, 搜索并安装插件mota-js
<pre><code>playBgm_s
: '播放背景音乐' EvalString '开始播放秒数' Int '持续到下个本事件' Bool <b style='color:green'>'参数列表' JsonEvalString?</b> Newline
/* playBgm_s
tooltip : playBgm: 播放背景音乐
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=playbgm%EF%BC%9A%E6%92%AD%E6%94%BE%E8%83%8C%E6%99%AF%E9%9F%B3%E4%B9%90
default : ["bgm.mp3", 0, true]
allBgms : ['EvalString_0']
colour : this.soundColor
Int_0 = Int_0 ? (', "startTime": '+Int_0) : '';
Bool_0 = Bool_0 ? ', "keep": true' : '';
<b style='color:green'>if (JsonEvalString_0) {
JsonEvalString_0 = ', "args": ' +JsonEvalString_0;
}</b>
var code = '{"type": "playBgm", "name": "'+EvalString_0+'"'+Int_0+Bool_0+<b style='color:green'>JsonEvalString_0+</b>'},\n';
return code;
*/;</code></pre>
使用了类型JsonEvalString, 并在注入的代码中处理了其新增出的JsonEvalString_0要如何体现在这个方块产生的json
此处使用了antlr-blockly产生的'类型名_次数'的默认名称, 也可以开头加一行`name : [null,null,null,'args']`来把这个变量命名为args, 对于setText_s这种域比较多的块会很有帮助.
在MotaAction中, 除了默认的Int/Number等
常规的字符串使用EvalString
ID类型的使用IdString
允许空的自然数使用IntString
位置坐标使用PosString
不转义的多行文本使用RawEvalString
json类型的文本使用JsonEvalString
相应的也需要改json到图块的部分
<pre><code> break;
case "playBgm":
this.next = MotaActionBlocks['playBgm_s'].xmlText([
data.name,data.startTime||0,data.keep||false<b style='color:green'>,data.args</b>,this.next]);
break
case "pauseBgm":</code></pre>
### demo - 增加新语句图块
假设已经制作了一个名为`陨石坠落`的公共事件, 其参数列表是长度3的数组, 依次是陨石颜色, 陨石位置, 爆炸范围.
每次要使用插入公共事件并要填`陨石坠落`和形如`[[231,231,41],[5,7],1]`的长而且带有格式的内容, 并且无法使用取色器和地图选点功能. 此时就可以借助'注册一个自定义事件'并填加新语句图块来解决这个问题.
首先注册成名为'meteorite'的事件, 在插件编写的init中添加以下内容
```js
core.registerEvent('meteorite', function(data){
core.insertAction({"type": "insert", "name": "陨石坠落", "args": [data.color,data.loc,data.range]})
})
```
然后在g4中修改以下位置(请善用搜索来定位)
<pre><code> | drawSelector_1_s
| unknown_s
| function_s<b style='color:green'>
| meteorite_s</b>
| pass_s
;
text_0_s</code></pre>
并在分号后面添加
```antlr
meteorite_s
: '陨石坠落' '颜色' ColorString? Colour 'x' PosString ',' 'y' PosString '爆炸范围' Int Newline
/* meteorite_s
tooltip : 陨石坠落
helpUrl : https://h5mota.com/games/template/_docs/#/event
default : ["255,0,0,1",'rgba(255,0,0,1)',"0","0",1]
selectPoint : ["PosString_0", "PosString_1"]
colour : this.soundColor
var loc = ', "loc": ['+PosString_0+','+PosString_1+']';
ColorString_0 = ColorString_0 ? (', "color": ['+ColorString_0+']') : '';
var code = '{"type": "meteorite"'+ColorString_0+loc+', "range": '+Int_0+'},\n';
return code;
*/;
```
希望是特效的颜色, 于是在g4搜索'画面闪烁', 找到了`colour : this.soundColor`, 抄出其中的颜色的写法, 地图选点的写法同理, 搜索'强制战斗'后模仿其写法
在MotaActionParser.js中添加json到图块的代码, 同理模仿'画面闪烁'和'强制战斗'
<pre><code> break;
case "playBgm":
this.next = MotaActionBlocks['playBgm_s'].xmlText([
data.name,data.startTime||0,data.keep||false,this.next]);
break<b style='color:green'>
case "meteorite":
data.color = this.Colour(data.color)
this.next = MotaActionBlocks['meteorite_s'].xmlText([
data.color,'rgba('+data.color+')',data.loc[0],data.loc[1],data.range,this.next]);
</b>case "pauseBgm":</code></pre>
最后在editor_blocklyconfig.js中将其加入到工具栏中
<pre><code> '特效/声音':[<b style='color:green'>
MotaActionBlocks['meteorite_s'].xmlText(),
</b>MotaActionBlocks['sleep_s'].xmlText(),</code></pre>

View File

@ -11,9 +11,77 @@
<meta http-equiv="expires" content="0">
<meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
<link href="https://cdn.bootcss.com/docsify/4.5.5/themes/vue.css" rel="stylesheet">
<script>
//先下载着
var xhr = new XMLHttpRequest();
xhr.open('GET', 'https://cdn.bootcss.com/docsify/4.5.5/docsify.min.js', true);
xhr.send(null);
xhr = new XMLHttpRequest();
xhr.open('GET', 'https://cdn.bootcss.com/docsify/4.5.5/plugins/search.min.js', true);
xhr.send(null);
(function(){
window.bg={replaceToken:{}}
bg.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);
});
}
bg.table=function(ths,tdss,args){
return `<table class="${((args||{}).class||[]).join(' ')}"><thead><tr>${ths.map(v=>`<th style="text-align:left">${v}</th>`).join('')}</tr></thead><tbody>${tdss.map(tds=>`<tr>${tds.map(v=>`<td style="text-align:left">${v}</td>`).join('')}</tr>`).join('')}</tbody></table>`;
}
bg.pattern=/```\s*MotaAction.*?\r?\n[^]*?\r?\n\s*```/g;
bg.replaceFunc=function(str){
var content=null;
try {
content=eval(str.split('\n').slice(1,-1).join('\n'))
} catch (ee) {
}
var match=/```\s*MotaAction(\.)?(\w+)?/.exec(str);
var blocksvg=''
if (!match[2] || match[2]=='action')blocksvg= bg.parseList(content);
else blocksvg=bg.parse(content,match[2]);
return '<p>'+blocksvg+'</p>\n\n';
}
bg.parse=function(obj,type){
MotaActionFunctions.workspace().clear();
xml_text = MotaActionFunctions.actionParser.parse(obj,type||'event');
xml = Blockly.Xml.textToDom('<xml>'+xml_text+'</xml>');
Blockly.Xml.domToWorkspace(xml, MotaActionFunctions.workspace());
svgBlock=document.querySelector("g.blocklyBlockCanvas > g.blocklyDraggable")
svgBlock.setAttribute('transform','translate(0,0)')
tmp={width:svgBlock.getBBox().width,height:svgBlock.getBBox().height}
var id=`<span>${bg.guid()}</span>`
bg.replaceToken[id]=`<svg width="${tmp.width}px" height="${tmp.height}px">`+svgBlock.outerHTML+'</svg>'
return id;
}
bg.parseList=function(obj){
MotaActionFunctions.workspace().clear();
xml_text = MotaActionFunctions.actionParser.parseList(obj);
xml = Blockly.Xml.textToDom('<xml>'+xml_text+'</xml>');
Blockly.Xml.domToWorkspace(xml, MotaActionFunctions.workspace());
svgBlock=document.querySelector("g.blocklyBlockCanvas > g.blocklyDraggable")
svgBlock.setAttribute('transform','translate(0,0)')
tmp={width:svgBlock.getBBox().width,height:svgBlock.getBBox().height}
var id=`<span>${bg.guid()}</span>`
bg.replaceToken[id]=`<svg width="${tmp.width}px" height="${tmp.height}px">`+svgBlock.outerHTML+'</svg>'
return id;
}
})()
</script>
</head>
<body>
<div id="app"></div>
<xml id="toolbox" style="display:none"></xml>
<div id="blocklyArea" style="opacity: 0;z-index: -1;"><div id="blocklyDiv"></div></div>
<textarea id="codeArea" style="display:none" spellcheck="false"></textarea>
<script>
window.$docsify = {
homepage: 'index.md',
@ -41,9 +109,82 @@
auto2top: true,
mergeNavbar: true,
formatUpdated: '{YYYY}-{MM}-{DD} {HH}:{mm}:{ss}',
plugins: [
function(hook){
var renderScriptNode=function(str){
return str.replace(/```.*?\r?\n['"]run['"];[^]*?\r?\n```/g,function(x){
return eval(`(function(){${x.replace(/```.*?\r?\n['"]run['"];/,'').slice(0,-3)}})()`)
})
}
var renderMotaAction=function(str){
return str.replace(bg.pattern,function(x){
return bg.replaceFunc(x)
})
}
hook.beforeEach(function(content){
return renderMotaAction(renderScriptNode(
content
))
})
hook.doneEach(function(){
var map=bg.replaceToken
var node=document.querySelector('.markdown-section')
var str=node.innerHTML
for(var id in map){
str=str.replace(id,map[id])
}
node.innerHTML=str
})
}
]
}
</script>
<script src="https://cdn.bootcss.com/docsify/4.5.5/docsify.min.js"></script>
<script src="https://cdn.bootcss.com/docsify/4.5.5/plugins/search.min.js"></script>
<!-- 为了保证时序用脚本加载 <script src="https://cdn.bootcss.com/docsify/4.5.5/docsify.min.js"></script>
<script src="https://cdn.bootcss.com/docsify/4.5.5/plugins/search.min.js"></script> -->
<script src="../_server/blockly/Converter.bundle.min.js"></script>
<script src="../_server/blockly/blockly_compressed.js"></script>
<script src="../_server/blockly/blocks_compressed.js"></script>
<script src="../_server/blockly/javascript_compressed.js"></script>
<script src="../_server/blockly/zh-hans.js"></script>
<script src='../_server/MotaActionParser.js'></script>
<script>
var xhr = new XMLHttpRequest();
xhr.onreadystatechange = function () {
if (xhr.readyState != 4) return;
if (xhr.status != 200) {
alert("图块描述文件加载失败, 请在'启动服务.exe'中打开编辑器");
return;
}
var grammerFile = xhr.responseText;
converter = new Converter().init();
converter.generBlocks(grammerFile);
//printf(converter.blocks);
converter.renderGrammerName();
//converter.generToolbox();
converter.generMainFile();
//printf(converter.mainFile.join(''));
//console.log(converter);
var script = document.createElement('script');
script.innerHTML = converter.mainFile[5] + converter.mainFile[6];
window.core={material:{items:[],enemys:[]}}
document.body.appendChild(script);
MotaActionFunctions.disableReplace = true;
MotaActionFunctions.disableExpandCompare = true;
script = document.createElement('script');
script.src='https://cdn.bootcss.com/docsify/4.5.5/docsify.min.js'
document.body.appendChild(script);
script = document.createElement('script');
script.src='https://cdn.bootcss.com/docsify/4.5.5/plugins/search.min.js'
document.body.appendChild(script);
}
xhr.open('GET', '../_server/MotaAction.g4', true);
xhr.send(null);
</script>
</body>
</html>

File diff suppressed because one or more lines are too long

View File

@ -1,6 +1,6 @@
// 编辑此文件用的vscode插件: https://marketplace.visualstudio.com/items?itemName=zhaouv.vscode-mota-js-extension
// 此文件通过antlr-blockly生成编辑器中的图块, 相关帮助说明: https://zhaouv.github.io/antlr-blockly/docs/#/README
// 添加和修改图块的说明见 _docs/editor.md ~ http://127.0.0.1:1055/_docs/#/editor?id=修改事件编辑器
/*
特殊注入demo
@ -18,6 +18,8 @@ allBgms : ['EvalString_1']
allSounds : ['EvalString_1']
allShops : ['EvalString_1']
allFloorIds : ['EvalString_1']
// 选择素材
material : ["./project/animates/", "IdString_0"]
*/
@ -57,7 +59,7 @@ autoEvent_m
/* autoEvent_m
tooltip : 自动事件
helpUrl : https://h5mota.com/games/template/_docs/#/event
default : ["flag:__door__==2",0,true,false,false,null]
default : ["flag:__door__===2",0,true,false,false,null]
var code = {
"condition": EvalString_0, // 条件不可为null
"currentFloor": Bool_0, // 是否仅在本层检测
@ -203,7 +205,7 @@ IntString_0 = IntString_0 ? (', "number": '+IntString_0) : '';
EvalString_0 = EvalString_0 ? (', "money": "'+EvalString_0+'"') : '';
EvalString_1 = EvalString_1 ? (', "sell": "'+EvalString_1+'"') : '';
if (!EvalString_0 && !EvalString_1) throw "买入金额和卖出金额至少需要填写一个";
EvalString_2 = EvalString_2 ? (', "condition": "'+EvalString_3+'"') : '';
EvalString_2 = EvalString_2 ? (', "condition": "'+EvalString_2+'"') : '';
var code = '{"id": "' + IdString_0 + '"' + IntString_0 + EvalString_0 + EvalString_1 + EvalString_2 + '},\n';
return code;
*/;
@ -464,6 +466,7 @@ tooltip : 楼层贴图
default : ["bg.jpg","null","bg",0,0,false,"","","","",""]
helpUrl : https://h5mota.com/games/template/_docs/#/event
allImages : ['EvalString_0']
previewBlock : true
if (Reverse_List_0 && Reverse_List_0 != 'null') {
Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"';
} else Reverse_List_0 = '';
@ -487,7 +490,7 @@ return code;
// doorInfo 事件编辑器入口之一
doorInfo_m
: '门信息' '开关门时间' Int '开门音效' EvalString? '关门音效' EvalString? BGNL? Newline '需要钥匙' doorKeyList+ BEND
: '门信息' '开关门时间' Int '开门音效' EvalString? '关门音效' EvalString? BGNL? Newline '需要钥匙' doorKeyList+ '如需撞到开门还需要把图块触发器改成 openDoor' BEND
/* doorInfo_m
@ -507,25 +510,27 @@ doorKeyList
doorKeyKnown
: Key_List ':' Int BEND
: Key_List ':' Int '需要但不消耗' Bool BEND
/* doorKeyKnown
tooltip : 需要钥匙
default : ['yellowKey', 1]
default : ['yellowKey', 1, false]
helpUrl : https://h5mota.com/games/template/_docs/#/event
if (Bool_0) Key_List_0 += ':o';
return '"'+Key_List_0+'": '+Int_0+', ';
*/;
doorKeyUnknown
: IdString ':' Int BEND
: IdString ':' Int '需要但不消耗' Bool BEND
/* doorKeyUnknown
tooltip : 需要钥匙
default : ['orangeKey', 1]
default : ['orangeKey', 1, false]
helpUrl : https://h5mota.com/games/template/_docs/#/event
allItems : ['IdString_0']
if (Bool_0) IdString_0 += ':o';
return '"'+IdString_0+'": '+Int_0+', ';
*/;
@ -593,6 +598,7 @@ return JSON.stringify(code);
action
: text_0_s
| text_1_s
| text_2_s
| comment_s
| autoText_s
| scrollText_s
@ -688,7 +694,6 @@ action
| callLoad_s
| previewUI_s
| clearMap_s
| clearMap_1_s
| setAttribute_s
| fillText_s
| fillBoldText_s
@ -753,6 +758,85 @@ var code = '"'+title+EvalString_2+EvalString_3+'",\n';
return code;
*/;
text_2_s
: '标题' EvalString? '图像' EvalString? '对话框效果' EvalString? ':' EvalString BGNL? Newline textDrawingList* Newline
/* text_2_s
tooltip : text显示一段文字剧情,选项较多请右键点击帮助
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=text%EF%BC%9A%E6%98%BE%E7%A4%BA%E4%B8%80%E6%AE%B5%E6%96%87%E5%AD%97%EF%BC%88%E5%89%A7%E6%83%85%EF%BC%89
doubleclicktext : EvalString_3
allIds : ['EvalString_1']
default : ["小妖精","fairy","","欢迎使用事件编辑器(双击方块进入多行编辑)",null]
var title='';
if (EvalString_0==''){
if (EvalString_1=='' )title='';
else title='\\t['+EvalString_1+']';
} else {
if (EvalString_1=='')title='\\t['+EvalString_0+']';
else title='\\t['+EvalString_0+','+EvalString_1+']';
}
if(EvalString_2 && !(/^(up|center|down|hero|this)(,(hero|null|\d+,\d+|\d+))?$/.test(EvalString_2))) {
throw new Error('对话框效果的用法请右键点击帮助');
}
EvalString_2 = EvalString_2 && ('\\b['+EvalString_2+']');
var code = '"'+title+EvalString_2+textDrawingList_0.replace(/\s/g, '')+EvalString_3+'",\n';
return code;
*/;
textDrawingList
: textDrawing
| textDrawingEmpty;
textDrawing
: '立绘' EvalString '翻转' Reverse_List '绘制坐标' 'x' IntString 'y' IntString '宽' IntString? '高' IntString? BGNL? Newline
'裁剪坐标' 'x' IntString? 'y' IntString? '宽' IntString? '高' IntString? '不透明度' EvalString? '旋转角度' IntString?
/* textDrawing
tooltip : 立绘
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=drawImage%ef%bc%9a%e7%bb%98%e5%88%b6%e5%9b%be%e7%89%87
default : ["fairy.png","null","0","0","","","","","","","",""]
colour : this.subColor
previewBlock : true
allImages : ['EvalString_0']
if (Reverse_List_0 && Reverse_List_0 != 'null') EvalString_0 += Reverse_List_0;
var list = [EvalString_0, IntString_0, IntString_1];
if (IntString_2 || IntString_3) {
if (list.length != 3 || !IntString_2 || !IntString_3) {
throw "绘制的宽和高需同时设置";
}
list.push(IntString_2);
list.push(IntString_3);
}
if (IntString_4 || IntString_5 || IntString_6 || IntString_7) {
if (list.length != 5) throw "如设置裁剪区域,请先设置绘制区域的宽高";
if (!IntString_4 || !IntString_5 || !IntString_6 || !IntString_7) {
throw "如设置裁剪区域,请同时设置全部的裁剪坐标和宽高";
}
list.splice(1, 0, IntString_4, IntString_5, IntString_6, IntString_7);
}
if (EvalString_1) {
if (list.length != 9) throw "如设置不透明度,需填满所有坐标和宽高";
var opacity = parseFloat(EvalString_1);
if (isNaN(opacity) || opacity < 0 || opacity > 1) throw "不合法的不透明度必须是0到1之间"
list.push(opacity);
}
if (IntString_8) {
if (list.length != 10) throw "如设置旋转角度,需填满所有坐标和宽高,以及不透明度";
list.push(IntString_8);
}
return "\\f[" + list.join(",")+"]";
*/;
textDrawingEmpty
: Newline
/* textDrawingEmpty
var code = '';
return code;
*/;
comment_s
: '添加注释' ':' EvalString Newline
@ -863,6 +947,7 @@ setValue_s
/* setValue_s
tooltip : setValue设置勇士的某个属性、道具个数, 或某个变量/Flag的值
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=setvalue%EF%BC%9A%E8%AE%BE%E7%BD%AE%E5%8B%87%E5%A3%AB%E7%9A%84%E6%9F%90%E4%B8%AA%E5%B1%9E%E6%80%A7%E3%80%81%E9%81%93%E5%85%B7%E4%B8%AA%E6%95%B0%EF%BC%8C%E6%88%96%E6%9F%90%E4%B8%AA%E5%8F%98%E9%87%8Fflag%E7%9A%84%E5%80%BC
default : ["","","",false]
colour : this.dataColor
if (AssignOperator_List_0 && AssignOperator_List_0 != '=') {
AssignOperator_List_0 = ', "operator": "' + AssignOperator_List_0 + '"';
@ -874,7 +959,7 @@ return code;
setEnemy_s
: '设置怪物属性' ':' '怪物ID' IdString '的' EnemyId_List '' expression Newline
: '设置怪物属性' ':' '怪物ID' IdString '的' EnemyId_List '' expression Newline
/* setEnemy_s
@ -889,7 +974,7 @@ return code;
setFloor_s
: '设置楼层属性' ':' Floor_Meta_List '楼层名' IdString? '' JsonEvalString Newline
: '设置楼层属性' ':' Floor_Meta_List '楼层名' IdString? '' JsonEvalString Newline
/* setFloor_s
@ -905,7 +990,7 @@ return code;
setGlobalAttribute_s
: '设置全局属性' ':' Global_Attribute_List '' EvalString Newline
: '设置全局属性' ':' Global_Attribute_List '' EvalString Newline
/* setGlobalAttribute_s
@ -919,7 +1004,7 @@ return code;
setGlobalValue_s
: '设置全局数值' ':' Global_Value_List '' EvalString Newline
: '设置全局数值' ':' Global_Value_List '' EvalString Newline
/* setGlobalValue_s
@ -1173,7 +1258,6 @@ tooltip : showFloorImg: 显示一个贴图xy为左上角坐标可用逗号
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=showFloorImg%ef%bc%9a%e6%98%be%e7%a4%ba%e8%b4%b4%e5%9b%be
default : ["","",""]
allFloorIds : ['IdString_0']
selectPoint : ["EvalString_0", "EvalString_1", "IdString_0"]
colour : this.mapColor
var floorstr = '';
if (EvalString_0 && EvalString_1) {
@ -1207,7 +1291,6 @@ helpUrl : https://h5mota.com/games/template/_docs/#/event?id=hideFloorImg%ef%bc%
default : ["","",""]
allFloorIds : ['IdString_0']
colour : this.mapColor
selectPoint : ["EvalString_0", "EvalString_1", "IdString_0"]
var floorstr = '';
if (EvalString_0 && EvalString_1) {
var pattern1 = MotaActionFunctions.pattern.id;
@ -1331,17 +1414,19 @@ return code;
*/;
setHeroIcon_s
: '更改角色行走图' EvalString? Newline
: '更改角色行走图' EvalString? '不重绘' Bool Newline
/* setHeroIcon_s
tooltip : setHeroIcon更改角色行走图
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=setheroicon%EF%BC%9A%E6%9B%B4%E6%94%B9%E8%A7%92%E8%89%B2%E8%A1%8C%E8%B5%B0%E5%9B%BE
colour : this.dataColor
default : ["hero.png"]
default : ["hero.png", false]
allImages : ['EvalString_0']
material : ["./project/images/", "EvalString_0"]
EvalString_0 = EvalString_0 && (', "name": "'+EvalString_0+'"');
var code = '{"type": "setHeroIcon"'+EvalString_0+'},\n';
Bool_0 = Bool_0 ? (', "noDraw": true') : '';
var code = '{"type": "setHeroIcon"'+EvalString_0+Bool_0+'},\n';
return code;
*/;
@ -1453,6 +1538,7 @@ battle_1_s
tooltip : battle: 强制战斗
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=battle%EF%BC%9A%E5%BC%BA%E5%88%B6%E6%88%98%E6%96%97
default : ["","",""]
selectPoint : ["PosString_0", "PosString_1"]
colour : this.mapColor
var floorstr = '';
if (PosString_0 && PosString_1) {
@ -1493,7 +1579,7 @@ tooltip : closeDoor: 关门事件,需要该点本身无事件
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=opendoor%EF%BC%9A%E5%BC%80%E9%97%A8
default : ["","","yellowDoor",false]
selectPoint : ["PosString_0", "PosString_1"]
allIds : ['IdString_0']
allDoors : ['IdString_0']
colour : this.mapColor
var floorstr = '';
if (PosString_0 && PosString_1) {
@ -1527,7 +1613,7 @@ else if (Stair_List_0!=='loc')loc = ', "stair": "'+Stair_List_0+'"';
if (DirectionEx_List_0 == 'null') DirectionEx_List_0 = '';
DirectionEx_List_0 = DirectionEx_List_0 && (', "direction": "'+DirectionEx_List_0+'"');
IntString_0 = IntString_0 ?(', "time": '+IntString_0):'';
var code = '{"type": "changeFloor"'+toFloorId+loc+DirectionEx_List_0+IntString_0+' }\n';
var code = '{"type": "changeFloor"'+toFloorId+loc+DirectionEx_List_0+IntString_0+' },\n';
return code;
*/;
@ -1627,6 +1713,7 @@ tooltip : follow: 跟随勇士
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=follow%ef%bc%9a%e8%b7%9f%e9%9a%8f%e5%8b%87%e5%a3%ab
default : ["npc.png"]
allImages : ['EvalString_0']
material : ["./project/images/", "EvalString_0"]
colour : this.dataColor
var code = '{"type": "follow", "name": "'+EvalString_0+'"},\n';
return code;
@ -1641,6 +1728,7 @@ tooltip : unfollow: 取消跟随
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=unfollow%ef%bc%9a%e5%8f%96%e6%b6%88%e8%b7%9f%e9%9a%8f
default : [""]
allImages : ['EvalString_0']
material : ["./project/images/", "EvalString_0"]
colour : this.dataColor
EvalString_0 = EvalString_0 ? (', "name": "' + EvalString_0 + '"') : "";
var code = '{"type": "unfollow"' + EvalString_0 + '},\n';
@ -1671,7 +1759,8 @@ tooltip : animate显示动画,位置填hero或者1,2形式的位置,或者不
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=animate%EF%BC%9A%E6%98%BE%E7%A4%BA%E5%8A%A8%E7%94%BB
default : ["zone","hero",false,false]
allAnimates : ['IdString_0']
selectPoint : ["EvalString_0", "EvalString_0"]
material : ["./project/animates/", "IdString_0"]
menu : [['选择位置','editor_blockly.selectPoint(block,["EvalString_0","EvalString_0"])']]
colour : this.soundColor
if (EvalString_0) {
if(MotaActionFunctions.pattern.id2.test(EvalString_0)) {
@ -1734,6 +1823,7 @@ helpUrl : https://h5mota.com/games/template/_docs/#/event?id=showImage%ef%bc%9a%
default : [1,"bg.jpg","null","0","0",1,0,false]
allImages : ['EvalString_0']
colour : this.printColor
previewBlock : true
if(Int_0<=0 || Int_0>50) throw new Error('图片编号在1~50之间');
if (Reverse_List_0 && Reverse_List_0 != 'null') {
Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"';
@ -1755,6 +1845,7 @@ helpUrl : https://h5mota.com/games/template/_docs/#/event?id=showImage%ef%bc%9a%
default : [1,"bg.jpg","null","0","0","","",1,"0","0","","",0,false]
allImages : ['EvalString_0']
colour : this.printColor
previewBlock : true
if(Int_0<=0 || Int_0>50) throw new Error('图片编号在1~50之间');
if (Reverse_List_0 && Reverse_List_0 != 'null') {
Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"';
@ -1769,7 +1860,7 @@ return code;
showTextImage_s
: '显示图片化文本' '文本内容' EvalString BGNL?
'图片编号' Int '起点像素' 'x' PosString 'y' PosString '行距' Number '不透明度' Number '时间' Int '不等待执行完毕' Bool Newline
'图片编号' Int '起点像素' 'x' PosString 'y' PosString '行距' Number '翻转' Reverse_List '不透明度' Number '时间' Int '不等待执行完毕' Bool Newline
/* showTextImage_s
@ -1777,10 +1868,13 @@ tooltip : showTextImage显示图片化文本
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=showTextImage%ef%bc%9a%e6%98%be%e7%a4%ba%e6%96%87%e6%9c%ac%e5%8c%96%e5%9b%be%e7%89%87
doubleclicktext : EvalString_0
colour : this.printColor
default : ["可以使用setText事件来控制字体、颜色、大小、偏移量等",1,"0","0",1.4,1,0,false]
default : ["可以使用setText事件来控制字体、颜色、大小、偏移量等",1,"0","0",1.4,"null",1,0,false]
if(Int_0<=0 || Int_0>50) throw new Error('图片编号在1~50之间');
if (Reverse_List_0 && Reverse_List_0 != 'null') {
Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"';
} else Reverse_List_0 = '';
var async = Bool_0?', "async": true':'';
var code = '{"type": "showTextImage", "code": '+Int_0+', "text": "'+EvalString_0+'", "loc": ['+PosString_0+','+PosString_1+'], "lineHeight": '+Number_0+', "opacity": '+Number_1+', "time": '+Int_1+async+'},\n';
var code = '{"type": "showTextImage", "code": '+Int_0+', "text": "'+EvalString_0+'", "loc": ['+PosString_0+','+PosString_1+'], "lineHeight": '+Number_0+Reverse_List_0+', "opacity": '+Number_1+', "time": '+Int_1+async+'},\n';
return code;
*/;
@ -1800,7 +1894,7 @@ return code;
*/;
showGif_s
: '显示动图' EvalString? '起点像素位置' 'x' PosString? 'y' PosString? Newline
: '显示或清除动图' EvalString? '起点像素位置' 'x' PosString? 'y' PosString? Newline
/* showGif_s
@ -1809,6 +1903,7 @@ helpUrl : https://h5mota.com/games/template/_docs/#/event?id=showgif%EF%BC%9A%E6
default : ["","",""]
allImages : ['EvalString_0']
colour : this.printColor
previewBlock : true
EvalString_0 = EvalString_0 ? (', "name": "'+EvalString_0+'"') : '';
var loc = (PosString_0 && PosString_1) ? (', "loc": ['+PosString_0+','+PosString_1+']') : '';
var code = '{"type": "showGif"'+EvalString_0+loc+'},\n';
@ -1844,6 +1939,7 @@ tooltip : setCurtain: 更改画面色调,动画时间可不填
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=setcurtain%EF%BC%9A%E6%9B%B4%E6%94%B9%E7%94%BB%E9%9D%A2%E8%89%B2%E8%B0%83
default : ["255,255,255,1",'rgba(255,255,255,1)',500,true,false]
colour : this.soundColor
previewBlock : true
IntString_0 = IntString_0 ?(', "time": '+IntString_0):'';
Bool_0 = Bool_0 ? ', "keep": true' : '';
var async = Bool_1?', "async": true':'';
@ -1955,9 +2051,9 @@ tooltip : jump: 让某个NPC/怪物跳跃
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=jump%EF%BC%9A%E8%AE%A9%E6%9F%90%E4%B8%AANPC%2F%E6%80%AA%E7%89%A9%E8%B7%B3%E8%B7%83
default : ["","","","",500,true,false]
selectPoint : ["PosString_2", "PosString_3"]
menu : [['选择起点位置','editor_blockly.selectPoint(block,["PosString_0", "PosString_1"])']]
colour : this.mapColor
// selectPoint 跳跃暂时只考虑终点
var floorstr = '';
if (PosString_0 && PosString_1) {
floorstr += ', "from": ['+PosString_0+','+PosString_1+']';
@ -2001,6 +2097,7 @@ tooltip : playBgm: 播放背景音乐
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=playbgm%EF%BC%9A%E6%92%AD%E6%94%BE%E8%83%8C%E6%99%AF%E9%9F%B3%E4%B9%90
default : ["bgm.mp3", 0, true]
allBgms : ['EvalString_0']
material : ["./project/bgms/", "EvalString_0"]
colour : this.soundColor
Int_0 = Int_0 ? (', "startTime": '+Int_0) : '';
Bool_0 = Bool_0 ? ', "keep": true' : '';
@ -2042,6 +2139,7 @@ tooltip : loadBgm: 预加载某个背景音乐,之后可以直接播放
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=loadBgm%ef%bc%9a%e9%a2%84%e5%8a%a0%e8%bd%bd%e4%b8%80%e4%b8%aa%e8%83%8c%e6%99%af%e9%9f%b3%e4%b9%90
default : ["bgm.mp3"]
allBgms : ['EvalString_0']
material : ["./project/bgms/", "EvalString_0"]
colour : this.soundColor
var code = '{"type": "loadBgm", "name": "'+EvalString_0+'"},\n';
return code;
@ -2071,6 +2169,7 @@ helpUrl : https://h5mota.com/games/template/_docs/#/event?id=playsound%EF%BC%9A%
default : ["item.mp3",false]
colour : this.soundColor
allSounds : ['EvalString_0']
material : ["./project/sounds/", "EvalString_0"]
Bool_0 = Bool_0 ? ', "stop": true' : '';
var code = '{"type": "playSound", "name": "'+EvalString_0+'"'+Bool_0+'},\n';
return code;
@ -2344,7 +2443,7 @@ break_s
: '跳出当前循环或公共事件' Newline
/* break_s
tooltip : break跳出循环, 如果break事件不在任何循环中被执行则和exit等价即会立刻结束当前事件!
tooltip : break跳出循环或公共事件!
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=break%EF%BC%9A%E8%B7%B3%E5%87%BA%E5%BE%AA%E7%8E%AF
colour : this.eventColor
var code = '{"type": "break"},\n';
@ -2352,10 +2451,10 @@ return code;
*/;
continue_s
: '继续当前循环' Newline
: '提前结束本轮循环或跳出公共事件' Newline
/* continue_s
tooltip : continue继续执行当前循环的下一轮, 如果continue事件不在任何循环中被执行则和exit等价即会立刻结束当前事件!
tooltip : continue继续执行当前循环的下一轮,或跳出公共事件!
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=continue%EF%BC%9A%E7%BB%A7%E7%BB%AD%E6%89%A7%E8%A1%8C%E5%BD%93%E5%89%8D%E5%BE%AA%E7%8E%AF
colour : this.eventColor
var code = '{"type": "continue"},\n';
@ -2501,29 +2600,19 @@ return code;
clearMap_s
: '清除画布' '起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString Newline
: '清除画布' '起点像素' 'x' PosString? 'y' PosString? '宽' PosString? '高' PosString? Newline
/* clearMap_s
tooltip : clearMap: 清除画布
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=clearMap%ef%bc%9a%e6%b8%85%e9%99%a4%e7%94%bb%e5%b8%83
colour : this.subColor
default : ["0", "0", "100", "100"]
default : ["", "", "", ""]
previewBlock : true
var code = '{"type": "clearMap", "x": ' + PosString_0 + ', "y": ' + PosString_1 +
', "width": ' + PosString_2 + ', "height": ' + PosString_3 + '},\n';
return code;
*/;
clearMap_1_s
: '清空画布' Newline
/* clearMap_1_s
tooltip : clearMap: 清除画布
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=clearMap%ef%bc%9a%e6%b8%85%e9%99%a4%e7%94%bb%e5%b8%83
previewBlock : true
colour : this.subColor
var code = '{"type": "clearMap"},\n';
PosString_0 = PosString_0 && (', "x": ' + PosString_0);
PosString_1 = PosString_1 && (', "y": ' + PosString_1);
PosString_2 = PosString_2 && (', "width": ' + PosString_2);
PosString_3 = PosString_3 && (', "height": ' + PosString_3);
var code = '{"type": "clearMap"'+PosString_0+PosString_1+PosString_2+PosString_3+'},\n';
return code;
*/;
@ -2606,33 +2695,35 @@ return code;
*/;
fillRect_s
: '绘制矩形' '起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString '圆角半径' PosString? '颜色' ColorString? Colour Newline
: '绘制矩形' '起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString '圆角半径' PosString? '旋转度数' PosString? '颜色' ColorString? Colour Newline
/* fillRect_s
tooltip : fillRect绘制矩形
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=fillRect%ef%bc%9a%e7%bb%98%e5%88%b6%e7%9f%a9%e5%bd%a2
colour : this.subColor
previewBlock : true
default : ["0","0","flag:x","300","","",null]
default : ["0","0","flag:x","300","","","","rgba(255,255,255,1)"]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
PosString_4 = PosString_4 ? (', "radius": '+PosString_4) : '';
var code = '{"type": "fillRect", "x": '+PosString_0+', "y": '+PosString_1+', "width": '+PosString_2+', "height": '+PosString_3+PosString_4+ColorString_0+'},\n';
PosString_5 = PosString_5 ? (', "angle": ' + PosString_5) : '';
var code = '{"type": "fillRect", "x": '+PosString_0+', "y": '+PosString_1+', "width": '+PosString_2+', "height": '+PosString_3+PosString_4+PosString_5+ColorString_0+'},\n';
return code;
*/;
strokeRect_s
: '绘制矩形边框' '起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString '圆角半径' PosString? '颜色' ColorString? Colour '线宽' IntString? Newline
: '绘制矩形边框' '起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString '圆角半径' PosString? '旋转度数' PosString? '颜色' ColorString? Colour '线宽' IntString? Newline
/* strokeRect_s
tooltip : strokeRect绘制矩形边框
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=strokeRect%ef%bc%9a%e7%bb%98%e5%88%b6%e7%9f%a9%e5%bd%a2%e8%be%b9%e6%a1%86
colour : this.subColor
previewBlock : true
default : ["0","0","flag:x","300","","",null,""]
default : ["0","0","flag:x","300","","","","rgba(255,255,255,1)",""]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
IntString_0 = IntString_0 ? (', "lineWidth": '+IntString_0) : '';
PosString_4 = PosString_4 ? (', "radius": '+PosString_4) : '';
var code = '{"type": "strokeRect", "x": '+PosString_0+', "y": '+PosString_1+', "width": '+PosString_2+', "height": '+PosString_3+PosString_4+ColorString_0+IntString_0+'},\n';
PosString_5 = PosString_5 ? (', "angle": ' + PosString_5) : '';
var code = '{"type": "strokeRect", "x": '+PosString_0+', "y": '+PosString_1+', "width": '+PosString_2+', "height": '+PosString_3+PosString_4+PosString_5+ColorString_0+IntString_0+'},\n';
return code;
*/;
@ -2644,7 +2735,7 @@ tooltip : drawLine绘制线段
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=drawLine%ef%bc%9a%e7%bb%98%e5%88%b6%e7%ba%bf%e6%ae%b5
colour : this.subColor
previewBlock : true
default : ["0","0","flag:x","300","",null,""]
default : ["0","0","flag:x","300","","rgba(255,255,255,1)",""]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
IntString_0 = IntString_0 ? (', "lineWidth": '+IntString_0) : '';
var code = '{"type": "drawLine", "x1": '+PosString_0+', "y1": '+PosString_1+', "x2": '+PosString_2+', "y2": '+PosString_3+ColorString_0+IntString_0+'},\n';
@ -2659,7 +2750,7 @@ tooltip : drawArrow绘制箭头
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=drawArrow%ef%bc%9a%e7%bb%98%e5%88%b6%e7%ae%ad%e5%a4%b4
colour : this.subColor
previewBlock : true
default : ["0","0","flag:x","300","",null,""]
default : ["0","0","flag:x","300","","rgba(255,255,255,1)",""]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
IntString_0 = IntString_0 ? (', "lineWidth": '+IntString_0) : '';
var code = '{"type": "drawArrow", "x1": '+PosString_0+', "y1": '+PosString_1+', "x2": '+PosString_2+', "y2": '+PosString_3+ColorString_0+IntString_0+'},\n';
@ -2675,7 +2766,7 @@ tooltip : fillPolygon绘制多边形
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=fillPolygon%ef%bc%9a%e7%bb%98%e5%88%b6%e5%a4%9a%e8%be%b9%e5%bd%a2
colour : this.subColor
previewBlock : true
default : ["0,0,100","0,100,0","",null]
default : ["0,0,100","0,100,0","","rgba(255,255,255,1)"]
var pattern2 = /^([+-]?\d+)(,[+-]?\d+)*$/;
if(!pattern2.test(EvalString_0) || !pattern2.test(EvalString_1))throw new Error('坐标格式错误,请右键点击帮助查看格式');
EvalString_0=EvalString_0.split(',');
@ -2696,7 +2787,7 @@ tooltip : strokePolygon绘制多边形边框
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=strokePolygon%ef%bc%9a%e7%bb%98%e5%88%b6%e5%a4%9a%e8%be%b9%e5%bd%a2%e8%be%b9%e6%a1%86
colour : this.subColor
previewBlock : true
default : ["0,0,100","0,100,0","",null,""]
default : ["0,0,100","0,100,0","","rgba(255,255,255,1)",""]
var pattern2 = /^([+-]?\d+)(,[+-]?\d+)*$/;
if(!pattern2.test(EvalString_0) || !pattern2.test(EvalString_1))throw new Error('坐标格式错误,请右键点击帮助查看格式');
EvalString_0=EvalString_0.split(',');
@ -2710,14 +2801,14 @@ return code;
*/;
fillEllipse_s
: '绘制椭圆' '中心' 'x' PosString 'y' PosString '长半径' PosString '短半径' PosString '顺时针旋转度数' PosString? '颜色' ColorString? Colour Newline
: '绘制椭圆' '中心' 'x' PosString 'y' PosString '长半径' PosString '短半径' PosString '旋转度数' PosString? '颜色' ColorString? Colour Newline
/* fillEllipse_s
tooltip : fillEllipse绘制椭圆
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=fillEllipse%ef%bc%9a%e7%bb%98%e5%88%b6%e5%9c%86
colour : this.subColor
previewBlock : true
default : ["0","0","100","100","0","",null]
default : ["0","0","100","100","0","","rgba(255,255,255,1)"]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
PosString_4 = PosString_4 ? (', "angle": ' + PosString_4) : '';
var code = '{"type": "fillEllipse", "x": '+PosString_0+', "y": '+PosString_1+', "a": '+PosString_2+', "b": '+PosString_3+PosString_4+ColorString_0+'},\n';
@ -2725,14 +2816,14 @@ return code;
*/;
strokeEllipse_s
: '绘制椭圆边框' '中心' 'x' PosString 'y' PosString '长半径' PosString '短半径' PosString '顺时针旋转度数' PosString? '颜色' ColorString? Colour '线宽' IntString? Newline
: '绘制椭圆边框' '中心' 'x' PosString 'y' PosString '长半径' PosString '短半径' PosString '旋转度数' PosString? '颜色' ColorString? Colour '线宽' IntString? Newline
/* strokeEllipse_s
tooltip : strokeEllipse绘制椭圆边框
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=strokeEllipse%ef%bc%9a%e7%bb%98%e5%88%b6%e5%9c%86%e8%be%b9%e6%a1%86
colour : this.subColor
previewBlock : true
default : ["0","0","100","100","0","",null,""]
default : ["0","0","100","100","0","","rgba(255,255,255,1)",""]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
IntString_0 = IntString_0 ? (', "lineWidth": '+IntString_0) : '';
PosString_4 = PosString_4 ? (', "angle": ' + PosString_4) : '';
@ -2747,7 +2838,7 @@ fillArc_s
tooltip : fillArc绘制扇形
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=fillEllipse%ef%bc%9a%e7%bb%98%e5%88%b6%e5%9c%86
colour : this.subColor
default : ["0","0","100","0","90","",null,""]
default : ["0","0","100","0","90","","rgba(255,255,255,1)",""]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
var code = '{"type": "fillArc", "x": '+PosString_0+', "y": '+PosString_1+', "r": '+PosString_2+', "start": '+PosString_3+', "end": '+PosString_4+ColorString_0+'},\n';
return code;
@ -2761,7 +2852,7 @@ strokeArc_s
tooltip : strokeArc绘制弧
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=fillEllipse%ef%bc%9a%e7%bb%98%e5%88%b6%e5%9c%86
colour : this.subColor
default : ["0","0","100","0","90","",null,""]
default : ["0","0","100","0","90","","rgba(255,255,255,1)",""]
ColorString_0 = ColorString_0 ? (', "style": ['+ColorString_0+']') : '';
IntString_0 = IntString_0 ? (', "lineWidth": '+IntString_0) : '';
var code = '{"type": "strokeArc", "x": '+PosString_0+', "y": '+PosString_1+', "r": '+PosString_2+', "start": '+PosString_3+', "end": '+PosString_4+ColorString_0+IntString_0+'},\n';
@ -2771,7 +2862,7 @@ return code;
drawImage_s
: '绘制图片' EvalString '翻转' Reverse_List '起点像素' 'x' PosString 'y' PosString '宽' PosString? '高' PosString? Newline
: '绘制图片' EvalString '翻转' Reverse_List '起点像素' 'x' PosString 'y' PosString '宽' PosString? '高' PosString? '旋转度数' PosString? Newline
/* drawImage_s
@ -2779,35 +2870,37 @@ tooltip : drawImage绘制图片
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=drawImage%ef%bc%9a%e7%bb%98%e5%88%b6%e5%9b%be%e7%89%87
previewBlock : true
allImages : ['EvalString_0']
default : ["bg.jpg","null","0","0","",""]
default : ["bg.jpg","null","0","0","","",""]
colour : this.subColor
if (Reverse_List_0 && Reverse_List_0 != 'null') {
Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"';
} else Reverse_List_0 = '';
PosString_2 = PosString_2 ? (', "w": '+PosString_2) : '';
PosString_3 = PosString_3 ? (', "h": '+PosString_3) : '';
var code = '{"type": "drawImage", "image": "'+EvalString_0+'"'+Reverse_List_0+', "x": '+PosString_0+', "y": '+PosString_1+PosString_2+PosString_3+'},\n';
PosString_4 = PosString_4 ? (', "angle": ' + PosString_4) : '';
var code = '{"type": "drawImage", "image": "'+EvalString_0+'"'+Reverse_List_0+', "x": '+PosString_0+', "y": '+PosString_1+PosString_2+PosString_3+PosString_4+'},\n';
return code;
*/;
drawImage_1_s
: '绘制图片' EvalString '翻转' Reverse_List '裁剪的起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString BGNL?
'绘制的起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString Newline
'绘制的起点像素' 'x' PosString 'y' PosString '宽' PosString '高' PosString '旋转度数' PosString? Newline
/* drawImage_1_s
tooltip : drawImage绘制图片
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=drawImage%ef%bc%9a%e7%bb%98%e5%88%b6%e5%9b%be%e7%89%87
default : ["bg.jpg","0","0","32","32","0","0","32","32"]
default : ["bg.jpg","null","0","0","32","32","0","0","32","32",""]
colour : this.subColor
allImages : ['EvalString_0']
previewBlock : true
if (Reverse_List_0 && Reverse_List_0 != 'null') {
Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"';
} else Reverse_List_0 = '';
PosString_8 = PosString_8 ? (', "angle": ' + PosString_8) : '';
var code = '{"type": "drawImage", "image": "'+EvalString_0+'"'+Reverse_List_0+
', "x": '+PosString_0+', "y": '+PosString_1+', "w": '+PosString_2+', "h": '+PosString_3+
', "x1": '+PosString_4+', "y1": '+PosString_5+', "w1": '+PosString_6+', "h1": '+PosString_7+'},\n';
', "x1": '+PosString_4+', "y1": '+PosString_5+', "w1": '+PosString_6+', "h1": '+PosString_7+PosString_8+'},\n';
return code;
*/;
@ -2836,7 +2929,7 @@ drawBackground_s
/* drawBackground_s
tooltip : drawBackground绘制背景
helpUrl : https://h5mota.com/games/template/_docs/#/event?id=drawBackground%ef%bc%9a%e7%bb%98%e5%88%b6%e8%83%8c%e6%99%af%e5%9b%be
default : ["winskin.png",null,"0","0","100","100"]
default : ["winskin.png","rgba(255,255,255,1)","0","0","100","100"]
colour : this.subColor
previewBlock : true
var colorRe = MotaActionFunctions.pattern.colorRe;
@ -2944,7 +3037,7 @@ expression
//todo 修改recieveOrder,根据Arithmetic_List_0不同的值设定不同的recieveOrder
var code = expression_0 + Arithmetic_List_0 + expression_1;
var ops = {
'^': 'Math.pow('+expression_0+','+expression_1+')'
'**': 'Math.pow('+expression_0+','+expression_1+')'
}
if (ops[Arithmetic_List_0])code = ops[Arithmetic_List_0];
var orders = {
@ -2952,7 +3045,8 @@ var orders = {
'-': Blockly.JavaScript.ORDER_SUBTRACTION,
'*': Blockly.JavaScript.ORDER_MULTIPLICATION,
'/': Blockly.JavaScript.ORDER_DIVISION,
'^': Blockly.JavaScript.ORDER_MEMBER, //recieveOrder : ORDER_COMMA
'%': Blockly.JavaScript.ORDER_MODULUS,
'**': Blockly.JavaScript.ORDER_MEMBER, //recieveOrder : ORDER_COMMA
'==': Blockly.JavaScript.ORDER_EQUALITY,
'!=': Blockly.JavaScript.ORDER_EQUALITY,
'===': Blockly.JavaScript.ORDER_EQUALITY,
@ -2962,7 +3056,8 @@ var orders = {
'>=': Blockly.JavaScript.ORDER_RELATIONAL,
'<=': Blockly.JavaScript.ORDER_RELATIONAL,
'&&': Blockly.JavaScript.ORDER_LOGICAL_AND,
'||': Blockly.JavaScript.ORDER_LOGICAL_OR
'||': Blockly.JavaScript.ORDER_LOGICAL_OR,
'^': Blockly.JavaScript.ORDER_BITWISE_XOR
}
return [code, orders[Arithmetic_List_0]];
*/;
@ -3159,12 +3254,12 @@ ShopUse_List
/*ShopUse_List ['money','exp']*/;
Arithmetic_List
: '+'|'-'|'*'|'/'|'^'|'=='|'!='|'==='|'!=='|'>'|'<'|'>='|'<='|'且'|'或'
/*Arithmetic_List ['+','-','*','/','^','==','!=','===','!==','>','<','>=','<=','&&','||']*/;
: '加'|'减'|'乘'|'除'|'取余'|'乘方'|'等于'|'不等于'|'大于'|'小于'|'大于等于'|'小于等于'|'且'|'或'|'异或'|'弱等于'|'弱不等于'
/*Arithmetic_List ['+','-','*','/','%','**','===','!==','>','<','>=','<=','&&','||','^','==','!=']*/;
AssignOperator_List
: '='|'+='|'-='|'*='|'/='|'**='|'//='|'%='
;
: '设为'|'增加'|'减少'|'乘以'|'除以'|'乘方'|'除以并取商'|'除以并取余'
/*AssignOperator_List ['=','+=','-=','*=','/=','**=','//=','%=']*/;
Weather_List
: '无'|'雨'|'雪'|'雾'
@ -3195,8 +3290,8 @@ Event_List
/*Event_List ['null','afterBattle','afterGetItem','afterOpenDoor']*/;
Floor_Meta_List
: '楼层中文名'|'状态栏名称'|'能否使用楼传'|'能否打开快捷商店'|'是否不可浏览地图'|'是否不可瞬间移动'|'默认地面ID'|'楼层贴图'|'宝石血瓶效果'|'上楼点坐标'|'下楼点坐标'|'背景音乐'|'画面色调'|'天气和强度'|'是否地下层'
/*Floor_Meta_List ['title','name','canFlyTo', 'canUseQuickShop', 'cannotViewMap', 'cannotMoveDirectly', 'defaultGround', 'images', 'ratio', 'upFloor', 'downFloor', 'bgm', 'color', 'weather', 'underGround']*/;
: '楼层中文名'|'状态栏名称'|'能否使用楼传'|'能否打开快捷商店'|'是否不可浏览地图'|'是否不可瞬间移动'|'默认地面ID'|'宝石血瓶效果'|'上楼点坐标'|'下楼点坐标'|'楼传落点坐标'|'背景音乐'|'画面色调'|'天气和强度'|'是否地下层'
/*Floor_Meta_List ['title','name','canFlyTo', 'canUseQuickShop', 'cannotViewMap', 'cannotMoveDirectly', 'defaultGround', 'ratio', 'upFloor', 'downFloor', 'fwlyPoint', 'bgm', 'color', 'weather', 'underGround']*/;
Global_Attribute_List
: '全局字体'|'横屏左侧状态栏背景'|'竖屏上方状态栏背景'|'竖屏下方道具栏背景'|'边框颜色'|'状态栏文字色'|'楼层转换样式'|'装备列表'
@ -3208,7 +3303,7 @@ Global_Value_List
Global_Flag_List
: '显示当前楼层'|'显示勇士图标'|'显示当前等级'|'启用生命上限'|'显示生命值'|'显示魔力值'|'显示攻击力'|'显示防御力'|'显示护盾值'|'显示金币值'|'显示经验值'|'允许等级提升'|'升级扣除模式'|'显示钥匙数量'|'显示绿钥匙'|'显示破炸飞'|'显示毒衰咒'|'显示当前技能'|'楼梯边才能楼传'|'楼传平面塔模式'|'铁门不需要钥匙'|'开启加点'|'开启负伤'|'夹击不超伤害值'|'循环计算临界'|'允许轻按'|'允许走到将死领域'|'允许瞬间移动'|'阻激夹域后禁用快捷商店'|'虚化前景层'|'检查控制台'
: '显示当前楼层'|'显示勇士图标'|'显示当前等级'|'启用生命上限'|'显示生命值'|'显示魔力值'|'显示攻击力'|'显示防御力'|'显示护盾值'|'显示金币值'|'显示经验值'|'允许等级提升'|'升级扣除模式'|'显示钥匙数量'|'显示绿钥匙'|'显示破炸飞'|'显示毒衰咒'|'显示当前技能'|'楼梯边才能楼传'|'楼传平面塔模式'|'铁门不需要钥匙'|'开启加点'|'开启负伤'|'夹击不超伤害值'|'循环计算临界'|'允许轻按'|'允许走到将死领域'|'允许瞬间移动'|'阻激夹域后禁用快捷商店'|'虚化前景层'
/*Global_Flag_List ['s:enableFloor','s:enableName','s:enableLv', 's:enableHPMax', 's:enableHP', 's:enableMana', 's:enableAtk', 's:enableDef', 's:enableMDef', 's:enableMoney', 's:enableExp', 's:enableLevelUp', 's:levelUpLeftMode', 's:enableKeys', 's:enableGreenKey', 's:enablePZF', 's:enableDebuff', 's:enableSkill', 'flyNearStair', 'flyRecordPosition', 'steelDoorWithoutKey', 'enableAddPoint', 'enableNegativeDamage', 'betweenAttackMax', 'useLoop', 'enableGentleClick', 'canGoDeadZone', 'enableMoveDirectly', 'disableShopOnDamage', 'blurFg']*/;
Colour
@ -3262,8 +3357,8 @@ Id_List
/*Id_List ['flag','status','item', 'switch', 'temp', 'global']*/;
EnemyId_List
: '生命'|'攻击'|'防御'|'金币'|'经验'|'加点'|'属性'|'名称'|'映射名'|'value'|'atkValue'|'defValue'|'notBomb'|'zoneSquare'|'range'|'n'|'add'|'damage'
/*EnemyId_List ['hp','atk','def','money','exp','point','special','name','displayInBook','属性值','退化扣攻','退化扣防','不可炸','九宫格领域','领域范围','连击数','吸血到自身','固伤值']*/;
: '生命'|'攻击'|'防御'|'金币'|'经验'|'加点'|'属性'|'名称'|'映射名'|'属性值'|'退化扣攻'|'退化扣防'|'不可炸'|'九宫格领域'|'领域范围'|'连击数'|'吸血到自身'|'固伤值'
/*EnemyId_List ['hp','atk','def','money','exp','point','special','name','displayInBook','value','atkValue','defValue','notBomb','zoneSquare','range','n','add','damage']*/;
Equip_List
: '生命'|'生命上限'|'攻击'|'防御'|'护盾'|'魔力'|'魔力上限'

View File

@ -81,9 +81,11 @@ ActionParser.prototype.parse = function (obj,type) {
var text_choices = null;
var knownListKeys = MotaActionBlocks['Key_List'].options.map(function (one) {return one[1];})
Object.keys(obj).sort().forEach(function (key) {
var noNeed = key.endsWith(':o');
if (noNeed) key = key.substring(0, key.length - 2);
var one = knownListKeys.indexOf(key) >= 0 ? 'doorKeyKnown' : 'doorKeyUnknown';
text_choices = MotaActionBlocks[one].xmlText([
one == 'doorKeyUnknown' ? MotaActionFunctions.replaceToName_token(key) : key, obj[key], text_choices
one == 'doorKeyUnknown' ? MotaActionFunctions.replaceToName_token(key) : key, obj[key], noNeed, text_choices
]);
})
return text_choices;
@ -208,7 +210,38 @@ ActionParser.prototype.parseAction = function() {
return;
case "text": // 文字/对话
var info = this.getTitleAndPosition(data.text);
if (info[0] || info[1] || info[2]) {
var textDrawing = [];
info[3] = (info[3] || "").replace(/(\f|\\f)\[(.*?)]/g, function (text, sympol, str) {
var ss = str.split(",");
if (ss.length == 3 || ss.length == 5 || ss.length >=9) {
var swap = function (i, j) { var x = ss[i]; ss[i] = ss[j]; ss[j] = x;}
if (ss.length >= 9) {
swap(1,5); swap(2,6); swap(3,7); swap(4,8);
}
textDrawing.push(ss);
}
return '';
});
if (textDrawing.length > 0) {
var buildTextDrawing = function (obj) {
if(!obj) obj=[];
var text_choices = null;
for(var ii=obj.length-1,choice;choice=obj[ii];ii--) {
var reverse = 'null';
if (choice[0].endsWith(':o') || choice[0].endsWith(':x') || choice[0].endsWith(':y')) {
reverse = choice[0].substring(choice[0].length - 2);
choice[0] = choice[0].substring(0, choice[0].length - 2);
}
text_choices=MotaActionBlocks['textDrawing'].xmlText([
choice[0], reverse, choice[1], choice[2], choice[3], choice[4], choice[5], choice[6],
choice[7], choice[8], choice[9], choice[10], text_choices]);
}
return text_choices;
}
this.next = MotaActionBlocks['text_2_s'].xmlText([
info[0], info[1], info[2], info[3], buildTextDrawing(textDrawing), this.next
]);
} else if (info[0] || info[1] || info[2]) {
this.next = MotaActionBlocks['text_1_s'].xmlText([
info[0], info[1], info[2], info[3], this.next]);
}
@ -352,7 +385,7 @@ ActionParser.prototype.parseAction = function() {
break;
case "setHeroIcon": // 改变勇士
this.next = MotaActionBlocks['setHeroIcon_s'].xmlText([
data.name||"",this.next]);
data.name||"", data.noDraw || false, this.next]);
break;
case "move": // 移动事件
data.loc=data.loc||['',''];
@ -439,7 +472,7 @@ ActionParser.prototype.parseAction = function() {
case "showTextImage": // 显示图片化文本
data.loc=data.loc||['','']
this.next = MotaActionBlocks['showTextImage_s'].xmlText([
this.EvalString(data.text),data.code,data.loc[0],data.loc[1],data.lineHeight||1.4,data.opacity,data.time||0,data.async||false,this.next]);
this.EvalString(data.text),data.code,data.loc[0],data.loc[1],data.lineHeight||1.4,data.reverse,data.opacity,data.time||0,data.async||false,this.next]);
break;
case "moveImage": // 移动图片
data.to=data.to||['','']
@ -766,14 +799,9 @@ ActionParser.prototype.parseAction = function() {
]);
break;
case "clearMap": // 清除画布
if (data.x != null && data.y != null && data.width != null && data.height != null) {
this.next = MotaActionBlocks['clearMap_s'].xmlText([
data.x, data.y, data.width, data.height, this.next
]);
}
else {
this.next = MotaActionBlocks['clearMap_1_s'].xmlText([this.next]);
}
this.next = MotaActionBlocks['clearMap_s'].xmlText([
data.x, data.y, data.width, data.height, this.next
]);
break;
case "setAttribute": // 设置画布属性
data.fillStyle=this.Colour(data.fillStyle);
@ -805,13 +833,13 @@ ActionParser.prototype.parseAction = function() {
case "fillRect": // 绘制矩形
data.style = this.Colour(data.style);
this.next = MotaActionBlocks['fillRect_s'].xmlText([
data.x, data.y, data.width, data.height, data.radius, data.style, 'rgba('+data.style+')', this.next
data.x, data.y, data.width, data.height, data.radius, data.angle, data.style, 'rgba('+data.style+')', this.next
]);
break;
case "strokeRect": // 绘制矩形边框
data.style = this.Colour(data.style);
this.next = MotaActionBlocks['strokeRect_s'].xmlText([
data.x, data.y, data.width, data.height, data.radius, data.style, 'rgba('+data.style+')', data.lineWidth, this.next
data.x, data.y, data.width, data.height, data.radius, data.angle, data.style, 'rgba('+data.style+')', data.lineWidth, this.next
]);
break;
case "drawLine": // 绘制线段
@ -875,12 +903,12 @@ ActionParser.prototype.parseAction = function() {
case "drawImage": // 绘制图片
if (data.x1 != null && data.y1 != null && data.w1 != null && data.h1 != null) {
this.next = MotaActionBlocks['drawImage_1_s'].xmlText([
data.image, data.reverse, data.x, data.y, data.w, data.h, data.x1, data.y1, data.w1, data.h1, this.next
data.image, data.reverse, data.x, data.y, data.w, data.h, data.x1, data.y1, data.w1, data.h1, data.angle, this.next
]);
}
else {
this.next = MotaActionBlocks['drawImage_s'].xmlText([
data.image, data.reverse, data.x, data.y, data.w, data.h, this.next
data.image, data.reverse, data.x, data.y, data.w, data.h, data.angle, this.next
]);
}
break;
@ -1157,7 +1185,7 @@ MotaActionFunctions.JsonEvalString_pre = function (JsonEvalString) {
}
MotaActionFunctions.IntString_pre = function (IntString) {
if (!/^\d*$/.test(IntString)) throw new Error('此项必须是整数或不填');
if (!/^[+-]?\d*$/.test(IntString)) throw new Error('此项必须是整数或不填');
return IntString;
}
@ -1173,6 +1201,8 @@ MotaActionFunctions.IdString_pre = function(IdString){
MotaActionFunctions.PosString_pre = function(PosString){
if (!PosString || /^-?\d+$/.test(PosString)) return PosString;
//if (!(MotaActionFunctions.pattern.id.test(PosString)))throw new Error(PosString+'中包含了0-9 a-z A-Z _ 和中文之外的字符,或者是没有以flag: 开头');
var comma = PosString.indexOf(',');
if (comma >= 0 && PosString.substring(0, comma).indexOf('(') < 0) throw '此处不可写多点坐标';
return '"'+MotaActionFunctions.replaceFromName(PosString)+'"';
}
@ -1332,7 +1362,7 @@ MotaActionFunctions.replaceToName = function (str) {
str = str.replace(new RegExp("item:(" + list.join("|") + ")\\b", "g"), function (a, b) {
return map[b] ? ("物品:" + map[b]) : b;
}).replace(/item:/g, "物品:");
str = str.replace(/flag:/g, "变量:").replace(/switch:/g, "独立开关:").replace(/global:/g, "全局存储:").replace(/temp:/g, "临时变量:");
str = str.replace(/flag:/g, "变量:").replace(/switch:/g, "独立开关:").replace(/global:/g, "全局存储:");
MotaActionFunctions.pattern.replaceEnemyValueList.forEach(function (v) {
@ -1370,7 +1400,7 @@ MotaActionFunctions.replaceFromName = function (str) {
str = str.replace(new RegExp("物品[:](" + list.join("|") + ")(?:$|(?=[^\\w\\u4e00-\\u9fa5]))", "g"), function (a, b) {
return map[b] ? ("item:" + map[b]) : b;
}).replace(/物品[:]/g, "item:");
str = str.replace(/临时变量[:]/g, "temp d:").replace(/变量[:]/g, "flag:").replace(/独立开关[:]/g, "switch:").replace(/全局存储[:]/g, "global:");
str = str.replace(/变量[:]/g, "flag:").replace(/独立开关[:]/g, "switch:").replace(/全局存储[:]/g, "global:");
map = {}; list = [];
MotaActionFunctions.pattern.replaceEnemyList.forEach(function (v) {

View File

@ -1 +1 @@
{"lastUsed":[{"idnum":10016,"id":"X10016","images":"magictower.png","x":0,"y":2,"isTile":true,"recent":1590311075105,"frequent":1}],"foldPerCol":50,"folded":false,"editorLastFloorId":"sample1","disableBlocklyReplace":false,"disableBlocklyExpandCompare":false,"shortcut":{"48":0,"49":0,"50":0,"51":0,"52":0,"53":0,"54":0,"55":0,"56":0,"57":0}}
{"lastUsed":[],"foldPerCol":50,"folded":false,"editorLastFloorId":"sample0","disableBlocklyReplace":false,"disableBlocklyExpandCompare":false,"shortcut":{"48":0,"49":0,"50":0,"51":0,"52":0,"53":0,"54":0,"55":0,"56":0,"57":0}}

View File

@ -178,7 +178,12 @@ body {
border: 1px solid #ccc;
border-radius: 2px;
font-size: 15px;
line-height: 14px;
line-height: 18px;
}
#tip p {
margin-top: 10px;
margin-bottom: 10px;
}
.files {
@ -457,9 +462,8 @@ table.row td {
font: normal 13px Arial, sans-serif;
}
/* for vue dom */
[v-cloak] {
display: none !important;
textarea[disabled] {
color: #999999;
}
#searchBlock {

View File

@ -153,7 +153,7 @@ body {
border: 1px solid #ccc;
border-radius: 2px;
font-size: 1rem;
line-height: 0.93rem;
line-height: 1.2rem;
}
#tip p{
@ -462,9 +462,8 @@ div.row .rowtd .rowtext{
font: normal 2.5vw Arial, sans-serif;
}
/* for vue dom */
[v-cloak] {
display: none !important;
textarea[disabled] {
color: #999999;
}
#down{

View File

@ -27,14 +27,6 @@ function editor() {
brushMod2:document.getElementById('brushMod2'),
brushMod3:document.getElementById('brushMod3'),
brushMod4:document.getElementById('brushMod4'),
bgc : document.getElementById('bg'),
bgCtx : document.getElementById('bg').getContext('2d'),
fgc : document.getElementById('fg'),
fgCtx : document.getElementById('fg').getContext('2d'),
evc : document.getElementById('event'),
evCtx : document.getElementById('event').getContext('2d'),
ev2c : document.getElementById('event2'),
ev2Ctx : document.getElementById('event2').getContext('2d'),
layerMod:document.getElementById('layerMod'),
layerMod2:document.getElementById('layerMod2'),
layerMod3:document.getElementById('layerMod3'),
@ -60,6 +52,9 @@ function editor() {
lastUsed: document.getElementById('lastUsed'),
lastUsedCtx: document.getElementById('lastUsed').getContext('2d'),
lockMode: document.getElementById('lockMode'),
gameInject: document.getElementById('gameInject'),
maps: ['bgmap', 'fgmap', 'map'],
canvas: ['bg', 'fg'],
};
this.uivalues={
@ -153,87 +148,133 @@ editor.info
/////////// 数据相关 ///////////
editor.prototype.init = function (callback) {
var useCompress = main.useCompress;
main.useCompress = false;
editor.airwallImg = new Image();
editor.airwallImg.src = './project/materials/airwall.png';
main.init('editor', function () {
editor.config = new editor_config();
editor.config.load(function() {
editor_util_wrapper(editor);
editor_game_wrapper(editor, main, core);
editor_file_wrapper(editor);
editor_table_wrapper(editor);
editor_ui_wrapper(editor);
editor_mappanel_wrapper(editor);
editor_datapanel_wrapper(editor);
editor_materialpanel_wrapper(editor);
editor_listen_wrapper(editor);
editor.printe=printe;
afterMainInit();
})
});
var afterMainInit = function () {
editor.game.fixFunctionInGameData();
editor.main = main;
editor.core = core;
editor.fs = fs;
editor_file = editor_file(editor, function () {
editor.file = editor_file;
editor_mode = editor_mode(editor);
editor.mode = editor_mode;
core.resetGame(core.firstData.hero, null, core.firstData.floorId, core.clone(core.initStatus.maps));
var lastFloorId = editor.config.get('editorLastFloorId', core.status.floorId);
if (core.floorIds.indexOf(lastFloorId) < 0) lastFloorId = core.status.floorId;
core.changeFloor(lastFloorId, null, core.firstData.hero.loc, null, function () {
afterCoreReset();
}, true);
});
}
var afterCoreReset = function () {
editor.game.idsInit(core.maps, core.icons.icons); // 初始化图片素材信息
editor.drawInitData(core.icons.icons); // 初始化绘图
editor.game.fetchMapFromCore();
editor.updateMap();
editor.buildMark();
editor.drawEventBlock();
editor.pos = {x: 0, y: 0};
editor.mode.loc();
editor.info = editor.ids[editor.indexs[201]];
editor.mode.enemyitem();
editor.mode.floor();
editor.mode.tower();
editor.mode.functions();
editor.mode.commonevent();
editor.mode.showMode('tower');
editor_multi = editor_multi();
editor_blockly = editor_blockly();
// --- 所有用到的flags
editor.used_flags = {};
for (var floorId in editor.main.floors) {
editor.addUsedFlags(JSON.stringify(editor.main.floors[floorId]));
var xhr = new XMLHttpRequest();
xhr.open('GET', 'index.html', true);
xhr.onload = function () {
if (xhr.status != 200) {
alert("HTTP " + xhr.status);
return;
}
if (events_c12a15a8_c380_4b28_8144_256cba95f760.commonEvent) {
for (var name in events_c12a15a8_c380_4b28_8144_256cba95f760.commonEvent) {
editor.addUsedFlags(JSON.stringify(events_c12a15a8_c380_4b28_8144_256cba95f760.commonEvent[name]));
var str = xhr.response.split('<!-- injection -->');
if (str.length != 3) window.onerror("index.html格式不正确");
editor.dom.gameInject.innerHTML = str[1];
var cvs = ['bg', 'fg', 'event', 'event2'].map(function(e) {
return document.getElementById(e);
});
['bg', 'fg', 'ev', 'ev2'].forEach(function(e, i) {
editor.dom[e+'c'] = cvs[i];
editor.dom[e+'Ctx'] = cvs[i].getContext('2d');
editor.dom.mapEdit.insertBefore(cvs[i], document.getElementById('efg'));
});
var mainScript = document.createElement('script');
mainScript.onload = function() {
var useCompress = main.useCompress;
main.useCompress = false;
main.init('editor', function () {
editor.config = new editor_config();
editor.config.load(function() {
editor_util_wrapper(editor);
editor_game_wrapper(editor, main, core);
editor_file_wrapper(editor);
editor_table_wrapper(editor);
editor_ui_wrapper(editor);
editor_mappanel_wrapper(editor);
editor_datapanel_wrapper(editor);
editor_materialpanel_wrapper(editor);
editor_listen_wrapper(editor);
editor.printe=printe;
afterMainInit();
})
});
var afterMainInit = function () {
editor.game.fixFunctionInGameData();
editor.main = main;
editor.core = core;
editor.fs = fs;
editor_file = editor_file(editor, function () {
editor.file = editor_file;
editor_mode = editor_mode(editor);
editor.mode = editor_mode;
core.resetGame(core.firstData.hero, null, core.firstData.floorId, core.clone(core.initStatus.maps));
var lastFloorId = editor.config.get('editorLastFloorId', core.status.floorId);
if (core.floorIds.indexOf(lastFloorId) < 0) lastFloorId = core.status.floorId;
core.changeFloor(lastFloorId, null, core.firstData.hero.loc, null, function () {
afterCoreReset();
}, true);
});
}
var afterCoreReset = function () {
var canvases = document.getElementsByClassName('gameCanvas');
for (var one in canvases) {
canvases[one].width = canvases[one].height = core.__PIXELS__;
}
editor.game.idsInit(core.maps, core.icons.icons); // 初始化图片素材信息
editor.drawInitData(core.icons.icons); // 初始化绘图
editor.game.fetchMapFromCore();
editor.updateMap();
editor.buildMark();
editor.drawEventBlock();
editor.pos = {x: 0, y: 0};
editor.mode.loc();
editor.info = editor.ids[editor.indexs[201]];
editor.mode.enemyitem();
editor.mode.floor();
editor.mode.tower();
editor.mode.functions();
editor.mode.commonevent();
editor.mode.showMode('tower');
editor_multi = editor_multi();
editor_blockly = editor_blockly();
// --- 所有用到的flags
editor.used_flags = {};
// 楼层属性
for (var floorId in editor.main.floors) {
editor.addUsedFlags(JSON.stringify(editor.main.floors[floorId]));
}
// 公共事件
if (events_c12a15a8_c380_4b28_8144_256cba95f760.commonEvent) {
for (var name in events_c12a15a8_c380_4b28_8144_256cba95f760.commonEvent) {
editor.addUsedFlags(JSON.stringify(events_c12a15a8_c380_4b28_8144_256cba95f760.commonEvent[name]));
}
}
// 道具效果
for (var id in items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a) {
editor.addUsedFlags(JSON.stringify(items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id]));
}
// 全局商店
editor.addUsedFlags(JSON.stringify(editor.main.core.firstData.shops));
if (editor.useCompress == null) editor.useCompress = useCompress;
if (Boolean(callback)) callback();
}
}
if (editor.useCompress == null) editor.useCompress = useCompress;
if (Boolean(callback)) callback();
mainScript.id = "mainScript";
mainScript.src = "main.js";
editor.dom.gameInject.appendChild(mainScript);
};
xhr.onabort = xhr.ontimeout = xhr.onerror = function () {
alert("无法访问index.html");
}
xhr.send();
}
editor.prototype.mapInit = function () {
@ -248,11 +289,9 @@ editor.prototype.mapInit = function () {
editor.map[y][x] = 0;
}
}
editor.fgmap=JSON.parse(JSON.stringify(editor.map));
editor.bgmap=JSON.parse(JSON.stringify(editor.map));
editor.currentFloorData.map = editor.map;
editor.currentFloorData.fgmap = editor.fgmap;
editor.currentFloorData.bgmap = editor.bgmap;
editor.dom.maps.forEach(function (one) {
editor.currentFloorData[one] = editor[one] = JSON.parse(JSON.stringify(editor.map));
});
editor.currentFloorData.firstArrive = [];
editor.currentFloorData.eachArrive = [];
editor.currentFloorData.events = {};
@ -264,7 +303,7 @@ editor.prototype.mapInit = function () {
}
editor.prototype.changeFloor = function (floorId, callback) {
for(var ii=0,name;name=['map','bgmap','fgmap'][ii];ii++){
for(var ii=0,name;name=editor.dom.maps[ii];ii++){
var mapArray=editor[name].map(function (v) {
return v.map(function (v) {
return v.idnum || v || 0
@ -326,7 +365,7 @@ editor.prototype.drawEventBlock = function () {
color.push('#00FF00');
if (editor.currentFloorData.afterGetItem[loc])
color.push('#00FFFF');
if (editor.currentFloorData.cannotMove[loc])
if (editor.currentFloorData.cannotMove[loc] && editor.currentFloorData.cannotMove[loc].length > 0)
color.push('#0000FF');
if (editor.currentFloorData.afterOpenDoor[loc])
color.push('#FF00FF');
@ -368,10 +407,11 @@ editor.prototype.updateMap = function () {
var updateMap = function () {
core.removeGlobalAnimate();
core.clearMap('bg');
editor.dom.canvas.forEach(function (one) {
core.clearMap(one);
});
core.clearMap('event');
core.clearMap('event2');
core.clearMap('fg');
core.maps._drawMap_drawAll();
}
updateMap();
@ -400,16 +440,15 @@ editor.prototype.updateMap = function () {
// 绘制地图 start
for (var y = 0; y < editor.map.length; y++) {
for (var x = 0; x < editor.map[0].length; x++) {
var tileInfo = editor.map[y][x];
drawTile(editor.dom.evCtx, x, y, tileInfo);
tileInfo = editor.fgmap[y][x];
drawTile(editor.dom.fgCtx, x, y, tileInfo);
tileInfo = editor.bgmap[y][x];
drawTile(editor.dom.bgCtx, x, y, tileInfo);
drawTile(editor.dom.evCtx, x, y, editor.map[y][x]);
editor.dom.canvas.forEach(function (one) {
drawTile(editor.dom[one + 'Ctx'], x, y, editor[one+'map'][y][x]);
});
}
}
// 绘制地图 end
editor.drawEventBlock();
this.updateLastUsedMap();
}
@ -691,10 +730,10 @@ editor.prototype.setSelectBoxFromInfo=function(thisevent, scrollTo){
editor.updateLastUsedMap();
});
editor.info = JSON.parse(JSON.stringify(thisevent));
tip.infos(JSON.parse(JSON.stringify(thisevent)));
editor.pos=pos;
editor_mode.onmode('nextChange');
editor_mode.onmode('enemyitem');
editor.uifunctions.showBlockInfo(JSON.parse(JSON.stringify(thisevent)));
}
editor.prototype.addUsedFlags = function (s) {

View File

@ -147,7 +147,7 @@ editor_blockly = function () {
editor_blockly.highlightParse = function (shouldHighLight) {
if (shouldNotifyParse == shouldHighLight) return;
shouldNotifyParse = shouldHighLight;
blocklyParseBtn.style.background = shouldNotifyParse ? '#FFCCAA' : 'unset';
blocklyParseBtn.style.background = shouldNotifyParse ? '#ffd700' : 'unset';
}
editor_blockly.cancel = function () {
@ -230,48 +230,145 @@ editor_blockly = function () {
return hasAsync;
}
var previewBlock = function (b) {
editor_blockly.previewBlock = function (b,args) {
if (b && MotaActionBlocks[b.type].previewBlock) {
try {
var code = "[" + Blockly.JavaScript.blockToCode(b).replace(/\\(i|c|d|e|z)/g, '\\\\$1') + "]";
eval("var obj="+code);
if (obj.length > 0 && b.type == 'waitContext_2') {
var dt = obj[0];
editor.uievent.previewUI([{"type": "fillRect", "x": dt.px[0], "y": dt.py[0],
"width": "(" + dt.px[1] + ")-(" + dt.px[0] + ")", "height": "(" + dt.py[1] + ")-(" + dt.py[0] + ")",
"style": "rgba(255,0,0,0.5)"}])
try {
// 特殊处理立绘
if (b.type == 'textDrawing') {
var str = Blockly.JavaScript.blockToCode(b);
var list = str.substring(str.indexOf('[')+1, str.lastIndexOf(']')).split(",");
if (list.length == 3 || list.length == 5 || list.length >= 9) {
var arr = [];
var name = list[0];
var obj = {"type": "drawImage"};
if (name.endsWith(":o") || name.endsWith(":x") || name.endsWith(":y")) {
obj.reverse = name.substring(name.length-2);
name = name.substring(0, name.length - 2);
}
obj.image = name;
obj.x = parseFloat(list[1]);
obj.y = parseFloat(list[2]);
if (list.length >= 5) {
obj.w = parseFloat(list[3]);
obj.h = parseFloat(list[4]);
}
if (list.length >= 9) {
obj.x1 = parseFloat(list[5]);
obj.y1 = parseFloat(list[6]);
obj.w1 = parseFloat(list[7]);
obj.h1 = parseFloat(list[8]);
}
if (list.length >= 10) {
arr.push({"type": "setAttribute", "alpha": parseFloat(list[9])});
}
if (list.length >= 11) {
obj.angle = parseFloat(list[10]);
}
arr.push(obj);
console.log(arr);
editor.uievent.previewUI(arr);
}
else if (obj.length > 0 && b.type.startsWith(obj[0].type)) {
if (b.type == 'previewUI_s')
editor.uievent.previewUI(obj[0].action);
else editor.uievent.previewUI([obj[0]]);
return true;
}
var code = "[" + Blockly.JavaScript.blockToCode(b).replace(/\\(i|c|d|e|z)/g, '\\\\$1') + "]";
eval("var obj="+code);
if (obj.length == 0) return true;
obj = obj[0];
switch (b.type) {
case 'waitContext_2': // 等待用户操作坐标预览
editor.uievent.previewUI([{"type": "fillRect", "x": obj.px[0], "y": obj.py[0],
"width": "(" + obj.px[1] + ")-(" + obj.px[0] + ")", "height": "(" + obj.py[1] + ")-(" + obj.py[0] + ")",
"style": "rgba(255,0,0,0.5)"}]);
break;
case 'showImage_s': // 显示图片
case 'showImage_1_s':
if (obj.sloc) {
editor.uievent.previewUI([
{type: "setAttribute", alpha: obj.opacity},
{type: "drawImage", image: obj.image, x: obj.sloc[0], y: obj.sloc[1], w: obj.sloc[2], h: obj.sloc[3],
x1: obj.loc[0], y1: obj.loc[1], w1: obj.loc[2], h1: obj.loc[3], reverse: obj.reverse}
]);
} else {
editor.uievent.previewUI([
{type: "setAttribute", alpha: obj.opacity},
{type: "drawImage", image: obj.image, x: obj.loc[0], y: obj.loc[1], w: obj.loc[2], h: obj.loc[3], reverse: obj.reverse}
]);
}
} catch (e) {main.log(e);}
return true;
}
return false;
break;
case 'showGif_s': // 显示动图
if (obj.name && obj.loc) {
editor.uievent.previewUI([{type: "drawImage", image: obj.name, x: obj.loc[0], y: obj.loc[1]}]);
}
break;
case 'setCurtain_0_s': // 更改色调
if (obj.color) {
editor.uievent.previewUI([{type: "fillRect", x: 0, y: 0, width: core.__PIXELS__, height: core.__PIXELS__, style: obj.color}]);
}
break;
case 'floorOneImage': // 楼层贴图
obj.w = obj.w / (obj.frame || 1);
editor.uievent.previewUI([
{type: "drawImage", image: obj.name, x: obj.sx || 0, y: obj.sy || 0, w: obj.w, h: obj.h,
x1: obj.x, y1: obj.y, w1: obj.w, h1: obj.h, reverse: obj.reverse}
]);
break;
case 'previewUI_s': // 预览
editor.uievent.previewUI(obj.action);
break;
default:
if (b.type.startsWith(obj.type)) {
editor.uievent.previewUI([obj]);
}
}
} catch (e) {main.log(e);}
}
editor_blockly.selectMaterial = function(b,material){
editor.uievent.selectMaterial([b.getFieldValue(material[1])], '请选择素材', material[0], function (one) {
if (b.type == 'animate_s') {
return /^[-A-Za-z0-9_.]+\.animate$/.test(one) ? one.substring(0, one.length - 8) : null;
}
return /^[-A-Za-z0-9_.]+$/.test(one) ? one : null;
}, function (value) {
if (value instanceof Array && value.length > 0) {
b.setFieldValue(value[0], material[1]);
}
});
}
editor_blockly.doubleclicktext = function(b,f){
var value = b.getFieldValue(f);
//多行编辑
editor_multi.multiLineEdit(value, b, f, {'lint': f === 'RawEvalString_0'}, function (newvalue, b, f) {
if (MotaActionBlocks[b.type].doubleclicktext !== 'RawEvalString_0') {
}
b.setFieldValue(newvalue.split('\n').join('\\n'), f);
});
}
editor_blockly.doubleClickBlock = function (blockId) {
var b = editor_blockly.workspace.getBlockById(blockId);
if (previewBlock(b)) return;
if (b && MotaActionBlocks[b.type].selectPoint) { // selectPoint
this.selectPoint();
if (b && MotaActionBlocks[b.type].previewBlock){
editor_blockly.previewBlock(b,MotaActionBlocks[b.type].previewBlock)
return;
}
var f = b ? MotaActionBlocks[b.type].doubleclicktext : null;
if (f) {
var value = b.getFieldValue(f);
//多行编辑
editor_multi.multiLineEdit(value, b, f, {'lint': f === 'RawEvalString_0'}, function (newvalue, b, f) {
if (MotaActionBlocks[b.type].doubleclicktext !== 'RawEvalString_0') {
}
b.setFieldValue(newvalue.split('\n').join('\\n'), f);
});
if (b && MotaActionBlocks[b.type].selectPoint) { // selectPoint
editor_blockly.selectPoint(b,eval(MotaActionBlocks[b.type].selectPoint));
return;
}
if (b && MotaActionBlocks[b.type].material) {
editor_blockly.selectMaterial(b,JSON.parse(MotaActionBlocks[b.type].material));
return;
}
if (b && MotaActionBlocks[b.type].doubleclicktext) { //多行编辑
editor_blockly.doubleclicktext(b,MotaActionBlocks[b.type].doubleclicktext);
return;
}
}
@ -291,7 +388,7 @@ editor_blockly = function () {
'sleep_s',
'setBlock_s',
'insert_1_s'
]; // 最常用的15个图块
]; // 最常用的15个事件
editor_blockly.lastUsedTypeNum=15;
editor_blockly.addIntoLastUsedType=function(blockId) {
@ -355,27 +452,26 @@ editor_blockly = function () {
// ------ select point ------
editor_blockly.selectPoint = function () {
var block = Blockly.selected, arr = null;
editor_blockly.selectPoint = function (block,arr) {
var floorId = editor.currentFloorId, pos = editor.pos, x = pos.x, y = pos.y;
if (block != null && MotaActionBlocks[block.type].selectPoint) {
arr = eval(MotaActionBlocks[block.type].selectPoint);
var xv = parseInt(block.getFieldValue(arr[0])), yv = parseInt(block.getFieldValue(arr[1]));
if (block.type == 'animate_s') {
var v = block.getFieldValue(arr[0]).split(",");
xv = parseInt(v[0]); yv = parseInt(v[1]);
}
if (!isNaN(xv)) x = xv;
if (!isNaN(yv)) y = yv;
if (arr[2] != null) floorId = block.getFieldValue(arr[2]) || floorId;
var xv = parseInt(block.getFieldValue(arr[0])), yv = parseInt(block.getFieldValue(arr[1]));
if (arr[0] === arr[1]) {
var v = block.getFieldValue(arr[0]).split(",");
xv = parseInt(v[0]); yv = parseInt(v[1]);
}
editor.uievent.selectPoint(floorId, x, y, arr && arr[2] == null, function (fv, xv, yv) {
if (!isNaN(xv)) x = xv;
if (!isNaN(yv)) y = yv;
if (arr[2] != null) floorId = block.getFieldValue(arr[2]) || floorId;
editor.uievent.selectPoint(floorId, x, y, false, function (fv, xv, yv) {
if (!arr) return;
if (arr[2] != null) {
if (fv != editor.currentFloorId) block.setFieldValue(fv, arr[2]);
else block.setFieldValue(arr[3] ? fv : "", arr[2]);
}
if (block.type == 'animate_s') {
if (arr[0] === arr[1]) {
block.setFieldValue(xv+","+yv, arr[0]);
}
else {
@ -442,7 +538,7 @@ editor_blockly = function () {
if (index2 >= 0) {
before = content.substring(0, index2);
if (before.endsWith("怪物") || (ch == ':' && ch2 == ':' && before.endsWith("enemy"))) {
var list = ["name", "hp", "atk", "def", "money", "exp", "point", "special"];
var list = MotaActionBlocks['EnemyId_List'].options.map(function(v){return v[1]});
if (before.endsWith("怪物") && MotaActionFunctions) {
list = MotaActionFunctions.pattern.replaceEnemyValueList.map(function (v) {
return v[1];
@ -491,6 +587,15 @@ editor_blockly = function () {
}).sort();
}
// 提供 hero.xxx 补全
index = content.lastIndexOf("hero.");
if (index >= 0) {
var token = content.substring(index+6);
return Object.keys(core.status.hero).filter(function (one) {
return one != token && one.startsWith(token);
}).sort();
}
var namesObj={};
namesObj.allIds = ["this"].concat(core.getAllIconIds());
@ -519,6 +624,10 @@ editor_blockly = function () {
namesObj.allColors = ["aqua青色", "black黑色", "blue蓝色", "fuchsia品红色", "gray灰色", "green深绿色", "lime绿色",
"maroon深红色", "navy深蓝色", "gold金色", "olive黄褐色", "orange橙色", "purple品红色",
"red红色", "silver淡灰色", "teal深青色", "white白色", "yellow黄色"];
namesObj.allDoors = ["this"].concat(Object.keys(maps_90f36752_8815_4be8_b32b_d7fad1d0542e)
.map(function (key) { return maps_90f36752_8815_4be8_b32b_d7fad1d0542e[key]; })
.filter(function (one) { return one.doorInfo != null; })
.map(function (one) { return one.id; }));
var filter = function (list, content) {
return list.filter(function (one) {
return one != content && one.startsWith(content);
@ -534,7 +643,7 @@ editor_blockly = function () {
// 对音效进行补全
// 对全局商店进行补全
// 对楼层名进行补全
for(var ii=0,names;names=['allIds','allEnemys','allItems','allImages','allAnimates','allBgms','allSounds','allShops','allFloorIds'][ii];ii++){
for(var ii=0,names;names=['allIds','allEnemys','allItems','allImages','allAnimates','allBgms','allSounds','allShops','allFloorIds','allDoors'][ii];ii++){
if (MotaActionBlocks[type][names] && eval(MotaActionBlocks[type][names]).indexOf(name)!==-1) {
return filter(namesObj[names], content);
}

View File

@ -24,7 +24,7 @@ editor_blocklyconfig=(function(){
{"type": "hide", "time": 500},
],'event'),
MotaActionFunctions.actionParser.parse({
"condition": "flag:__door__==2",
"condition": "flag:__door__===2",
"currentFloor": true,
"priority": 0,
"delayExecute": false,
@ -87,6 +87,7 @@ editor_blocklyconfig=(function(){
'显示文字':[
MotaActionBlocks['text_0_s'].xmlText(),
MotaActionBlocks['text_1_s'].xmlText(),
MotaActionFunctions.actionParser.parseList("\t[小妖精,fairy]\f[fairy.png,0,0]欢迎使用事件编辑器(双击方块进入多行编辑)"),
MotaActionBlocks['comment_s'].xmlText(),
MotaActionBlocks['autoText_s'].xmlText(),
MotaActionBlocks['scrollText_s'].xmlText(),
@ -204,7 +205,6 @@ editor_blocklyconfig=(function(){
'UI绘制':[
MotaActionBlocks['previewUI_s'].xmlText(),
MotaActionBlocks['clearMap_s'].xmlText(),
MotaActionBlocks['clearMap_1_s'].xmlText(),
MotaActionBlocks['setAttribute_s'].xmlText(),
MotaActionBlocks['fillText_s'].xmlText(),
MotaActionBlocks['fillBoldText_s'].xmlText(),
@ -303,7 +303,7 @@ editor_blocklyconfig=(function(){
'<label text="打怪开门"></label>',
MotaActionFunctions.actionParser.parse([
{"type": "setValue", "name": "flag:__door__", "operator": "+=", "value": "1"},
{"type": "if", "condition": "flag:__door__==2",
{"type": "if", "condition": "flag:__door__===2",
"true": [
{"type": "openDoor", "loc": [10,5]}
],

View File

@ -6,7 +6,7 @@ editor_config.prototype.load = function(callback) {
var _this = this;
fs.readFile(this.address, "utf-8", function(e, d) {
if (e) {
console.warn("无法读取配置文件, 已重新生成");
console.error("无法读取配置文件, 已重新生成");
_this.config = {};
_this.save(callback);
} else {
@ -28,7 +28,7 @@ editor_config.prototype.set = function(key, value, callback) {
editor_config.prototype.save = function(callback) {
fs.writeFile(this.address, JSON.stringify(this.config) ,'utf-8', function(e) {
if (e) printe("写入配置文件失败");
if (e) console.error("写入配置文件失败");
if (callback instanceof Function) callback();
})
}

View File

@ -6,118 +6,18 @@ editor_datapanel_wrapper = function (editor) {
//////////////////// 地图编辑 //////////////////////////////////////////
///////////////////////////////////////////////////////////////////////
// 由于历史遗留原因, 以下变量作为全局变量使用
// pout exportMap mapEditArea mapEditArea copyMap clearMapButton deleteMap
window.pout = document.getElementById('pout')
window.exportMap = document.getElementById('exportMap')
exportMap.isExport=false
exportMap.onclick=function(){
editor.updateMap();
var sx=editor.map.length-1,sy=editor.map[0].length-1;
var pout = document.getElementById('pout');
var exportMap = document.getElementById('exportMap');
var importMap = document.getElementById('importMap');
var clearMapButton=document.getElementById('clearMapButton')
var deleteMap=document.getElementById('deleteMap')
var filestr = '';
for (var yy = 0; yy <= sy; yy++) {
filestr += '['
for (var xx = 0; xx <= sx; xx++) {
var mapxy = editor.map[yy][xx];
if (typeof(mapxy) == typeof({})) {
if ('idnum' in mapxy) mapxy = mapxy.idnum;
else {
// mapxy='!!?';
tip.whichShow(3);
return;
}
} else if (typeof(mapxy) == 'undefined') {
tip.whichShow(3);
return;
}
mapxy = String(mapxy);
mapxy = Array(Math.max(4 - mapxy.length, 0)).join(' ') + mapxy;
filestr += mapxy + (xx == sx ? '' : ',')
}
filestr += ']' + (yy == sy ? '' : ',\n');
}
pout.value = filestr;
mapEditArea.mapArr(filestr);
exportMap.isExport = true;
mapEditArea.error(0);
tip.whichShow(2);
}
window.mapEditArea = document.getElementById('mapEditArea')
mapEditArea.errors=[ // 编号1,2
"格式错误!请使用正确格式(请使用地图生成器进行生成,且需要和本地图宽高完全一致)",
"当前有未定义ID在地图区域显示红块请修改ID或者到icons.js和maps.js中进行定义"
]
mapEditArea.formatTimer=null
mapEditArea._mapArr=''
mapEditArea.mapArr=function(value){
if(value!=null){
var val=value
var oldval=mapEditArea._mapArr
if (val==oldval) return;
if (exportMap.isExport) {
exportMap.isExport = false;
return;
}
if (mapEditArea.formatArr()) {
mapEditArea.error(0);
setTimeout(function () {
if (mapEditArea.formatArr())mapEditArea.mapArr(mapEditArea.formatArr());
mapEditArea.drawMap();
tip.whichShow(8)
}, 1000);
clearTimeout(mapEditArea.formatTimer);
mapEditArea.formatTimer = setTimeout(function () {
pout.value = mapEditArea.formatArr();
}, 5000); //5s后再格式化不然光标跳到最后很烦
} else {
mapEditArea.error(1);
}
mapEditArea._mapArr=value
}
return mapEditArea._mapArr
}
pout.oninput=function(){
mapEditArea.mapArr(pout.value)
}
mapEditArea._error=0
mapEditArea.error=function(value){
if(value!=null){
mapEditArea._error=value
if (value>0)
printe(mapEditArea.errors[value-1])
}
return mapEditArea._error
}
mapEditArea.drawMap= function () {
// var mapArray = mapEditArea.mapArr().split(/\D+/).join(' ').trim().split(' ');
var mapArray = JSON.parse('[' + mapEditArea.mapArr() + ']');
var sy=editor.map.length,sx=editor.map[0].length;
for (var y = 0; y < sy; y++)
for (var x = 0; x < sx; x++) {
var num = mapArray[y][x];
if (num == 0)
editor.map[y][x] = 0;
else if (typeof(editor.indexs[num][0]) == 'undefined') {
mapEditArea.error(2);
editor.map[y][x] = undefined;
} else editor.map[y][x] = editor.ids[[editor.indexs[num][0]]];
}
editor.updateMap();
}
mapEditArea.formatArr= function () {
var formatArr= function () {
var formatArrStr = '';
console.log(1)
var si=editor.map.length,sk=editor.map[0].length;
if (mapEditArea.mapArr().split(/\D+/).join(' ').trim().split(' ').length != si*sk) return false;
var arr = mapEditArea.mapArr().replace(/\s+/g, '').split('],[');
if (pout.value.split(/\D+/).join(' ').trim().split(' ').length != si*sk) return false;
var arr = pout.value.replace(/\s+/g, '').split('],[');
if (arr.length != si) return;
for (var i = 0; i < si; i++) {
@ -138,31 +38,71 @@ editor_datapanel_wrapper = function (editor) {
}
return formatArrStr;
}
window.copyMap=document.getElementById('copyMap')
copyMap.err=''
copyMap.onclick=function(){
tip.whichShow(0);
if (pout.value.trim() != '') {
if (mapEditArea.error()) {
copyMap.err = mapEditArea.errors[mapEditArea.error() - 1];
tip.whichShow(5)
return;
}
try {
pout.focus();
pout.setSelectionRange(0, pout.value.length);
document.execCommand("Copy");
tip.whichShow(6);
} catch (e) {
copyMap.err = e;
tip.whichShow(5);
exportMap.onclick=function(){
editor.updateMap();
var sx=editor.map.length-1,sy=editor.map[0].length-1;
var filestr = '';
for (var yy = 0; yy <= sy; yy++) {
filestr += '['
for (var xx = 0; xx <= sx; xx++) {
var mapxy = editor.map[yy][xx];
if (typeof(mapxy) == typeof({})) {
if ('idnum' in mapxy) mapxy = mapxy.idnum;
else {
printe("生成失败! 地图中有未定义的图块,建议先用其他有效图块覆盖或点击清除地图!");
return;
}
} else if (typeof(mapxy) == 'undefined') {
printe("生成失败! 地图中有未定义的图块,建议先用其他有效图块覆盖或点击清除地图!");
return;
}
mapxy = String(mapxy);
mapxy = Array(Math.max(4 - mapxy.length, 0)).join(' ') + mapxy;
filestr += mapxy + (xx == sx ? '' : ',')
}
filestr += ']' + (yy == sy ? '' : ',\n');
}
pout.value = filestr;
if (formatArr()) {
pout.focus();
pout.setSelectionRange(0, pout.value.length);
document.execCommand("Copy");
printf("导出并复制成功!");
} else {
tip.whichShow(7);
printe("无法导出并复制此地图,可能有不合法块。")
}
}
window.clearMapButton=document.getElementById('clearMapButton')
importMap.onclick= function () {
var sy=editor.map.length,sx=editor.map[0].length;
var mapArray;
try {
mapArray = JSON.parse('[' + pout.value + ']');
if (mapArray.length != sy || mapArray[0].length != sx) throw '';
} catch (e) {
printe('格式错误!请使用正确格式(请使用地图生成器进行生成,且需要和本地图宽高完全一致)');
return;
}
var hasError = false;
for (var y = 0; y < sy; y++)
for (var x = 0; x < sx; x++) {
var num = mapArray[y][x];
if (num == 0)
editor.map[y][x] = 0;
else if (editor.indexs[num]==null || editor.indexs[num][0]==null) {
printe('当前有未定义ID在地图区域显示红块请用有效的图块进行覆盖')
hasError = true;
editor.map[y][x] = {};
} else editor.map[y][x] = editor.ids[[editor.indexs[num][0]]];
}
editor.updateMap();
if (!hasError) printf('地图导入成功!');
}
clearMapButton.onclick=function () {
if (!confirm('你确定要清除地图上所有内容么?此过程不可逆!')) return;
editor.mapInit();
editor_mode.onmode('');
editor.file.saveFloorFile(function (err) {
@ -173,15 +113,10 @@ editor_datapanel_wrapper = function (editor) {
;printf('地图清除成功');
});
editor.updateMap();
clearTimeout(mapEditArea.formatTimer);
clearTimeout(tip.timer);
pout.value = '';
mapEditArea.mapArr('');
tip.whichShow(4);
mapEditArea.error(0);
}
window.deleteMap=document.getElementById('deleteMap')
deleteMap.onclick=function () {
if (!confirm('你确定要删除此地图么?此过程不可逆!')) return;
editor_mode.onmode('');
var index = core.floorIds.indexOf(editor.currentFloorId);
if (index>=0) {
@ -197,7 +132,6 @@ editor_datapanel_wrapper = function (editor) {
else printe('删除成功,请F5刷新编辑器生效');
}
editor.uifunctions.newMap_func = function () {
var newMap = document.getElementById('newMap');
@ -408,6 +342,8 @@ editor_datapanel_wrapper = function (editor) {
editor.uifunctions.copyPasteEnemyItem_func = function () {
var copyEnemyItem = document.getElementById('copyEnemyItem');
var pasteEnemyItem = document.getElementById('pasteEnemyItem');
var clearEnemyItem = document.getElementById('clearEnemyItem');
var clearAllEnemyItem = document.getElementById('clearAllEnemyItem');
copyEnemyItem.onclick = function () {
var cls = (editor_mode.info || {}).images;
@ -417,13 +353,8 @@ editor_datapanel_wrapper = function (editor) {
if (cls == 'enemys' || cls == 'enemy48') {
editor.uivalues.copyEnemyItem.data = core.clone(enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id]);
printf("怪物属性复制成功");
} else {
editor.uivalues.copyEnemyItem.data = {};
for (var x in items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a) {
if (items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[x][id] != null) {
editor.uivalues.copyEnemyItem.data[x] = core.clone(items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[x][id]);
}
}
} else if (cls == 'items') {
editor.uivalues.copyEnemyItem.data = core.clone(items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id]);
printf("道具属性复制成功");
}
}
@ -434,26 +365,99 @@ editor_datapanel_wrapper = function (editor) {
var id = editor_mode.info.id;
if (cls == 'enemys' || cls == 'enemy48') {
if (confirm("你确定要覆盖此怪物的全部属性么?这是个不可逆操作!")) {
var name = enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id].name;
var displayIdInBook = enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id].displayIdInBook;
enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id] = core.clone(editor.uivalues.copyEnemyItem.data);
enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id].id = id;
enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id].name = name;
enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id].displayIdInBook = displayIdInBook;
editor.file.saveSetting('enemys', [], function (err) {
if (err) printe(err);
else printf("怪物属性粘贴成功\n请再重新选中该怪物方可查看更新后的表格。");
})
}
} else {
} else if (cls == 'items') {
if (confirm("你确定要覆盖此道具的全部属性么?这是个不可逆操作!")) {
for (var x in editor.uivalues.copyEnemyItem.data) {
items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[x][id] = core.clone(editor.uivalues.copyEnemyItem.data[x]);
}
var name = items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id].name;
items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id] = core.clone(editor.uivalues.copyEnemyItem.data[x]);
items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id].id = id;
items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id].name = name;
editor.file.saveSetting('items', [], function (err) {
if (err) printe(err);
else printf("道具属性粘贴成功\n请再重新选中该道具方可查看更新后的表格。");
})
}
}
}
var _clearEnemy = function (id) {
var info = core.clone(comment_c456ea59_6018_45ef_8bcc_211a24c627dc._data.enemys_template);
info.id = id;
info.name = enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id].name;
info.displayIdInBook = enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id].displayIdInBook;
enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80[id] = info;
}
var _clearItem = function (id) {
for (var x in items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id]) {
if (x != 'id' && x!='cls' && x != 'name') delete items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a[id][x];
}
}
clearEnemyItem.onclick = function () {
var cls = (editor_mode.info || {}).images;
if (editor_mode.mode != 'enemyitem' || !cls) return;
var id = editor_mode.info.id;
if (cls == 'enemys' || cls == 'enemy48') {
if (confirm("你确定要清空本怪物的全部属性么?这是个不可逆操作!")) {
_clearEnemy(id);
editor.file.saveSetting('enemys', [], function (err) {
if (err) printe(err);
else printf("怪物属性清空成功\n请再重新选中该怪物方可查看更新后的表格。");
})
}
} else if (cls == 'items') {
if (confirm("你确定要清空本道具的全部属性么?这是个不可逆操作!")) {
_clearItem(id);
editor.file.saveSetting('items', [], function (err) {
if (err) printe(err);
else printf("道具属性清空成功\n请再重新选中该道具方可查看更新后的表格。");
})
}
}
}
clearAllEnemyItem.onclick = function () {
var cls = (editor_mode.info || {}).images;
if (editor_mode.mode != 'enemyitem' || !cls) return;
var id = editor_mode.info.id;
if (cls == 'enemys' || cls == 'enemy48') {
if (confirm("你确定要批量清空【全塔怪物】的全部属性么?这是个不可逆操作!")) {
for (var id in enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80)
_clearEnemy(id);
editor.file.saveSetting('enemys', [], function (err) {
if (err) printe(err);
else printf("全塔全部怪物属性清空成功!");
})
}
} else if (cls == 'items') {
if (confirm("你确定要批量清空【全塔所有自动注册且未修改ID的道具】的全部属性么这是个不可逆操作")) {
for (var id in items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a) {
if (/^I\d+$/.test(id)) {
_clearItem(id);
}
}
editor.file.saveSetting('items', [], function (err) {
if (err) printe(err);
else printf("全塔全部道具属性清空成功!");
})
}
}
}
}
@ -529,7 +533,7 @@ editor_datapanel_wrapper = function (editor) {
newFloorData.height = height;
// Step 2:更新map, bgmap和fgmap
["bgmap", "fgmap", "map"].forEach(function (name) {
editor.dom.maps.forEach(function (name) {
newFloorData[name] = [];
if (currentFloorData[name] && currentFloorData[name].length > 0) {
for (var j = 0; j < height; ++j) {

View File

@ -83,7 +83,9 @@ editor_file_wrapper = function (editor) {
var datastr = ['main.floors.', floorId, '=\n'];
var tempJsonObj = Object.assign({}, floorData);
var tempMap = [['map', editor.util.guid()], ['bgmap', editor.util.guid()], ['fgmap', editor.util.guid()]];
var tempMap = editor.dom.maps.map(function (one) {
return [one, editor.util.guid()]
});
tempMap.forEach(function (v) {
v[2] = tempJsonObj[v[0]];
tempJsonObj[v[0]] = v[1];
@ -164,11 +166,8 @@ editor_file = function (editor, callback) {
/* if (!isset(editor.currentFloorId) || !isset(editor.currentFloorData)) {
callback('未选中文件或无数据');
} */
var filename = 'project/floors/' + editor.currentFloorId + '.js';
var datastr = ['main.floors.', editor.currentFloorId, '=\n'];
if (core.floorIds.indexOf(editor.currentFloorId) >= 0) {
for(var ii=0,name;name=['map','bgmap','fgmap'][ii];ii++){
for(var ii=0,name;name=editor.dom.maps[ii];ii++){
var mapArray=editor[name].map(function (v) {
return v.map(function (v) {
return v.idnum || v || 0
@ -401,7 +400,7 @@ editor_file = function (editor, callback) {
var mapActions = [];
iconActions.push(["add", "['autotile']['" + filename + "']", 0]);
mapActions.push(["add", "['" + idnum + "']", {'cls': 'autotile', 'id': filename, 'noPass': true}]);
mapActions.push(["add", "['" + idnum + "']", {'cls': 'autotile', 'id': filename}]);
var templist = [];
var tempcallback = function (err) {
@ -575,7 +574,7 @@ editor_file = function (editor, callback) {
var value=actionList[ii];
// 是tilesets 且未定义 且在这里是第一次定义
if(idnum>=editor.core.icons.tilesetStartOffset && !isset(editor.core.maps.blocksInfo[idnum]) && tempmap.indexOf(idnum)===-1){
actionList.splice(ii,0,["add","['" + idnum + "']",{"cls": "tileset", "id": "X"+idnum, "noPass": true}]);
actionList.splice(ii,0,["add","['" + idnum + "']",{"cls": "tileset", "id": "X"+idnum}]);
tempmap.push(idnum);
ii++;
}
@ -588,7 +587,7 @@ editor_file = function (editor, callback) {
callback([
(function () {
var sourceobj=editor.core.maps.blocksInfo[idnum];
if(!isset(sourceobj) && idnum>=editor.core.icons.tilesetStartOffset)sourceobj={"cls": "tileset", "id": "X"+idnum, "noPass": true}
if(!isset(sourceobj) && idnum>=editor.core.icons.tilesetStartOffset)sourceobj={"cls": "tileset", "id": "X"+idnum}
var locObj = Object.assign({}, sourceobj);
Object.keys(editor.file.comment._data.maps._data).forEach(function (v) {
if (!isset(sourceobj[v]))
@ -667,9 +666,7 @@ editor_file = function (editor, callback) {
Object.keys(editor.file.comment._data.floors._data.loc._data).forEach(function (v) {
delete(locObj[v]);
});
delete(locObj.map);
delete(locObj.bgmap);
delete(locObj.fgmap);
editor.dom.maps.forEach(function (one) { delete locObj[one]; });
return locObj;
})(),
editor.file.comment._data.floors._data.floor,
@ -919,10 +916,9 @@ editor_file = function (editor, callback) {
eval("items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a" + value[1] + '=' + JSON.stringify(value[2]));
});
var datastr = 'var items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a = \n';
datastr += JSON.stringify(items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a, function (k, v) {
if (v.id != null) delete v.id;
return v;
}, '\t');
var items = core.clone(items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a);
for (var id in items) delete items[id].id;
datastr += JSON.stringify(items, null, '\t');
fs.writeFile('project/items.js', encode(datastr), 'base64', function (err, data) {
callback(err);
});
@ -934,9 +930,10 @@ editor_file = function (editor, callback) {
});
var datastr = 'var enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80 = \n';
var emap = {};
var estr = JSON.stringify(enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80, function (k, v) {
if (v.hp != null) {
delete v.id;
var enemys = core.clone(enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80);
for (var id in enemys) delete enemys[id].id;
var estr = JSON.stringify(enemys, function (k, v) {
if (v && v.hp != null) {
var id_ = editor.util.guid();
emap[id_] = JSON.stringify(v);
return id_;

View File

@ -135,7 +135,7 @@ editor_game_wrapper = function (editor, main, core) {
// 获取当前地图
editor_game.prototype.fetchMapFromCore = function () {
var mapArray = core.getMapArray(core.status.floorId, true);
var mapArray = core.getMapArray(core.status.floorId);
editor.map = mapArray.map(function (v) {
return v.map(function (v) {
var x = parseInt(v), y = editor.indexs[x];
@ -151,7 +151,8 @@ editor_game_wrapper = function (editor, main, core) {
// 补出缺省的数据
editor.currentFloorData.autoEvent = editor.currentFloorData.autoEvent || {};
//
for (var ii = 0, name; name = ['bgmap', 'fgmap'][ii]; ii++) {
for (var ii = 0, name; name = editor.dom.canvas[ii]; ii++) {
name += 'map';
var mapArray = editor.currentFloorData[name];
if (!mapArray || JSON.stringify(mapArray) == JSON.stringify([])) {//未设置或空数组
//与editor.map同形的全0

View File

@ -28,15 +28,15 @@ editor_listen_wrapper = function (editor) {
editor.dom.iconLib.onmouseup = editor.uifunctions.material_onup
editor.dom.iconLib.oncontextmenu = function (e) { e.preventDefault() }
editor.dom.extraEvent.onmousedown = editor.uifunctions.extraEvent_click
editor.dom.chooseThis.onmousedown = editor.uifunctions.chooseThis_click
editor.dom.chooseInRight.onmousedown = editor.uifunctions.chooseInRight_click
editor.dom.copyLoc.onmousedown = editor.uifunctions.copyLoc_click
editor.dom.pasteLoc.onmousedown = editor.uifunctions.pasteLoc_click
editor.dom.clearEvent.onmousedown = editor.uifunctions.clearEvent_click
editor.dom.clearLoc.onmousedown = editor.uifunctions.clearLoc_click
editor.dom.extraEvent.onmouseup = editor.uifunctions.extraEvent_click
editor.dom.chooseThis.onmouseup = editor.uifunctions.chooseThis_click
editor.dom.chooseInRight.onmouseup = editor.uifunctions.chooseInRight_click
editor.dom.copyLoc.onmouseup = editor.uifunctions.copyLoc_click
editor.dom.pasteLoc.onmouseup = editor.uifunctions.pasteLoc_click
editor.dom.clearEvent.onmouseup = editor.uifunctions.clearEvent_click
editor.dom.clearLoc.onmouseup = editor.uifunctions.clearLoc_click
editor.dom.lastUsed.onmousedown = editor.uifunctions.lastUsed_click;
editor.dom.lastUsed.onmouseup = editor.uifunctions.lastUsed_click;
editor.dom.lastUsed.oncontextmenu = function (e) { e.preventDefault(); }
editor.dom.clearLastUsedBtn.onclick = editor.uifunctions.clearLastUsedBtn_click;
editor.dom.lockMode.onchange = editor.uifunctions.lockMode_onchange;

View File

@ -99,8 +99,7 @@ editor_mappanel_wrapper = function (editor) {
editor_mode.onmode('nextChange');
editor_mode.onmode('loc');
//editor_mode.loc();
//tip.whichShow(1);
tip.showHelp(6);
editor.uifunctions.showTips(6);
editor.uivalues.startPos = pos;
editor.dom.euiCtx.strokeStyle = '#FF0000';
editor.dom.euiCtx.lineWidth = 3;
@ -127,7 +126,6 @@ editor_mappanel_wrapper = function (editor) {
editor.uivalues.lastMoveE=e;
if (!selectBox.isSelected()) {
if (editor.uivalues.startPos == null) return;
//tip.whichShow(1);
var loc = editor.uifunctions.eToLoc(e);
var pos = editor.uifunctions.locToPos(loc, true);
if (editor.uivalues.endPos != null && editor.uivalues.endPos.x == pos.x && editor.uivalues.endPos.y == pos.y) return;
@ -163,8 +161,6 @@ editor_mappanel_wrapper = function (editor) {
// editor_mode.onmode('nextChange');
// editor_mode.onmode('loc');
//editor_mode.loc();
//tip.whichShow(1);
// tip.showHelp(6);
return false;
}
@ -218,6 +214,8 @@ editor_mappanel_wrapper = function (editor) {
var e=editor.uivalues.lastMoveE;
if (e.buttons == 2 && (editor.uivalues.endPos==null || (editor.uivalues.startPos.x == editor.uivalues.endPos.x && editor.uivalues.startPos.y == editor.uivalues.endPos.y))) {
editor.uifunctions.showMidMenu(e.clientX, e.clientY);
editor.uivalues.holdingPath = 0;
editor.uivalues.stepPostfix = [];
editor.dom.euiCtx.clearRect(0, 0, core.__PIXELS__, core.__PIXELS__);
editor.uivalues.startPos = editor.uivalues.endPos = null;
return false;
@ -230,7 +228,6 @@ editor_mappanel_wrapper = function (editor) {
// 后续的处理
} else {
// 左键拖拽: 交换
//tip.whichShow(1);
// editor.movePos(editor.uivalues.startPos, editor.uivalues.endPos);
editor.exchangePos(editor.uivalues.startPos, editor.uivalues.endPos);
editor.uifunctions.unhighlightSaveFloorButton();
@ -436,13 +433,10 @@ editor_mappanel_wrapper = function (editor) {
* 隐藏右键菜单
*/
editor.uifunctions.hideMidMenu = function () {
if (editor.isMobile) {
setTimeout(function () {
editor.dom.midMenu.style = 'display:none';
}, 200)
} else {
editor.uivalues.lastMoveE={buttons:0,clientX:0,clientY:0};
setTimeout(function () {
editor.dom.midMenu.style = 'display:none';
}
}, 100)
}
/**
@ -582,13 +576,15 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.chooseThis_click = function (e) {
editor.uifunctions.hideMidMenu();
e.stopPropagation();
e.stopImmediatePropagation();
e.preventDefault();
selectBox.isSelected(false);
editor_mode.onmode('nextChange');
editor_mode.onmode('loc');
//editor_mode.loc();
//tip.whichShow(1);
if (editor.isMobile) editor.showdataarea(false);
return false;
}
/**
@ -598,8 +594,11 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.chooseInRight_click = function (e) {
editor.uifunctions.hideMidMenu();
e.stopPropagation();
e.stopImmediatePropagation();
e.preventDefault();
var thisevent = editor[editor.layerMod][editor.pos.y][editor.pos.x];
editor.setSelectBoxFromInfo(thisevent, true);
return false;
}
/**
@ -609,11 +608,12 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.copyLoc_click = function (e) {
editor.uifunctions.hideMidMenu();
e.stopPropagation();
e.stopImmediatePropagation();
e.preventDefault();
editor_mode.onmode('');
editor.uivalues.copyedInfo = editor.copyFromPos();
printf('该点事件已复制');
return;
return false;
}
/**
@ -623,10 +623,11 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.pasteLoc_click = function (e) {
editor.uifunctions.hideMidMenu();
e.stopPropagation();
e.stopImmediatePropagation();
e.preventDefault();
if (!editor.uivalues.copyedInfo) {
printe("没有复制的事件");
return;
return false;
}
editor.savePreMap();
editor_mode.onmode('');
@ -641,7 +642,7 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.unhighlightSaveFloorButton();
editor.drawPosSelection();
});
return;
return false;
}
/**
@ -650,8 +651,11 @@ editor_mappanel_wrapper = function (editor) {
*/
editor.uifunctions.clearEvent_click = function (e) {
e.stopPropagation();
e.stopImmediatePropagation();
e.preventDefault();
editor.clearPos(false);
editor.uifunctions.unhighlightSaveFloorButton();
return false;
}
/**
@ -660,8 +664,11 @@ editor_mappanel_wrapper = function (editor) {
*/
editor.uifunctions.clearLoc_click = function (e) {
e.stopPropagation();
e.stopImmediatePropagation();
e.preventDefault();
editor.clearPos(true);
editor.uifunctions.unhighlightSaveFloorButton();
return false;
}
/**
@ -669,8 +676,7 @@ editor_mappanel_wrapper = function (editor) {
* 点击
*/
editor.uifunctions.lockMode_onchange = function () {
tip.msgs[11] = String('锁定模式开启下将不再点击空白处自动保存,请谨慎操作。');
tip.whichShow(12);
printf('锁定模式开启下将不再点击空白处自动保存,请谨慎操作。');
editor.uivalues.lockMode = editor.dom.lockMode.checked;
}
@ -681,9 +687,7 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.brushMod_onchange = function () {
editor.brushMod = editor.dom.brushMod.value;
if (editor.brushMod == 'fill') {
tip.isSelectedBlock(false);
tip.msgs[11] = String('填充模式下,将会用选中的素材替换所有和目标点联通的相同素材');
tip.whichShow(12);
printf('填充模式下,将会用选中的素材替换所有和目标点联通的相同素材');
}
}
@ -704,43 +708,36 @@ editor_mappanel_wrapper = function (editor) {
!confirm("从V2.7开始,请直接素材区拖框进行绘制区域。\n\n点取消将不再显示此提示。")) {
editor.config.set('alertTileModeV2.7', true);
}
// tip.showHelp(5)
tip.isSelectedBlock(false)
tip.msgs[11] = String('tileset平铺模式下可以按选中tileset素材并在地图上拖动来一次绘制一个区域');
tip.whichShow(12);
printf('tileset平铺模式下可以按选中tileset素材并在地图上拖动来一次绘制一个区域');
editor.brushMod = editor.dom.brushMod3.value;
}
editor.uifunctions.brushMod4_onchange = function () {
tip.isSelectedBlock(false);
tip.msgs[11] = String('填充模式下,将会用选中的素材替换所有和目标点联通的相同素材');
tip.whichShow(12);
printf('填充模式下,将会用选中的素材替换所有和目标点联通的相同素材');
editor.brushMod = editor.dom.brushMod4.value;
}
editor.uifunctions.setLayerMod = function (layer) {
editor.layerMod = layer;
var canvas = ['ev', 'ev2'].concat(editor.dom.canvas);
canvas.forEach(function (one) {
editor.dom[one+'c'].style.opacity = 1;
});
if (layer != 'map') {
canvas.filter(function (one) {
return one + 'map' != editor.layerMod
}).forEach(function (one) {
editor.dom[one+'c'].style.opacity = 0.3;
});
}
}
/**
* editor.dom.layerMod.onchange
* 切换编辑的层
*/
editor.uifunctions.layerMod_onchange = function () {
editor.layerMod = editor.dom.layerMod.value;
[editor.dom.bgc, editor.dom.fgc, editor.dom.evc, editor.dom.ev2c].forEach(function (x) {
x.style.opacity = 1;
});
// 手机端....
if (editor.isMobile) {
if (editor.dom.layerMod.value == 'bgmap') {
[editor.dom.fgc, editor.dom.evc, editor.dom.ev2c].forEach(function (x) {
x.style.opacity = 0.3;
});
}
if (editor.dom.layerMod.value == 'fgmap') {
[editor.dom.bgc, editor.dom.evc, editor.dom.ev2c].forEach(function (x) {
x.style.opacity = 0.3;
});
}
}
editor.uifunctions.setLayerMod(editor.dom.layerMod.value);
}
/**
@ -748,11 +745,7 @@ editor_mappanel_wrapper = function (editor) {
* 切换编辑的层
*/
editor.uifunctions.layerMod2_onchange = function () {
editor.layerMod = editor.dom.layerMod2.value;
[editor.dom.fgc, editor.dom.evc, editor.dom.ev2c].forEach(function (x) {
x.style.opacity = 0.3;
});
editor.dom.bgc.style.opacity = 1;
editor.uifunctions.setLayerMod('bgmap');
}
/**
@ -760,11 +753,7 @@ editor_mappanel_wrapper = function (editor) {
* 切换编辑的层
*/
editor.uifunctions.layerMod3_onchange = function () {
editor.layerMod = editor.dom.layerMod3.value;
[editor.dom.bgc, editor.dom.evc, editor.dom.ev2c].forEach(function (x) {
x.style.opacity = 0.3;
});
editor.dom.fgc.style.opacity = 1;
editor.uifunctions.setLayerMod('fgmap');
}
/**
@ -773,6 +762,13 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.viewportButtons_func = function () {
var pressTimer = null;
for (var ii = 0, node; node = editor.dom.viewportButtons.children[ii]; ii++) {
if (ii == 4) {
// 大地图
node.onclick = function () {
editor.uievent.selectPoint(null, editor.pos.x, editor.pos.y, true);
}
continue;
}
(function (x, y) {
var move = function () {
editor.moveViewport(x, y);
@ -820,7 +816,7 @@ editor_mappanel_wrapper = function (editor) {
editor.uifunctions.highlightSaveFloorButton=function(){
var saveFloor = document.getElementById('saveFloor');
saveFloor.style.background='#FFCCAA';
saveFloor.style.background='#ffd700';
}
editor.uifunctions.unhighlightSaveFloorButton=function(){
@ -845,7 +841,10 @@ editor_mappanel_wrapper = function (editor) {
}
editor.uifunctions.lastUsed_click = function (e) {
if (editor.isMobile) return;
e.preventDefault();
e.stopImmediatePropagation();
e.stopPropagation();
if (editor.isMobile) return false;
var scrollLeft = document.documentElement.scrollLeft || document.body.scrollLeft
var scrollTop = document.documentElement.scrollTop || document.body.scrollTop
@ -968,11 +967,10 @@ editor_mappanel_wrapper = function (editor) {
}
editor.constructor.prototype.savePreMap = function () {
var dt = {
map: editor.map,
fgmap: editor.fgmap,
bgmap: editor.bgmap,
};
var dt = {};
editor.dom.maps.forEach(function (one) {
dt[one] = editor[one];
});
if (editor.uivalues.preMapData.length == 0
|| !core.same(editor.uivalues.preMapData[editor.uivalues.preMapData.length - 1], dt)) {
editor.uivalues.preMapData.push(core.clone(dt));

View File

@ -8,9 +8,6 @@ editor_materialpanel_wrapper = function (editor) {
selectBox.isSelected=function(value){
if(value!=null){
selectBox._isSelected=value;
tip.isSelectedBlock(value);
tip.whichShow(0);
clearTimeout(tip.timer);
editor.dom.dataSelection.style.display=value?'':'none'
}
return selectBox._isSelected
@ -230,7 +227,7 @@ editor_materialpanel_wrapper = function (editor) {
}
}
tip.infos(JSON.parse(JSON.stringify(editor.info)));
editor.uifunctions.showBlockInfo(JSON.parse(JSON.stringify(editor.info)));
editor_mode.onmode('nextChange');
editor_mode.onmode('enemyitem');
editor.updateLastUsedMap();

View File

@ -57,7 +57,20 @@ editor_mode = function (editor) {
printe(objs_.slice(-1)[0]);
throw (objs_.slice(-1)[0])
}
; printf('修改成功' + (data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d.firstData.name == 'template' ? '\n\n请注意全塔属性的name尚未修改请及时予以设置' : ''));
;
var str = '修改成功!';
if (data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d.firstData.name == 'template')
str += '\n请注意全塔属性的name尚未修改请及时予以设置。';
if (mode == 'enemyitem') {
if (editor.info && editor.info.idnum) {
var block = editor.core.maps.blocksInfo[editor.info.idnum];
if (block.doorInfo != null && block.doorInfo.keys != null && Object.keys(block.doorInfo.keys).length > 0
&& block.trigger != 'openDoor') {
str += "\n你修改了门信息但触发器未改成openDoor请修改否则无法撞击开门。"
}
}
}
printf(str);
if (callback) callback();
}
switch (mode) {
@ -115,7 +128,7 @@ editor_mode = function (editor) {
editor.drawEventBlock();
if (editor_mode[mode]) editor_mode[mode]();
editor.dom.editModeSelect.value = mode;
if (!selectBox.isSelected()) tip.showHelp();
if (!selectBox.isSelected()) editor.uifunctions.showTips();
}
editor_mode.prototype.change = function (value) {

View File

@ -49,10 +49,14 @@ editor_table_wrapper = function (editor) {
editor_table.prototype.checkboxSetMember = function (value,key,prefixString) {
return /* html */`${prefixString}<input key='${key}' ctype='${typeof key}' type='checkbox' class='checkboxSetMember' onchange='editor.table.checkboxSetMemberOnchange(this)' ${(value ? 'checked ' : '')}/>\n`;
}
editor_table.prototype.editGrid = function (showComment, showEdit) {
editor_table.prototype.editGrid = function (showComment, type) {
var list = [];
if (showComment) list.push("<button onclick='editor.table.onCommentBtnClick(this)'>注释</button>");
if (showEdit) list.push("<button onclick='editor.table.onEditBtnClick(this)'>编辑</button>");
if (type != 'select' && type != 'checkbox' && type != 'checkboxSet' && type != 'popCheckboxSet' && type != 'disable')
list.push("<button onclick='editor.table.onEditBtnClick(this)' style='background-color: #ddf8ff'>编辑</button>");
if (type == 'popCheckboxSet')
list.push("<button onclick='editor.table.onEditBtnClick(this)' style='background-color: #ddf8ff'>多选框编辑</button>");
if (type == 'disable') list.push("<button onclick='editor.table.onCopyBtnClick(this)'>复制</button>");
return list.join(' ');
}
@ -70,7 +74,7 @@ editor_table_wrapper = function (editor) {
<td>----</td>
<td>----</td>
<td>${field}</td>
<td><button style="background: #FFCCAA" onclick='editor.table.onFoldBtnClick(this)' data-fold="${ status ? "true" : "false" }">${ status ? "展开" : "折叠" }</button></td>
<td><button style="background: #fff4bb" onclick='editor.table.onFoldBtnClick(this)' data-fold="${ status ? "true" : "false" }">${ status ? "展开" : "折叠" }</button></td>
</tr>\n`
}
@ -79,13 +83,15 @@ editor_table_wrapper = function (editor) {
<td title="${field}">${shortField}</td>
<td title="${commentHTMLescape}" cobj="${cobjstr}">${shortComment || commentHTMLescape}</td>
<td><div class="etableInputDiv ${type}">${tdstr}</div></td>
<td>${editor.table.editGrid(shortComment, type != 'select' && type != 'checkbox' && type != 'checkboxSet' && type != 'disable')}</td>
<td>${editor.table.editGrid(shortComment, type)}</td>
</tr>\n`
}
/**
* checkboxset中checkbox的onchange
* 这个函数本质是模板editor_table.prototype.checkboxSetMember的一部分
* 故放在HTML模板分类下
*/
editor_table.prototype.checkboxSetMemberOnchange = function (onemember) {
var thisset=onemember.parentNode
@ -416,6 +422,23 @@ editor_table_wrapper = function (editor) {
if (cobj._type === 'textarea') editor_multi.import(guid, { lint: cobj._lint, string: cobj._string });
if (cobj._type === 'material') editor.table.selectMaterial(input, cobj);
if (cobj._type === 'color') editor.table.selectColor(input);
if (cobj._type === 'point') editor.table.selectPoint(input);
if (cobj._type === 'popCheckboxSet') editor.table.popCheckboxSet(input, cobj);
}
editor_table.prototype.onCopyBtnClick = function (button) {
var tr = button.parentNode.parentNode;
var input = tr.children[2].children[0].children[0];
var value = JSON.parse(input.value);
if (value == null) {
printe('没有赋值的内容');
return;
}
if (core.copy(value.toString())) {
printf('复制成功!');
} else {
printe('无法复制此内容,请手动选择复制');
}
}
/**
@ -431,6 +454,8 @@ editor_table_wrapper = function (editor) {
if (cobj._type === 'textarea') editor_multi.import(guid, { lint: cobj._lint, string: cobj._string });
if (cobj._type === 'material') editor.table.selectMaterial(input, cobj);
if (cobj._type === 'color') editor.table.selectColor(input);
if (cobj._type === 'point') editor.table.selectPoint(input);
if (cobj._type === 'popCheckboxSet') editor.table.popCheckboxSet(input, cobj);
} else if (editor_mode.doubleClickMode === 'add') {
editor_mode.doubleClickMode = 'change';
editor.table.addfunc(guid, obj, commentObj, thisTr, input, field, cobj, modeNode)
@ -466,6 +491,30 @@ editor_table_wrapper = function (editor) {
})
}
editor_table.prototype.selectPoint = function (input) {
var x = 0, y = 0, value = input.value;
if (value != null) {
try {
var loc = JSON.parse(value);
if (loc instanceof Array && loc.length == 2) {
x = loc[0];
y = loc[1];
}
} catch (e) {}
}
editor.uievent.selectPoint(editor.currentFloorId, x, y, false, function (floorId, x, y) {
input.value = '['+x+','+y+']';
input.onchange();
})
}
editor_table.prototype.popCheckboxSet = function (input, cobj) {
editor.uievent.popCheckboxSet(JSON.parse(input.value), cobj._checkboxSet, cobj._docs || cobj._data || '请选择多选项', function (value) {
input.value = JSON.stringify(value);
input.onchange();
})
}
/**
* 删除表格项
*/

View File

@ -1,29 +1,46 @@
editor_ui_wrapper = function (editor) {
// 由于历史遗留原因, 以下变量作为全局变量使用
// printf printe tip
window.printf = function (str_, type) {
selectBox.isSelected(false);
if (!type) {
tip.whichShow(11);
} else {
tip.whichShow(12);
var tip=document.getElementById('tip');
var print = function (msg, cls) {
if (msg == '') {
tip.innerHTML = '';
return;
}
setTimeout(function () {
if (!type) {
tip.msgs[11] = String(str_);
tip.whichShow(12);
} else {
tip.msgs[10] = String(str_);
tip.whichShow(11);
}
}, 1);
tip.innerHTML = '<p class="'+cls+'">' + msg + "</p>";
}
window.printe = function (str_) {
printf(str_, 'error')
window.printf = function (msg) {
selectBox.isSelected(false);
print(msg, 'successText');
}
window.tip=document.getElementById('tip')
tip.showHelp = function(value) {
window.printe = function (msg) {
selectBox.isSelected(false);
print(msg, 'warnText');
}
window.printi = function (msg) {
print(msg, 'infoText');
}
editor.uifunctions.showBlockInfo = function (value) {
if (value == 0) {
printi("当前选择为清除块,可擦除地图上块");
return;
}
var hasId = 'id' in value;
if (hasId && value.idnum == 17) {
printi("当前选择为空气墙, 在编辑器中可视, 在游戏中隐藏的墙, 用来配合前景/背景的贴图");
return;
}
var isAutotile = hasId && value.images == "autotile";
tip.innerHTML = (hasId?`<p>图块编号:<span class="infoText">${ value['idnum'] }</span></p>
<p>图块ID<span class="infoText">${ value['id'] }</span></p>`:`
<p class="warnText">该图块无对应的数字或ID存在请先前往icons.js和maps.js中进行定义</p>`)+`
<p>图块所在素材<span class="infoText">${ value['images'] + (isAutotile ? '( '+value['id']+' )' : '') }</span>
</p>
<p>图块索引<span class="infoText">${ value['y'] }</span></p>`;
}
editor.uifunctions.showTips = function (value) {
var tips = [
'表格的文本域可以双击进行编辑',
'双击地图可以选中素材,右键可以弹出菜单',
@ -37,147 +54,6 @@ editor_ui_wrapper = function (editor) {
if (value == null) value = Math.floor(Math.random() * tips.length);
printf('tips: ' + tips[value])
}
tip._infos= {}
tip.infos=function(value){
if(value!=null){
var val=value
var oldval=tip._infos
tip.isClearBlock(false);
tip.isAirwall(false);
if (typeof(val) != 'undefined') {
if (val == 0) {
tip.isClearBlock(true);
return;
}
if ('id' in val) {
if (val.idnum == 17) {
tip.isAirwall(true);
return;
}
tip.hasId = true;
} else {
tip.hasId = false;
}
tip.isAutotile = false;
if (val.images == "autotile" && tip.hasId) tip.isAutotile = true;
document.getElementById('isAirwall-else').innerHTML=(tip.hasId?`<p>图块编号:<span class="infoText">${ value['idnum'] }</span></p>
<p>图块ID<span class="infoText">${ value['id'] }</span></p>`:`
<p class="warnText">该图块无对应的数字或ID存在请先前往icons.js和maps.js中进行定义</p>`)+`
<p>图块所在素材<span class="infoText">${ value['images'] + (tip.isAutotile ? '( '+value['id']+' )' : '') }</span>
</p>
<p>图块索引<span class="infoText">${ value['y'] }</span></p>`
}
tip._infos=value
}
return tip._infos
}
tip.hasId= true
tip.isAutotile= false
tip._isSelectedBlock= false
tip.isSelectedBlock=function(value){
if(value!=null){
var dshow=document.getElementById('isSelectedBlock-if')
var dhide=document.getElementById('isSelectedBlock-else')
if(!value){
var dtemp=dshow
dshow=dhide
dhide=dtemp
}
dshow.style.display=''
dhide.style.display='none'
tip._isSelectedBlock=value
}
return tip._isSelectedBlock
}
tip._isClearBlock= false
tip.isClearBlock=function(value){
if(value!=null){
var dshow=document.getElementById('isClearBlock-if')
var dhide=document.getElementById('isClearBlock-else')
if(!value){
var dtemp=dshow
dshow=dhide
dhide=dtemp
}
dshow.style.display=''
dhide.style.display='none'
tip._isClearBlock=value
}
return tip._isClearBlock
}
tip._isAirwall= false
tip.isAirwall=function(value){
if(value!=null){
var dshow=document.getElementById('isAirwall-if')
var dhide=document.getElementById('isAirwall-else')
if(!value){
var dtemp=dshow
dshow=dhide
dhide=dtemp
}
dshow.style.display=''
dhide.style.display='none'
tip._isAirwall=value
}
return tip._isAirwall
}
tip.geneMapSuccess= false
tip.timer= null
tip.msgs= [ //分别编号1,2,3,4,5,6,7,8,9,10奇数警告偶数成功
"当前未选择任何图块,请先在右边选择要画的图块!",
"生成地图成功!可点击复制按钮复制地图数组到剪切板",
"生成失败! 地图中有未定义的图块,建议先用其他有效图块覆盖或点击清除地图!",
"地图清除成功!",
"复制失败!",
"复制成功!可直接粘贴到楼层文件的地图数组中。",
"复制失败!当前还没有数据",
"修改成功!可点击复制按钮复制地图数组到剪切板",
"选择背景图片失败!文件名格式错误或图片不存在!",
"更新背景图片成功!",
"11:警告",
"12:成功"
]
tip._mapMsg= ''
tip.mapMsg=function(value){
if(value!=null){
document.getElementById('whichShow-if').innerText=value
tip._mapMsg=value
}
return tip._mapMsg
}
tip._whichShow= 0
tip.whichShow=function(value){
if(value!=null){
var dshow=document.getElementById('whichShow-if')
var dhide=null
if(!value){
var dtemp=dshow
dshow=dhide
dhide=dtemp
}
if(dshow)dshow.style.display=''
if(dhide)dhide.style.display='none'
if(dshow)dshow.setAttribute('class',(value%2) ? 'warnText' : 'successText')
tip.mapMsg('');
tip.msgs[4] = "复制失败!" + editTip.err;
clearTimeout(tip.timer);
if (value) {
tip.mapMsg(tip.msgs[value - 1]);
tip.timer = setTimeout(function () {
if (!(value % 2))
value = 0;
}, 5000); //5秒后自动清除successwarn不清除
}
tip._whichShow=value
}
return tip._whichShow
}
/**
* 根据鼠标点击, 得到从元素向上到body的所有id
@ -247,7 +123,7 @@ editor_ui_wrapper = function (editor) {
if (e.button != 2 && !editor.isMobile) {
editor.uifunctions.hideMidMenu();
}
if (clickpath.indexOf('down') !== -1 && editor.isMobile && clickpath.indexOf('midMenu') === -1) {
if (clickpath.indexOf('down') !== -1 && clickpath.indexOf('midMenu') === -1 && editor.isMobile && clickpath.indexOf('midMenu') === -1) {
editor.uifunctions.hideMidMenu();
}
if (clickpath.length >= 2 && clickpath[0].indexOf('id_') === 0) { editor.lastClickId = clickpath[0] }
@ -261,13 +137,7 @@ editor_ui_wrapper = function (editor) {
// UI预览 & 地图选点
if (editor.uievent && editor.uievent.isOpen) {
e.preventDefault();
if (e.keyCode == 27) editor.uievent.close();
else if (e.keyCode == 13) editor.uievent.confirm();
else if (e.keyCode == 87) editor.uievent.move(0, -1)
else if (e.keyCode == 65) editor.uievent.move(-1, 0)
else if (e.keyCode == 83) editor.uievent.move(0, 1);
else if (e.keyCode == 68) editor.uievent.move(1, 0);
editor.uievent.onKeyDown(e);
return;
}
@ -314,9 +184,9 @@ editor_ui_wrapper = function (editor) {
e.preventDefault();
if (editor.uivalues.preMapData.length > 0) {
var data = editor.uivalues.preMapData.pop();
editor.map = JSON.parse(JSON.stringify(data.map));
editor.fgmap = JSON.parse(JSON.stringify(data.fgmap));
editor.bgmap = JSON.parse(JSON.stringify(data.bgmap));
editor.dom.maps.forEach(function (one) {
editor[one] = JSON.parse(JSON.stringify(data[one]));
});
editor.updateMap();
editor.uivalues.postMapData.push(data);
editor.uifunctions.highlightSaveFloorButton();
@ -329,9 +199,9 @@ editor_ui_wrapper = function (editor) {
e.preventDefault();
if (editor.uivalues.postMapData.length > 0) {
var data = editor.uivalues.postMapData.pop();
editor.map = JSON.parse(JSON.stringify(data.map));
editor.fgmap = JSON.parse(JSON.stringify(data.fgmap));
editor.bgmap = JSON.parse(JSON.stringify(data.bgmap));
editor.dom.maps.forEach(function (one) {
editor[one] = JSON.parse(JSON.stringify(data[one]));
});
editor.updateMap();
editor.uivalues.preMapData.push(data);
editor.uifunctions.highlightSaveFloorButton();
@ -475,12 +345,15 @@ editor_ui_wrapper = function (editor) {
uievent.elements.selectPointButtons = document.getElementById('selectPointButtons');
uievent.elements.canvas = document.getElementById('uievent');
uievent.elements.usedFlags = document.getElementById('uieventUsedFlags');
uievent.elements.usedFlagList = document.getElementById('uieventUsedFlagList');
uievent.elements.materialList = document.getElementById('uieventMaterialList');
uievent.elements.extraBody = document.getElementById('uieventExtraBody');
uievent.close = function () {
uievent.isOpen = false;
uievent.elements.div.style.display = 'none';
if (uievent.values.interval) {
clearTimeout(uievent.values.interval);
clearInterval(uievent.values.interval);
}
uievent.values = {};
}
uievent.elements.no.onclick = uievent.close;
@ -524,18 +397,16 @@ editor_ui_wrapper = function (editor) {
uievent.elements.selectPointBox.style.display = 'none';
uievent.elements.canvas.style.display = 'block';
uievent.elements.usedFlags.style.display = 'none';
uievent.elements.usedFlagList.style.display = 'none';
uievent.elements.extraBody.style.display = 'none';
uievent.elements.body.style.overflow = "hidden";
uievent.values.list = list;
uievent.drawPreviewUI();
}
uievent.selectPoint = function (floorId, x, y, hideFloor, callback) {
uievent.values.hideFloor = hideFloor;
uievent.selectPoint = function (floorId, x, y, bigmap, callback) {
uievent.values.bigmap = bigmap;
uievent.values.size = editor.isMobile ? window.innerWidth / core.__SIZE__ : 32;
uievent.elements.selectPointBox.style.width = (uievent.values.size - 6) + "px";
uievent.elements.selectPointBox.style.height = (uievent.values.size - 6) + "px";
uievent.isOpen = true;
uievent.elements.div.style.display = 'block';
@ -543,12 +414,11 @@ editor_ui_wrapper = function (editor) {
uievent.elements.selectPoint.style.display = 'block';
uievent.elements.yes.style.display = 'inline';
uievent.elements.selectBackground.style.display = 'none';
// uievent.elements.selectFloor.style.display = hideFloor ? 'none' : 'inline';
uievent.elements.selectFloor.style.display = 'inline';
uievent.elements.selectPointBox.style.display = 'block';
uievent.elements.canvas.style.display = 'block';
uievent.elements.usedFlags.style.display = 'none';
uievent.elements.usedFlagList.style.display = 'none';
uievent.elements.extraBody.style.display = 'none';
uievent.elements.body.style.overflow = "hidden";
uievent.elements.yes.onclick = function () {
var floorId = uievent.values.floorId, x = uievent.values.x, y = uievent.values.y;
@ -576,11 +446,26 @@ editor_ui_wrapper = function (editor) {
core.drawThumbnail(uievent.values.floorId, null, null,
{
ctx: 'uievent', centerX: uievent.values.left + core.__HALF_SIZE__,
centerY: uievent.values.top + core.__HALF_SIZE__
centerY: uievent.values.top + core.__HALF_SIZE__, all: uievent.values.bigmap
});
}
uievent.elements.selectPointBox.style.left = uievent.values.size * (uievent.values.x - uievent.values.left) + "px";
uievent.elements.selectPointBox.style.top = uievent.values.size * (uievent.values.y - uievent.values.top) + "px";
// 计算size
uievent.values.boxSize = uievent.values.size *
(uievent.values.bigmap ? (core.__SIZE__ / Math.max(uievent.values.width, uievent.values.height)) : 1);
uievent.values.boxLeft = uievent.values.bigmap ?
(core.__PIXELS__ * Math.max(0, (1 - uievent.values.width / uievent.values.height) / 2)) : 0;
uievent.values.boxTop = uievent.values.bigmap ?
(core.__PIXELS__ * Math.max(0, (1 - uievent.values.height / uievent.values.width) / 2)) : 0;
if (uievent.values.bigmap) {
uievent.elements.selectPointBox.style.left = uievent.values.boxSize * uievent.values.x + uievent.values.boxLeft + "px";
uievent.elements.selectPointBox.style.top = uievent.values.boxSize * uievent.values.y + uievent.values.boxTop + "px";
} else {
uievent.elements.selectPointBox.style.left = uievent.values.boxSize * (uievent.values.x - uievent.values.left) + "px";
uievent.elements.selectPointBox.style.top = uievent.values.boxSize * (uievent.values.y - uievent.values.top) + "px";
}
uievent.elements.selectPointBox.style.width = uievent.values.boxSize - 6 + "px";
uievent.elements.selectPointBox.style.height = uievent.values.boxSize - 6 + "px";
}
uievent.setPoint = function (floorId, x, y) {
@ -606,23 +491,44 @@ editor_ui_wrapper = function (editor) {
uievent.elements.body.onclick = function (e) {
if (uievent.mode != 'selectPoint') return;
uievent.values.x = uievent.values.left + Math.floor(e.offsetX / uievent.values.size);
uievent.values.y = uievent.values.top + Math.floor(e.offsetY / uievent.values.size);
if (uievent.values.bigmap) {
uievent.values.x = core.clamp(Math.floor((e.offsetX - uievent.values.boxLeft) / uievent.values.boxSize), 0, uievent.values.width - 1);
uievent.values.y = core.clamp(Math.floor((e.offsetY - uievent.values.boxTop) / uievent.values.boxSize), 0, uievent.values.height - 1);
} else {
uievent.values.x = uievent.values.left + Math.floor(e.offsetX / uievent.values.size);
uievent.values.y = uievent.values.top + Math.floor(e.offsetY / uievent.values.size);
}
uievent.updateSelectPoint(false);
}
uievent.move = function (dx, dy) {
if (uievent.mode != 'selectPoint') return;
if (uievent.values.bigmap) return;
uievent.values.left = core.clamp(uievent.values.left + dx, 0, uievent.values.width - core.__SIZE__);
uievent.values.top = core.clamp(uievent.values.top + dy, 0, uievent.values.height - core.__SIZE__);
this.updateSelectPoint(true);
};
uievent.triggerBigmap = function () {
if (uievent.mode != 'selectPoint') return;
uievent.values.bigmap = !uievent.values.bigmap;
uievent.setPoint(uievent.values.floorId);
};
(function () {
var viewportButtons = uievent.elements.selectPointButtons;
var pressTimer = null;
for (var ii = 0, node; node = viewportButtons.children[ii]; ii++) {
if (ii == 4) {
node.onclick = uievent.triggerBigmap;
continue;
}
if (ii == 5) {
node.onclick = function () {
alert(core.copy(uievent.values.floorId) ? ('楼层ID '+uievent.values.floorId+' 已成功复制到剪切板') : '无法复制楼层ID');
}
}
(function (x, y) {
var move = function () {
uievent.move(x, y);
@ -652,7 +558,6 @@ editor_ui_wrapper = function (editor) {
})();
uievent.elements.div.onmousewheel = function (e) {
// if (uievent.mode != 'selectPoint' || uievent.values.hideFloor) return;
if (uievent.mode != 'selectPoint') return;
var index = core.floorIds.indexOf(uievent.values.floorId);
try {
@ -665,6 +570,16 @@ editor_ui_wrapper = function (editor) {
uievent.setPoint(core.floorIds[index]);
}
uievent.onKeyDown = function (e) {
if (e.keyCode == 27) editor.uievent.close();
if (uievent.mode == 'selectPoint') {
if (e.keyCode == 87) editor.uievent.move(0, -1)
if (e.keyCode == 65) editor.uievent.move(-1, 0)
if (e.keyCode == 83) editor.uievent.move(0, 1);
if (e.keyCode == 68) editor.uievent.move(1, 0);
}
}
// ------ 搜索变量出现的位置也放在uievent好了 ------ //
uievent.searchUsedFlags = function () {
@ -679,7 +594,7 @@ editor_ui_wrapper = function (editor) {
uievent.elements.selectPointBox.style.display = 'none';
uievent.elements.canvas.style.display = 'none';
uievent.elements.usedFlags.style.display = 'inline';
uievent.elements.usedFlagList.style.display = 'block';
uievent.elements.extraBody.style.display = 'block';
uievent.elements.body.style.overflow = "auto";
// build flags
@ -708,7 +623,7 @@ editor_ui_wrapper = function (editor) {
html += x;
});
html += "</ul>";
uievent.elements.usedFlagList.innerHTML = html;
uievent.elements.extraBody.innerHTML = html;
}
var hasUsedFlags = function (obj, flag) {
@ -775,8 +690,7 @@ editor_ui_wrapper = function (editor) {
uievent.elements.selectPointBox.style.display = 'none';
uievent.elements.canvas.style.display = 'none';
uievent.elements.usedFlags.style.display = 'none';
uievent.elements.usedFlagList.style.display = 'none';
uievent.elements.materialList.style.display = 'block';
uievent.elements.extraBody.style.display = 'block';
uievent.elements.body.style.overflow = "auto";
uievent.elements.yes.onclick = function () {
@ -805,10 +719,19 @@ editor_ui_wrapper = function (editor) {
<audio preload="none" src="${directory+one}" ontimeupdate="editor.uievent._previewMaterialAudio_onTimeUpdate(this)"></audio>
<progress value="0" max="1" style="display:none; width:100%" onclick="editor.uievent._previewMaterialAudio_seek(this, event)"></progress>`;
}
// 预览动画
if (directory.indexOf('animates') >= 0) {
html += "<button onclick='editor.uievent._previewMaterialAnimate(this)' style='margin-left: 10px'>预览</button>";
html += `<span style="display:none; margin-left: 10px" key="${directory+one+'.animate'}"><br/>音效:<input type="text" />
<button onclick="editor.uievent._previewMaterialAnimate_previewSound(this)" style='marin-left: 10px'>试听</button>
<button onclick="editor.uievent._previewMaterialAnimate_saveSound(this)">保存</button><br/>
</span>`;
}
html += '<br/>';
});
html += "</p>";
uievent.elements.materialList.innerHTML = html;
html += "<p style='margin-left: 10px'><small>如果文件未在此列表显示,请检查文件名是否合法(只能由数字字母下划线横线和点组成),后缀名是否正确。</small></p>";
uievent.elements.extraBody.innerHTML = html;
});
}
@ -869,6 +792,155 @@ editor_ui_wrapper = function (editor) {
if (audio.paused) audio.play();
}
var _previewMaterialAnimate = function (span, content) {
var input = span.children[1];
input.value = content.se || "";
// 创建dom
if (!uievent.values.dom) {
var dom = document.createElement('span');
dom.style.position = "relative";
dom.style.marginLeft = "-10px";
var canvas = document.createElement('canvas');
canvas.width = canvas.height = core.__PIXELS__;
canvas.style.position = 'absolute';
core.drawThumbnail(editor.currentFloorId, null, {}, canvas.getContext('2d'));
dom.appendChild(canvas);
var canvas2 = document.createElement('canvas');
canvas2.style.position = 'absolute';
canvas2.width = canvas2.height = core.__PIXELS__;
uievent.values.ctx = canvas2.getContext('2d');
dom.appendChild(canvas2);
var canvas3 = document.createElement('canvas');
canvas3.width = canvas3.height = core.__PIXELS__;
dom.appendChild(canvas3);
uievent.values.dom = dom;
}
span.appendChild(uievent.values.dom);
clearInterval(uievent.values.interval);
var frame = 0;
uievent.values.interval = setInterval(function () {
if (span.style.display == 'none') {
clearInterval(uievent.values.interval);
uievent.values.interval = null;
span.removeChild(uievent.values.dom);
return;
}
core.clearMap(uievent.values.ctx);
core.maps._drawAnimateFrame(uievent.values.ctx, content, core.__PIXELS__ / 2, core.__PIXELS__ / 2, frame++);
}, 50);
}
uievent._previewMaterialAnimate = function (button) {
var span = button.nextElementSibling;
var filename = span.getAttribute("key");
uievent.values.animates = uievent.values.animates || {};
if (span.style.display == 'none') {
button.innerText = '收起';
span.style.display = 'inline';
if (uievent.values.animates[filename]) {
_previewMaterialAnimate(span, uievent.values.animates[filename]);
} else {
fs.readFile(filename, 'utf-8', function (e, d) {
if (e) {
alert('无法打开动画文件!'+e); return;
}
uievent.values.animates[filename] = core.loader._loadAnimate(d);
if (uievent.values.animates[filename]) {
uievent.values.animates[filename + ':raw'] = JSON.parse(d);
_previewMaterialAnimate(span, uievent.values.animates[filename]);
}
})
}
} else {
button.innerText = '预览';
span.style.display = 'none';
}
}
uievent._previewMaterialAnimate_previewSound = function (button) {
var input = button.previousElementSibling;
if (!input.value) return;
if (!uievent.values.audio)
uievent.values.audio = new Audio();
uievent.values.audio.src = './project/sounds/' + input.value;
uievent.values.audio.play();
}
uievent._previewMaterialAnimate_saveSound = function (button) {
var input = button.previousElementSibling.previousElementSibling;
var filename = button.parentElement.getAttribute("key");
if (!filename || !uievent.values.animates[filename]) return;
uievent.values.animates[filename+':raw'].se = input.value || "";
fs.writeFile(filename, JSON.stringify(uievent.values.animates[filename+':raw']), 'utf-8', function (e, d) {
if (e) alert('无法修改音效文件!'+e);
else {
alert('动画音效修改成功!别忘了在全塔属性中注册本音效哦!');
}
})
}
// ------ 多选框 ------ //
uievent.popCheckboxSet = function (value, comments, title, callback) {
if (value == null) value = [];
if (!(value instanceof Array)) {
if (value == 0) value = [];
else value = [value];
}
uievent.isOpen = true;
uievent.elements.div.style.display = 'block';
uievent.mode = 'popCheckboxSet';
uievent.elements.selectPoint.style.display = 'none';
uievent.elements.yes.style.display = 'block';
uievent.elements.title.innerText = title;
uievent.elements.selectBackground.style.display = 'none';
uievent.elements.selectFloor.style.display = 'none';
uievent.elements.selectPointBox.style.display = 'none';
uievent.elements.canvas.style.display = 'none';
uievent.elements.usedFlags.style.display = 'none';
uievent.elements.extraBody.style.display = 'block';
uievent.elements.body.style.overflow = "auto";
uievent.elements.yes.onclick = function () {
var list = Array.from(document.getElementsByClassName('uieventCheckboxSet')).filter(function (one) {
return one.checked;
}).map(function (one) {
var value = one.getAttribute('key');
if (one.getAttribute('_type') == 'number') value = parseFloat(value);
return value;
});
uievent.close();
if (callback) callback(list);
}
var keys=Array.from(comments.key)
var prefixStrings=Array.from(comments.prefix)
for (var index = 0; index < value.length; index++) {
if (keys.indexOf(value[index])==-1) {
prefixStrings.push(value[index]+': ')
keys.push(value[index])
}
}
var table = '<table style="width: 100%">';
for (var index = 0; index < keys.length; index++) {
var one = keys[index];
if (index % 3 == 0) {
table += '<tr>';
}
table += `<td style='color:black'>${prefixStrings[index]}<input type="checkbox" _type="${typeof one}" key="${one}" class="uieventCheckboxSet" ${value.indexOf(one) >= 0? 'checked' : ''}/></td>`;
if (index % 3 == 2) {
table += '</tr>';
}
}
if (keys.length % 3 != 0) table += '</tr>';
table += '</table>';
uievent.elements.extraBody.innerHTML = "<p>"+table+"</p>";
}
editor.constructor.prototype.uievent=uievent;
}

View File

@ -2,6 +2,7 @@
* 表格配置项
* 在这里可以对表格中的各项显示进行配置包括表格项提示内容等内容具体写法照葫芦画瓢即可
* 本配置项包括道具怪物图块属性楼层属性等内容
* 相关文档 _docs/editor.md ~ http://127.0.0.1:1055/_docs/#/editor?id=修改表格
*/
var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
@ -167,19 +168,20 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
},
"special": {
"_leaf": true,
"_type": "checkboxSet",
"_checkboxSet":function(){
var array=functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a.enemys.getSpecials()
var b=[],c=[];
"_type": "popCheckboxSet",
"_checkboxSet": function () {
var array = functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a.enemys.getSpecials()
var b = [],
c = [];
for (var index = 0; index < array.length; index++) {
b.push(array[index][0])
var name = array[index][1];
if (name instanceof Function) name = name({});
c.push((index%2==0&&index>0?'<br>':'')+name+'')
c.push(name + "(" + array[index][0] + ")")
}
return {
"prefix":c,
"key":b
"prefix": c,
"key": b
}
},
"_data": "特殊属性"
@ -282,7 +284,7 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_type": "select",
"_select": {
"values": [
"null",
null,
"openDoor",
"pushBox",
"ski",
@ -309,8 +311,8 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_leaf": true,
"_type": "checkboxSet",
"_checkboxSet": {
"prefix":["上: ","下: ","<br>左: ","右: "],
"key":["up","down","left","right"]
"prefix": ["上: ", "下: ", "<br>左: ", "右: "],
"key": ["up", "down", "left", "right"]
},
"_docs": "不可出方向",
"_data": "该图块的不可出方向\n对背景层、事件层、前景层上的图块均有效"
@ -319,8 +321,8 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_leaf": true,
"_type": "checkboxSet",
"_checkboxSet": {
"prefix":["上: ","下: ","<br>左: ","右: "],
"key":["up","down","left","right"]
"prefix": ["上: ", "下: ", "<br>左: ", "右: "],
"key": ["up", "down", "left", "right"]
},
"_docs": "不可入方向",
"_data": "该图块的不可入方向\n对背景层、事件层、前景层上的图块均有效"
@ -335,7 +337,7 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_leaf": true,
"_type": "select",
"_select": {
"values": [null,1,2,3,4],
"values": [null, 1, 2, 3, 4],
},
"_docs": "动画帧数",
"_data": "null代表素材默认帧数"
@ -343,7 +345,7 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"doorInfo": {
"_leaf": true,
"_type": "event",
"_event": "doorInfo",
"_event": "doorInfo",
"_docs": "门信息",
"_data": "该图块的门信息仅对animates和npc48生效。"
},
@ -407,7 +409,7 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"canUseQuickShop": {
"_leaf": true,
"_type": "checkbox",
"_docs": "快捷商店",
"_docs": "快捷商店",
"_data": "该层是否允许使用快捷商店"
},
"cannotViewMap": {
@ -422,6 +424,12 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_docs": "不可瞬移",
"_data": "该层是否不允许瞬间移动;如果勾上则不可在此层进行瞬移"
},
"underGround": {
"_leaf": true,
"_type": "checkbox",
"_docs": "地下层",
"_data": "是否是地下层如果该项为true则同层传送将传送至上楼梯"
},
"firstArrive": {
"_leaf": true,
"_type": "event",
@ -446,18 +454,25 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
},
"upFloor": {
"_leaf": true,
"_type": "textarea",
"_type": "point",
"_range": "thiseval==null||((thiseval instanceof Array) && thiseval.length==2)",
"_docs": "上楼点",
"_data": "该层上楼点,如[2,3]。\n如果此项不为null则楼层转换时的stair:upFloor以及楼传器的落点会被替换成该点而不是该层的上楼梯。"
},
"downFloor": {
"_leaf": true,
"_type": "textarea",
"_type": "point",
"_range": "thiseval==null||((thiseval instanceof Array) && thiseval.length==2)",
"_docs": "下楼点",
"_data": "该层下楼点,如[2,3]。\n如果此项不为null则楼层转换时的stair:downFloor以及楼传器的落点会被替换成该点而不是该层的下楼梯。"
},
"flyPoint": {
"_leaf": true,
"_type": "point",
"_range": "thiseval==null||((thiseval instanceof Array) && thiseval.length==2)",
"_docs": "楼传落点",
"_data": "该层楼传落点,如[2,3]。\n如果此项不为null则楼层飞行器强行落到此点无视上下楼或平面塔属性。"
},
"defaultGround": {
"_leaf": true,
"_type": "textarea",
@ -494,15 +509,9 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"ratio": {
"_leaf": true,
"_type": "textarea",
"_range": "(thiseval==~~thiseval && thiseval>=0)||thiseval==null",
"_range": "thiseval==~~thiseval && thiseval>=0",
"_docs": "宝石血瓶效果",
"_data": "每一层的宝石/血瓶效果,即获得宝石和血瓶时框内\"ratio\"的值。"
},
"underGround": {
"_leaf": true,
"_type": "checkbox",
"_docs": "是否是地下层",
"_data": "是否是地下层如果该项为true则同层传送将传送至上楼梯"
}
}
},
@ -566,8 +575,8 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_leaf": true,
"_type": "checkboxSet",
"_checkboxSet": {
"prefix":["上: ","下: ","<br>左: ","右: "],
"key":["up","down","left","right"]
"prefix": ["上: ", "下: ", "<br>左: ", "右: "],
"key": ["up", "down", "left", "right"]
},
"_docs": "不可通行性",
"_data": "该点不可通行的方向 \n 可以在这里定义该点不能前往哪个方向,可以达到悬崖之类的效果\n例如 [\"up\", \"left\"] 代表该点不能往上和左走"

View File

@ -2,6 +2,7 @@
* 表格配置项
* 在这里可以对表格中的各项显示进行配置包括表格项提示内容等内容具体写法照葫芦画瓢即可
* 本配置项包括全塔属性的配置项
* 相关文档 _docs/editor.md ~ http://127.0.0.1:1055/_docs/#/editor?id=修改表格
*/
var data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
@ -430,19 +431,19 @@ var data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_leaf": true,
"_type": "textarea",
"_docs": "破甲比例",
"_data": "破甲的比例战斗前怪物附加角色防御的x倍作为伤害"
"_data": "破甲的比例战斗前怪物附加角色防御的x倍作为伤害;可以用怪物的 defValue 覆盖此值。"
},
"counterAttack": {
"_leaf": true,
"_type": "textarea",
"_docs": "反击比例",
"_data": "反击的比例战斗时怪物每回合附加角色攻击的x倍作为伤害无视角色防御"
"_data": "反击的比例战斗时怪物每回合附加角色攻击的x倍作为伤害无视角色防御;可以用怪物的 atkValue 覆盖此值。"
},
"purify": {
"_leaf": true,
"_type": "textarea",
"_docs": "净化比例",
"_data": "净化的比例战斗前怪物附加勇士护盾的x倍作为伤害"
"_data": "净化的比例战斗前怪物附加勇士护盾的x倍作为伤害;可以用怪物的 n 覆盖此值。"
},
"hatred": {
"_leaf": true,

View File

@ -2,6 +2,7 @@
* 表格配置项
* 在这里可以对表格中的各项显示进行配置包括表格项提示内容等内容具体写法照葫芦画瓢即可
* 本配置项包括公共事件
* 相关文档 _docs/editor.md ~ http://127.0.0.1:1055/_docs/#/editor?id=修改表格
*/
var events_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {

View File

@ -2,6 +2,7 @@
* 表格配置项
* 在这里可以对表格中的各项显示进行配置包括表格项提示内容等内容具体写法照葫芦画瓢即可
* 本配置项包括脚本编辑
* 相关文档 _docs/editor.md ~ http://127.0.0.1:1055/_docs/#/editor?id=修改表格
*/
var functions_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {

View File

@ -2,6 +2,7 @@
* 表格配置项
* 在这里可以对表格中的各项显示进行配置包括表格项提示内容等内容具体写法照葫芦画瓢即可
* 本配置项包括插件编写
* 相关文档 _docs/editor.md ~ http://127.0.0.1:1055/_docs/#/editor?id=修改表格
*/
var plugins_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
@ -32,6 +33,12 @@ var plugins_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = {
"_range": "typeof(thiseval)=='string' || thiseval==null",
"_data": "砍层插件"
},
"fiveLayers": {
"_leaf": true,
"_type": "textarea",
"_range": "typeof(thiseval)=='string' || thiseval==null",
"_data": "五图层(背景前景2)"
},
"itemShop": {
"_leaf": true,
"_type": "textarea",

View File

@ -7,6 +7,7 @@
<link href="_server/CodeMirror/codemirror.css" rel="stylesheet">
<link href="_server/thirdparty/awesomplete.css" rel="stylesheet">
<link href="_server/css/editor_mode_mobile.css" rel="stylesheet">
<link rel="icon" href="data:;base64,iVBORw0KGgo=">
</head>
<body>
<script>
@ -37,8 +38,8 @@
<input type="button" value="新建空白地图" id='newMap'/>
</div>
<div id='editBtns'>
<input type="button" value="导出地图" id="exportMap"/>
<input type="button" value="复制地图" id="copyMap"/>
<input type="button" value="导出并复制地图" id="exportMap"/>
<input type="button" value="导入地图" id="importMap"/>
<input type="button" value="清除地图" id='clearMapButton'/>
<input type="button" value="删除地图" id="deleteMap"/>
</div>
@ -139,6 +140,8 @@
<div style="margin-top: -10px; margin-bottom: 10px">
<button id="copyEnemyItem">复制属性</button>
<button id="pasteEnemyItem">粘贴属性</button>
<button id="clearEnemyItem">清空属性</button>
<button id="clearAllEnemyItem">批量清空属性</button>
</div>
</div>
<div id='newIdIdnum'><!-- id and idnum -->
@ -210,7 +213,7 @@
<!-- 手机端放不下,因此不显示搜索框 -->
<div style="display: none">
<div class="searchLogo"></div>
<input type="text" id="searchBlock" placeholder="搜索图块"/>
<input type="text" id="searchBlock" placeholder="搜索事件块..."/>
</div>
<button class="cpPanel" onclick="editor_blockly.selectPoint()">地图选点</button>
<button class="cpPanel" onclick="editor.uievent.searchUsedFlags()" style="margin-left:5px">变量出现位置搜索</button>
@ -298,19 +301,15 @@
<div class="col" id='mapColMark'></div>
<div class="row" id='mapRowMark'></div>
<div class="map" id="mapEdit">
<canvas class='gameCanvas' id='bg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='event' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='event2' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='fg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='efg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='eui' width='416' height='416' style='z-index:100'></canvas>
<canvas class='gameCanvas' id='efg'></canvas>
<canvas class='gameCanvas' id='eui' style='z-index:100'></canvas>
</div>
</div>
<div id="mid2" style="display: none">
<p style="margin: 10px"><span id='lastUsedTitle'></span> <button id='clearLastUsedBtn'>清除</button></p>
<div class="map" style="height: 160px; margin-top: 25px" id="lastUsedDiv">
<canvas class='gameCanvas' id='lastUsed' width='416' height='160'></canvas>
<canvas class='gameCanvas' id='lastUsed'></canvas>
</div>
</div>
<div id="right" style="z-index:-1;opacity: 0;">
@ -325,19 +324,7 @@
<div id="down">
<div style="margin:0.5rem">
<div class="tools">
<div id="tip">
<div id="isSelectedBlock-if" style="display:none">
<p id="isClearBlock-if" style="display:none" class="infoText">当前选择为清除块,可擦除地图上块</p>
<div id="isClearBlock-else"><p id="isAirwall-if" style="display:none" class="infoText">当前选择为空气墙, 在编辑器中可视, 在游戏中隐藏的墙, 用来配合前景/背景的贴图</p>
<div id="isAirwall-else">
</div></div>
</div>
<div id="isSelectedBlock-else">
<p id="whichShow-if" style="display:none"></p>
</div>
</div>
<div id="tip"></div>
<span id='mobileview'>
<input type="button" value="数据区"/>
<input type="button" value="地图区"/>
@ -384,6 +371,7 @@
<input type="button" style="padding:1px 6px" value="↑"/>
<input type="button" style="padding:1px 6px" value="↓"/>
<input type="button" style="padding:1px 1px" value="→"/>
<input type="button" value="大地图" style="margin-left: 5px"/>
</div>
<select id="selectFloor" style="clear:left"></select>
<input type="button" value="保存地图" id='saveFloor'/>
@ -398,148 +386,9 @@
</div>
<!-- <script>/* -->
<div id='gameGroup' style='display:none'>
<p id='mainTips'>请稍后...</p>
<img id='musicBtn'>
<div id='startPanel'>
<div id='startTop'>
<div id='startTopProgressBar'>
<div id='startTopProgress'></div>
</div>
<p id='startTopLoadTips'>资源即将开始加载</p>
</div>
<img id='startBackground'>
<p id='startLogo'></p>
<div id='startButtonGroup'>
<div id='startButtons'>
<span class='startButton' id='playGame'>开始游戏</span>
<span class='startButton' id='loadGame'>载入游戏</span>
<span class='startButton' id='replayGame'>录像回放</span>
</div>
<div id='levelChooseButtons'></div>
</div>
</div>
<div id='floorMsgGroup'>
<p id='logoLabel'></p>
<p id='versionLabel'></p>
<p id='floorNameLabel'></p>
</div>
<div id='statusBar' class="clearfix">
<div class="status" id="floorCol">
<img id="img-floor">
<p class='statusLabel statusText' id='floor'></p>
</div>
<div class="status" id="nameCol">
<img id="img-name">
<p class='statusLabel statusText' id='name'></p>
</div>
<div class="status" id="lvCol">
<img id="img-lv">
<p class='statusLabel statusText' id='lv'></p>
</div>
<div class="status" id='hpmaxCol'>
<img id="img-hpmax">
<p class='statusLabel statusText' id='hpmax'></p>
</div>
<div class="status" id='hpCol'>
<img id="img-hp">
<p class='statusLabel statusText' id='hp'></p>
</div>
<div class="status" id='manaCol'>
<img id="img-mana">
<p class='statusLabel statusText' id='mana'></p>
</div>
<div class="status" id='atkCol'>
<img id="img-atk">
<p class='statusLabel statusText' id='atk'></p>
</div>
<div class="status" id='defCol'>
<img id="img-def">
<p class='statusLabel statusText' id='def'></p>
</div>
<div class="status" id="mdefCol">
<img id="img-mdef">
<p class='statusLabel statusText' id='mdef'></p>
</div>
<div class="status" id="moneyCol">
<img id="img-money">
<p class='statusLabel statusText' id='money'></p>
</div>
<div class="status" id="expCol">
<img id="img-exp">
<p class='statusLabel statusText' id='exp'></p>
</div>
<div class="status" id="upCol">
<img id="img-up">
<p class='statusLabel statusText' id='up'></p>
</div>
<div class="status" id="skillCol">
<img id="img-skill">
<p class='statusLabel statusText' id='skill' style='font-style: normal'></p>
</div>
<div class="status" id='keyCol'>
<span class='statusLabel' id='yellowKey' style="color:#FFCCAA"></span>
<span class='statusLabel' id='blueKey' style="color:#AAAADD"></span>
<span class='statusLabel' id='redKey' style="color:#FF8888"></span>
<span class='statusLabel' id='greenKey' style="color:#88FF88"></span>
</div>
<div class="status" id='pzfCol'>
<span class='statusLabel' id='pickaxe' style="color: #BC6E27"></span>
<span class='statusLabel' id='bomb' style="color: #FA14B9"></span>
<span class='statusLabel' id='fly' style="color: #8DB600"></span>
</div>
<div class="status" id="debuffCol">
<span class='statusLabel' id='poison' style="color: #AFFCA8;"></span>
<span class='statusLabel' id='weak' style="color: #FECCD0;"></span>
<span class='statusLabel' id='curse' style="color: #C2F4E7;"></span>
</div>
<!-- 状态栏canvas化 -->
<canvas id="statusCanvas"></canvas>
</div>
<div id="toolBar" class="clearfix">
<img class="tools" id='img-book'>
<img class="tools" id='img-fly'>
<img class="tools" id='img-toolbox'>
<img class="tools" id='img-keyboard'>
<img class="tools" id='img-shop'>
<img class="tools" id='img-save'>
<img class="tools" id='img-load'>
<img class="tools" id='img-settings'>
<img class="tools" id='img-btn1' style='display:none'>
<img class="tools" id='img-btn2' style='display:none'>
<img class="tools" id='img-btn3' style='display:none'>
<img class="tools" id='img-btn4' style='display:none'>
<img class="tools" id='img-btn5' style='display:none'>
<img class="tools" id='img-btn6' style='display:none'>
<img class="tools" id='img-btn7' style='display:none'>
<img class="tools" id='img-btn8' style='display:none'>
<p class="statusLabel tools" id="hard"></p>
</div>
<div id="gameDraw">
<div id="gif"></div>
<div id="gif2"></div>
<!-- <canvas class='gameCanvas' id='bg' width='416' height='416'></canvas> -->
<!-- <canvas class='gameCanvas' id='event' width='416' height='416'></canvas> -->
<canvas class='gameCanvas' id='hero' width='416' height='416'></canvas>
<!-- <canvas class='gameCanvas' id='event2' width='416' height='416'></canvas> -->
<!-- <canvas class='gameCanvas' id='fg' width='416' height='416'></canvas> -->
<canvas class='gameCanvas' id='damage' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='animate' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='curtain' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='ui' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='data' width='416' height='416'>此浏览器不支持HTML5</canvas>
<div id="next"></div>
</div>
</div>
<div id='inputDiv' style='display: none'>
<div id='inputDialog'>
<p id="inputMessage">请输入文字...</p>
<input id='inputBox' type="text"/>
<button id='inputYes'>确定</button>
<button id='inputNo'>取消</button>
</div>
</div>
<div id="gameInject" style='display: none'></div>
<!-- UI预览 & 地图选点 -->
<div id='uieventDiv' style='display: none'>
<div id='uieventDialog'>
@ -556,10 +405,9 @@
</div>
<hr style="clear: both; margin-top: 0"/>
<div id='uieventBody'>
<canvas class='gameCanvas' id='uievent' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='uievent'></canvas>
<div id="selectPointBox"></div>
<div id="uieventUsedFlagList" style="display: none"></div>
<div id="uieventMaterialList" style="display: none"></div>
<div id="uieventExtraBody" style="display: none"></div>
</div>
<div id="selectPoint">
<select id="selectPointFloor"></select>
@ -568,6 +416,8 @@
<input type="button" value="↑"/>
<input type="button" value="↓"/>
<input type="button" value="→"/>
<input type="button" value="大地图" style="margin-left: 5px"/>
<input type="button" value="复制楼层ID">
</div>
</div>
</div>
@ -594,7 +444,6 @@
<script src='libs/thirdparty/lz-string.min.js'></script>
<script src='libs/thirdparty/localforage.min.js'></script>
<script src='libs/thirdparty/zip.min.js'></script>
<script id='mainScript' src='main.js'></script>
<script src='_server/editor.js'></script>
<script>
editor.isMobile=true;

View File

@ -6,6 +6,7 @@
<link href="_server/CodeMirror/codemirror.css" rel="stylesheet">
<link href="_server/thirdparty/awesomplete.css" rel="stylesheet">
<link href="_server/css/editor_mode.css" rel="stylesheet">
<link rel="icon" href="data:;base64,iVBORw0KGgo=">
</head>
<body>
<script>
@ -35,8 +36,8 @@
<span style='vertical-align: bottom; margin-left: -4px'>保留楼层属性</span>
</div>
<div id="editBtns">
<input type="button" value="导出地图" id="exportMap"/>
<input type="button" value="复制地图" id="copyMap"/>
<input type="button" value="导出并复制地图" id="exportMap"/>
<input type="button" value="从框中导入地图" id="importMap"/>
<input type="button" value="清除地图" id='clearMapButton'/>
<input type="button" value="删除地图" id="deleteMap"/>
</div>
@ -135,6 +136,8 @@
<div style="margin-top: -10px; margin-bottom: 10px">
<button id="copyEnemyItem">复制属性</button>
<button id="pasteEnemyItem">粘贴属性</button>
<button id="clearEnemyItem">清空属性</button>
<button id="clearAllEnemyItem">批量清空属性</button>
</div>
</div>
<div id='newIdIdnum'><!-- id and idnum -->
@ -205,7 +208,7 @@
<button onclick="editor_blockly.cancel()">取消</button>
<div style="position: relative; display: inline-block; margin-left: 10px">
<div class="searchLogo"></div>
<input type="text" id="searchBlock" placeholder="搜索图块"/>
<input type="text" id="searchBlock" placeholder="搜索事件块..."/>
</div>
<button class="cpPanel" onclick="editor_blockly.selectPoint()" style="margin-left:5px">地图选点</button>
<button class="cpPanel" onclick="editor.uievent.searchUsedFlags()" style="margin-left:5px">变量出现位置搜索</button>
@ -293,28 +296,11 @@
<table class="col" id='mapColMark'></table>
<table class="row" id='mapRowMark'></table>
<div class="map" id="mapEdit">
<canvas class='gameCanvas' id='bg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='event' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='event2' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='fg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='efg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='eui' width='416' height='416' style='z-index:100'></canvas>
<canvas class='gameCanvas' id='efg'></canvas>
<canvas class='gameCanvas' id='eui' style='z-index:100'></canvas>
</div>
<div class="tools">
<div id="tip">
<div id="isSelectedBlock-if" style="display:none">
<p id="isClearBlock-if" style="display:none" class="infoText">当前选择为清除块,可擦除地图上块</p>
<div id="isClearBlock-else"><p id="isAirwall-if" style="display:none" class="infoText">当前选择为空气墙, 在编辑器中可视, 在游戏中隐藏的墙, 用来配合前景/背景的贴图</p>
<div id="isAirwall-else">
</div></div>
</div>
<div id="isSelectedBlock-else">
<p id="whichShow-if" style="display:none"></p>
</div>
</div>
<div id="tip"></div>
<select id="editModeSelect">
<option value="map">地图编辑</option>
<option value="loc">地图选点</option>
@ -347,6 +333,7 @@
<input type="button" value="↑"/>
<input type="button" value="↓"/>
<input type="button" value="→"/>
<input type="button" value="大地图" style="margin-left: 5px"/>
</div>
<br>
<select id="selectFloor"></select>
@ -356,7 +343,7 @@
<div id="mid2">
<p style="margin: 10px"><span id='lastUsedTitle'></span><small>Ctrl+滚轮放缩,右键置顶)</small> <button id='clearLastUsedBtn'>清除</button></p>
<div class="map" id="lastUsedDiv">
<canvas id='lastUsed' width='416' height='416' style="overflow: hidden"></canvas>
<canvas id='lastUsed' class="gameCanvas" style="overflow: hidden"></canvas>
</div>
</div>
<div id="right">
@ -381,148 +368,9 @@
</div>
</div>
<!-- <script>/* -->
<div id='gameGroup' style='display:none'>
<p id='mainTips'>请稍后...</p>
<img id='musicBtn'>
<div id='startPanel'>
<div id='startTop'>
<div id='startTopProgressBar'>
<div id='startTopProgress'></div>
</div>
<p id='startTopLoadTips'>资源即将开始加载</p>
</div>
<img id='startBackground'>
<p id='startLogo'></p>
<div id='startButtonGroup'>
<div id='startButtons'>
<span class='startButton' id='playGame'>开始游戏</span>
<span class='startButton' id='loadGame'>载入游戏</span>
<span class='startButton' id='replayGame'>录像回放</span>
</div>
<div id='levelChooseButtons'></div>
</div>
</div>
<div id='floorMsgGroup'>
<p id='logoLabel'></p>
<p id='versionLabel'></p>
<p id='floorNameLabel'></p>
</div>
<div id='statusBar' class="clearfix">
<div class="status" id="floorCol">
<img id="img-floor">
<p class='statusLabel statusText' id='floor'></p>
</div>
<div class="status" id="nameCol">
<img id="img-name">
<p class='statusLabel statusText' id='name'></p>
</div>
<div class="status" id="lvCol">
<img id="img-lv">
<p class='statusLabel statusText' id='lv'></p>
</div>
<div class="status" id='hpmaxCol'>
<img id="img-hpmax">
<p class='statusLabel statusText' id='hpmax'></p>
</div>
<div class="status" id='hpCol'>
<img id="img-hp">
<p class='statusLabel statusText' id='hp'></p>
</div>
<div class="status" id='manaCol'>
<img id="img-mana">
<p class='statusLabel statusText' id='mana'></p>
</div>
<div class="status" id='atkCol'>
<img id="img-atk">
<p class='statusLabel statusText' id='atk'></p>
</div>
<div class="status" id='defCol'>
<img id="img-def">
<p class='statusLabel statusText' id='def'></p>
</div>
<div class="status" id="mdefCol">
<img id="img-mdef">
<p class='statusLabel statusText' id='mdef'></p>
</div>
<div class="status" id="moneyCol">
<img id="img-money">
<p class='statusLabel statusText' id='money'></p>
</div>
<div class="status" id="expCol">
<img id="img-exp">
<p class='statusLabel statusText' id='exp'></p>
</div>
<div class="status" id="upCol">
<img id="img-up">
<p class='statusLabel statusText' id='up'></p>
</div>
<div class="status" id="skillCol">
<img id="img-skill">
<p class='statusLabel statusText' id='skill' style='font-style: normal'></p>
</div>
<div class="status" id='keyCol'>
<span class='statusLabel' id='yellowKey' style="color:#FFCCAA"></span>
<span class='statusLabel' id='blueKey' style="color:#AAAADD"></span>
<span class='statusLabel' id='redKey' style="color:#FF8888"></span>
<span class='statusLabel' id='greenKey' style="color:#88FF88"></span>
</div>
<div class="status" id='pzfCol'>
<span class='statusLabel' id='pickaxe' style="color: #BC6E27"></span>
<span class='statusLabel' id='bomb' style="color: #FA14B9"></span>
<span class='statusLabel' id='fly' style="color: #8DB600"></span>
</div>
<div class="status" id="debuffCol">
<span class='statusLabel' id='poison' style="color: #AFFCA8;"></span>
<span class='statusLabel' id='weak' style="color: #FECCD0;"></span>
<span class='statusLabel' id='curse' style="color: #C2F4E7;"></span>
</div>
<!-- 状态栏canvas化 -->
<canvas id="statusCanvas"></canvas>
</div>
<div id="toolBar" class="clearfix">
<img class="tools" id='img-book'>
<img class="tools" id='img-fly'>
<img class="tools" id='img-toolbox'>
<img class="tools" id='img-keyboard'>
<img class="tools" id='img-shop'>
<img class="tools" id='img-save'>
<img class="tools" id='img-load'>
<img class="tools" id='img-settings'>
<img class="tools" id='img-btn1' style='display:none'>
<img class="tools" id='img-btn2' style='display:none'>
<img class="tools" id='img-btn3' style='display:none'>
<img class="tools" id='img-btn4' style='display:none'>
<img class="tools" id='img-btn5' style='display:none'>
<img class="tools" id='img-btn6' style='display:none'>
<img class="tools" id='img-btn7' style='display:none'>
<img class="tools" id='img-btn8' style='display:none'>
<p class="statusLabel tools" id="hard"></p>
</div>
<div id="gameDraw">
<div id="gif"></div>
<div id="gif2"></div>
<!-- <canvas class='gameCanvas' id='bg' width='416' height='416'></canvas> -->
<!-- <canvas class='gameCanvas' id='event' width='416' height='416'></canvas> -->
<canvas class='gameCanvas' id='hero' width='416' height='416'></canvas>
<!-- <canvas class='gameCanvas' id='event2' width='416' height='416'></canvas> -->
<!-- <canvas class='gameCanvas' id='fg' width='416' height='416'></canvas> -->
<canvas class='gameCanvas' id='damage' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='animate' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='curtain' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='ui' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='data' width='416' height='416'>此浏览器不支持HTML5</canvas>
<div id="next"></div>
</div>
</div>
<div id='inputDiv' style='display: none'>
<div id='inputDialog'>
<p id="inputMessage">请输入文字...</p>
<input id='inputBox' type="text"/>
<button id='inputYes'>确定</button>
<button id='inputNo'>取消</button>
</div>
</div>
<div id="gameInject" style='display: none'></div>
<!-- UI预览 & 地图选点 -->
<div id='uieventDiv' style='display: none'>
<div id='uieventDialog'>
@ -539,10 +387,9 @@
</div>
<hr style="clear: both; margin-top: 0"/>
<div id='uieventBody'>
<canvas class='gameCanvas' id='uievent' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='uievent'></canvas>
<div id="selectPointBox"></div>
<div id="uieventUsedFlagList" style="display: none; margin-top: -10px"></div>
<div id="uieventMaterialList" style="display: none; margin-top: -10px"></div>
<div id="uieventExtraBody" style="display: none; margin-top: -10px"></div>
</div>
<div id="selectPoint">
<select id="selectPointFloor"></select>
@ -551,6 +398,8 @@
<input type="button" value="↑"/>
<input type="button" value="↓"/>
<input type="button" value="→"/>
<input type="button" value="切换大地图" style="margin-left: 10px;">
<input type="button" value="复制楼层ID">
</div>
</div>
</div>
@ -579,7 +428,6 @@
<script src='libs/thirdparty/lz-string.min.js'></script>
<script src='libs/thirdparty/localforage.min.js'></script>
<script src='libs/thirdparty/zip.min.js'></script>
<script id='mainScript' src='main.js'></script>
<script src='_server/editor.js'></script>
<script>
editor.init(function () {

View File

@ -43,6 +43,7 @@
startImageLogo.src = "logo.png";
})();
</script>
<!-- injection -->
<div id='gameGroup'>
<p id='mainTips'>请稍后...</p>
<img id='musicBtn'>
@ -165,16 +166,16 @@
<div id="gameDraw">
<div id="gif"></div>
<div id="gif2"></div>
<canvas class='gameCanvas' id='bg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='event' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='hero' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='event2' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='fg' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='damage' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='animate' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='curtain' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='ui' width='416' height='416'></canvas>
<canvas class='gameCanvas' id='data' width='416' height='416'>此浏览器不支持HTML5</canvas>
<canvas class='gameCanvas' id='bg'></canvas>
<canvas class='gameCanvas' id='event'></canvas>
<canvas class='gameCanvas' id='hero'></canvas>
<canvas class='gameCanvas' id='event2'></canvas>
<canvas class='gameCanvas' id='fg'></canvas>
<canvas class='gameCanvas' id='damage'></canvas>
<canvas class='gameCanvas' id='animate'></canvas>
<canvas class='gameCanvas' id='curtain'></canvas>
<canvas class='gameCanvas' id='ui'></canvas>
<canvas class='gameCanvas' id='data'>此浏览器不支持HTML5</canvas>
<div id="next"></div>
</div>
</div>
@ -186,6 +187,7 @@
<button id='inputNo'>取消</button>
</div>
</div>
<!-- injection -->
<script src='libs/thirdparty/lz-string.min.js'></script>
<script src='libs/thirdparty/priority-queue.min.js'></script>
<script src='libs/thirdparty/localforage.min.js'></script>

View File

@ -176,9 +176,9 @@ control.prototype._animationFrame_animate = function (timestamp) {
});
core.status.animateObjs.forEach(function (obj) {
if (obj.hero) {
core.maps._drawAnimateFrame(obj.animate, core.status.heroCenter.px, core.status.heroCenter.py, obj.index++);
core.maps._drawAnimateFrame('animate', obj.animate, core.status.heroCenter.px, core.status.heroCenter.py, obj.index++);
} else {
core.maps._drawAnimateFrame(obj.animate, obj.centerX, obj.centerY, obj.index++);
core.maps._drawAnimateFrame('animate', obj.animate, obj.centerX, obj.centerY, obj.index++);
}
});
core.animateFrame.animateTime = timestamp;
@ -695,11 +695,7 @@ control.prototype._moveHero_moving = function () {
// 检测是否穿出去
var nx = core.nextX(), ny = core.nextY();
if (nx < 0 || nx >= core.bigmap.width || ny < 0 || ny >= core.bigmap.height) return;
core.status.heroMoving=-1;
core.eventMoveHero([core.getHeroLoc('direction')], core.values.moveSpeed, function () {
core.status.heroMoving=0;
move();
});
core.eventMoveHero([core.getHeroLoc('direction')], core.values.moveSpeed, move);
}
else {
core.moveAction();
@ -2061,6 +2057,22 @@ control.prototype.getRealStatusOrDefault = function (status, name) {
return Math.floor(this.getStatusOrDefault(status, name) * this.getBuff(name));
}
////// 获得勇士原始属性(无装备和衰弱影响) //////
control.prototype.getNakedStatus = function (name) {
var value = this.getStatus(name);
if (value == null) return value;
// 装备增幅
core.status.hero.equipment.forEach(function (v) {
if (!v || !(core.material.items[v] || {}).equip) return;
value -= core.material.items[v].equip.value[name] || 0;
});
// 衰弱扣除
if (core.hasFlag('weak') && core.values.weakValue >= 1 && (name == 'atk' || name == 'def')) {
value += core.values.weakValue;
}
return value;
}
////// 设置某个属性的增幅值 //////
control.prototype.setBuff = function (name, value) {
// 仅保留三位有效buff值
@ -2721,6 +2733,9 @@ control.prototype._resize_gameGroup = function (obj) {
floorMsgGroup.style = obj.globalAttribute.floorChangingStyle;
floorMsgGroup.style.width = obj.outerSize - 2 * obj.BORDER + "px";
floorMsgGroup.style.height = totalHeight - 2 * obj.BORDER + "px";
floorMsgGroup.style.fontSize = 16 * core.domStyle.scale + "px";
// startPanel
core.dom.startPanel.style.fontSize = 16 * core.domStyle.scale + "px";
// musicBtn
if (core.domStyle.isVertical || core.domStyle.scale < 1) {
core.dom.musicBtn.style.right = core.dom.musicBtn.style.bottom = "3px";
@ -2781,7 +2796,7 @@ control.prototype._resize_statusBar = function (obj) {
statusBar.style.borderBottom = core.domStyle.isVertical ? '' : obj.border;
// 自绘状态栏
if (core.domStyle.isVertical) {
core.dom.statusCanvas.style.width = obj.CANVAS_WIDTH + "px";
core.dom.statusCanvas.style.width = obj.CANVAS_WIDTH * core.domStyle.scale + "px";
core.dom.statusCanvas.width = obj.CANVAS_WIDTH;
core.dom.statusCanvas.style.height = obj.statusBarHeightInVertical - 3 + "px";
core.dom.statusCanvas.height = obj.col * 32 + 9;

View File

@ -226,11 +226,18 @@ core.prototype.init = function (coreData, callback) {
this._init_others();
this._initPlugins();
// 初始化画布
for (var name in core.canvas) {
core.canvas[name].canvas.width = core.canvas[name].canvas.height = core.__PIXELS__;
}
core.loader._load(function () {
core.extensions._load(function () {
core._afterLoadResources(callback);
});
});
});
core.dom.musicBtn.style.display = 'block';
core.setMusicBtn();
}
core.prototype._init_flags = function () {

View File

@ -77,6 +77,41 @@ enemys.prototype.getSpecialText = function (enemy) {
return text;
}
////// 获得所有特殊属性的颜色 //////
enemys.prototype.getSpecialColor = function (enemy) {
if (typeof enemy == 'string') enemy = core.material.enemys[enemy];
if (!enemy) return [];
var special = enemy.special;
var colors = [];
var specials = this.getSpecials();
if (specials) {
for (var i = 0; i < specials.length; i++) {
if (this.hasSpecial(special, specials[i][0]))
colors.push(specials[i][3] || null);
}
}
return colors;
}
////// 获得所有特殊属性的额外标记 //////
enemys.prototype.getSpecialFlag = function (enemy) {
if (typeof enemy == 'string') enemy = core.material.enemys[enemy];
if (!enemy) return [];
var special = enemy.special;
var flag = 0;
var specials = this.getSpecials();
if (specials) {
for (var i = 0; i < specials.length; i++) {
if (this.hasSpecial(special, specials[i][0]))
flag |= (specials[i][4] || 0);
}
}
return flag;
}
////// 获得每个特殊属性的说明 //////
enemys.prototype.getSpecialHint = function (enemy, special) {
var specials = this.getSpecials();
@ -86,7 +121,8 @@ enemys.prototype.getSpecialHint = function (enemy, special) {
var hints = [];
for (var i = 0; i < specials.length; i++) {
if (this.hasSpecial(enemy, specials[i][0]))
hints.push("\r[#FF6A6A]\\d"+this._calSpecialContent(enemy, specials[i][1]) + "\\d\r[]" + this._calSpecialContent(enemy, specials[i][2]));
hints.push("\r[" + core.arrayToRGBA(specials[i][3] || "#FF6A6A") + "]\\d" + this._calSpecialContent(enemy, specials[i][1]) +
"\\d\r[]" + this._calSpecialContent(enemy, specials[i][2]));
}
return hints;
}
@ -323,8 +359,7 @@ enemys.prototype._getCurrentEnemys_addEnemy = function (enemyId, enemys, used, f
var enemyInfo = this.getEnemyInfo(enemy, null, null, null, floorId);
var specialText = core.enemys.getSpecialText(enemy);
if (specialText.length >= 3) specialText = "多属性...";
else specialText = specialText.join(" ");
var specialColor = core.enemys.getSpecialColor(enemy);
var critical = this.nextCriticals(enemy, 1, null, null, floorId);
if (critical.length > 0) critical = critical[0];
@ -334,6 +369,7 @@ enemys.prototype._getCurrentEnemys_addEnemy = function (enemyId, enemys, used, f
e[x] = enemyInfo[x];
}
e.specialText = specialText;
e.specialColor = specialColor;
e.damage = this.getDamage(enemy, null, null, floorId);
e.critical = critical[0];
e.criticalDamage = critical[1];

View File

@ -81,7 +81,7 @@ events.prototype._startGame_setHard = function () {
core.insertAction(one.action);
}
});
core.setFlag('hard', 0);
core.setFlag('hard', hardValue || 0);
core.setFlag('__hardColor__', hardColor);
}
@ -325,9 +325,12 @@ events.prototype.trigger = function (x, y, callback) {
return;
}
if (core.status.gameOver) return _executeCallback();
if (core.status.event.id && core.status.event.id != 'action') return _executeCallback();
var inAction = core.status.event.id == 'action';
if (core.status.event.id == 'action') {
core.insertAction({"type": "function", "function": "function () { core.events._trigger_inAction("+x+","+y+"); }", "async": true},
null, null, null, true);
return _executeCallback();
}
if (core.status.event.id) return _executeCallback();
var block = core.getBlock(x, y);
if (block == null) return _executeCallback();
@ -343,26 +346,39 @@ events.prototype.trigger = function (x, y, callback) {
if (noPass) core.clearAutomaticRouteNode(x, y);
// 转换楼层能否穿透
if (!inAction && trigger == 'changeFloor' && !noPass && this._trigger_ignoreChangeFloor(block))
if (trigger == 'changeFloor' && !noPass && this._trigger_ignoreChangeFloor(block))
return;
core.status.automaticRoute.moveDirectly = false;
if (inAction) {
// 切换事件点的坐标
this.setEvents(null, block.x, block.y);
if (block.event.trigger == 'action') {
this.insertAction(block.event.data);
}
else {
this.doSystemEvent(block.event.trigger, block, _executeCallback);
return;
}
} else {
this.doSystemEvent(trigger, block);
}
this.doSystemEvent(trigger, block);
}
return _executeCallback();
}
events.prototype._trigger_inAction = function (x, y) {
if (core.status.gameOver || core.status.event.id != 'action') return;
var block = core.getBlock(x, y);
if (block == null) return core.doAction();
block = block.block;
// 执行该点的脚本
try {
eval(block.event.script);
} catch (e) { main.log(e); }
if (block.event.trigger && block.event.trigger != 'null') {
this.setEvents(null, x, y);
if (block.event.trigger == 'action') {
this.insertAction(block.event.data);
}
else {
this.doSystemEvent(block.event.trigger, block, core.doAction);
return;
}
}
return core.doAction();
}
events.prototype._trigger_ignoreChangeFloor = function (block) {
var able = core.flags.ignoreChangeFloor;
if (block.event.data && block.event.data.ignoreChangeFloor != null)
@ -471,20 +487,22 @@ events.prototype._openDoor_check = function (id, x, y, needKey) {
var keyInfo = doorInfo.keys || {};
if (needKey) {
for (var keyName in keyInfo) {
var keyValue = keyInfo[keyName];
if (keyName.endsWith(':o')) keyName = keyName.substring(0, keyName.length - 2);
// --- 如果是一个不存在的道具,则直接认为无法开启
if (!core.material.items[keyName]) {
core.drawTip("无法开启此门");
return clearAndReturn();
}
var keyValue = keyInfo[keyName];
if (core.itemCount(keyName) < keyValue) {
core.drawTip("你没有" + ((core.material.items[keyName] || {}).name || "钥匙"), null, true);
core.drawTip("你" + ((core.material.items[keyName] || {}).name || "钥匙") + "不足!", null, true);
return false;
}
}
if (!core.status.event.id) core.autosave(true);
for (var keyName in keyInfo) {
core.removeItem(keyName, keyInfo[keyName]);
for (var keyName in keyInfo) {
if (!keyName.endsWith(':o')) core.removeItem(keyName, keyInfo[keyName]);
}
}
core.playSound(doorInfo.openSound);
@ -774,7 +792,7 @@ events.prototype.pushBox = function (data) {
// 检测能否推上去
if (!core.canMoveHero()) return;
var canGoDeadZone = core.flags.canGoDeadZone;
core.flags.canGoDeadZone = false;
core.flags.canGoDeadZone = true;
if (!core.canMoveHero(data.x, data.y, direction)) {
core.flags.canGoDeadZone = canGoDeadZone;
return;
@ -869,7 +887,10 @@ events.prototype.doEvent = function (data, x, y, prefix) {
events.prototype.setEvents = function (list, x, y, callback) {
var data = core.status.event.data || {};
if (list) {
data.list = [{todo: core.clone(list), total: core.clone(list), condition: "false"}];
var l = core.clone(list);
if (!(l instanceof Array)) l = [l];
l.push({"type": "_label"});
data.list = [{todo: l, total: core.clone(l), condition: "false"}];
// 结束所有正在执行的自动事件
if (list.length == 0) {
core.status.autoEvents.forEach(function (autoEvent) {
@ -973,21 +994,40 @@ events.prototype.insertAction = function (action, x, y, callback, addToLast) {
this.startEvents(action, x, y, callback);
}
else {
if (addToLast)
core.push(core.status.event.data.list[0].todo, action)
else
core.unshift(core.status.event.data.list[0].todo, action);
if (addToLast) {
var list = core.status.event.data.list[0].todo;
var index = 0;
for (var index = 0; index < list.length; index++) {
if (list[index].type == '_label') {
list.splice(index, 0, action);
break;
}
}
}
else core.unshift(core.status.event.data.list[0].todo, action);
this.setEvents(null, x, y, callback);
}
}
////// 往当前事件列表之前或之后添加一个公共事件 //////
events.prototype.insertCommonEvent = function (name, x, y, callback, addToLast) {
events.prototype.insertCommonEvent = function (name, args, x, y, callback, addToLast) {
var commonEvent = this.getCommonEvent(name);
if (!commonEvent) {
if (callback) callback();
return;
}
// 设置参数
core.setFlag('arg0', name);
if (args instanceof Array) {
for (var i = 0; i < args.length; ++i) {
try {
if (args[i] != null)
core.setFlag('arg'+(i+1), args[i]);
} catch (e) { main.log(e); }
}
}
this.insertAction({"type": "dowhile", "condition": "false", "data": commonEvent}, x, y, callback, addToLast);
}
@ -1154,13 +1194,15 @@ events.prototype.__precompile_getArray = function () {
"fillArc", "strokeArc", "drawIcon", "drawSelector", "drawBackground",
];
var others = {
"fillEllipse": ["a", "b"],
"strokeEllipse": ["a", "b"],
"fillEllipse": ["a", "b", "angle"],
"strokeEllipse": ["a", "b", "angle"],
"fillRect": ["radius", "angle"],
"strokeRect": ["radius", "angle"],
"fillArc": ["r", "start", "end"],
"strokeArc": ["r", "start", "end"],
"drawLine": ["x1", "y1", "x2", "y2"],
"drawArrow": ["x1", "y1", "x2", "y2"],
"drawImage": ["x", "y", "w", "h", "x1", "y1", "w1", "h1"],
"drawImage": ["x", "y", "w", "h", "x1", "y1", "w1", "h1", "angle"],
"drawTextContent": ["left", "top"],
};
return {
@ -1254,6 +1296,10 @@ events.prototype._action_comment = function (data, x, y, prefix) {
core.doAction();
}
events.prototype._action__label = function (data, x, y, prefix) {
core.doAction();
}
events.prototype._action_setText = function (data, x, y, prefix) {
["position", "offset", "align", "bold", "titlefont", "textfont", "lineHeight", "time", "interval"].forEach(function (t) {
if (data[t] != null) core.status.textAttribute[t] = data[t];
@ -1406,6 +1452,7 @@ events.prototype._action_moveAction = function (data, x, y, prefix) {
core.insertAction([
{"type": "moveHero", "steps": ["forward"]},
{"type": "function", "function": "function() { core.moveOneStep(core.doAction); }", "async": true},
{"type": "_label"},
]);
}
}
@ -1471,8 +1518,11 @@ events.prototype._action_showTextImage = function (data, x, y, prefix) {
var loc = this.__action_getLoc(data.loc, 0, 0, prefix);
if (core.isReplaying()) data.time = 0;
data.text = core.replaceText(data.text, prefix);
var __tmpName = (Math.random()+"_"+Math.random()).replace(/\./g, "") + ".png";
core.material.images.images[__tmpName] = core.ui.textImage(data.text);
this.__action_doAsyncFunc(data.async || data.time == 0, core.showImage,
data.code, core.ui.textImage(data.text), null, loc, data.opacity, data.time);
data.code, __tmpName + (data.reverse || ""), null, loc, data.opacity, data.time);
delete core.material.images.images[__tmpName];
}
events.prototype._action_hideImage = function (data, x, y, prefix) {
@ -1587,24 +1637,23 @@ events.prototype._action_battle = function (data, x, y, prefix) {
events.prototype._action_trigger = function (data, x, y, prefix) {
var loc = this.__action_getLoc(data.loc, x, y, prefix);
core.trigger(loc[0], loc[1], core.doAction);
this._trigger_inAction(loc[0], loc[1]);
}
events.prototype._action_insert = function (data, x, y, prefix) {
// 设置参数
if (data.args instanceof Array) {
for (var i = 0; i < data.args.length; ++i) {
try {
if (data.args[i] != null)
core.setFlag('arg'+(i+1), data.args[i]);
} catch (e) { main.log(e); }
}
}
if (data.name) { // 公共事件
core.setFlag('arg0', data.name);
core.insertCommonEvent(data.name);
core.insertCommonEvent(data.name, data.args);
}
else {
// 设置参数
if (data.args instanceof Array) {
for (var i = 0; i < data.args.length; ++i) {
try {
if (data.args[i] != null)
core.setFlag('arg'+(i+1), data.args[i]);
} catch (e) { main.log(e); }
}
}
var loc = this.__action_getLoc(data.loc, x, y, prefix);
core.setFlag('arg0', loc);
var floorId = data.floorId;
@ -1703,7 +1752,7 @@ events.prototype._action_setGlobalFlag = function (data, x, y, prefix) {
}
events.prototype._action_setHeroIcon = function (data, x, y, prefix) {
this.setHeroIcon(data.name);
this.setHeroIcon(data.name, data.noDraw);
core.doAction();
}
@ -1766,7 +1815,7 @@ events.prototype._action_switch = function (data, x, y, prefix) {
var list = [];
for (var i = 0; i < data.caseList.length; i++) {
var condition = data.caseList[i]["case"];
if (condition == "default" || core.calValue(condition, prefix) == key) {
if (condition == "default" || core.calValue(condition, prefix) === key) {
core.push(list, data.caseList[i].action);
if (!data.caseList[i].nobreak)
break;
@ -1795,8 +1844,10 @@ events.prototype._action_choices = function (data, x, y, prefix) {
var action = core.status.replay.toReplay.shift();
// --- 忽略可能的turn事件
if (action == 'turn') action = core.status.replay.toReplay.shift();
if (core.hasFlag('@temp@shop') && action.startsWith('shop:')) action = core.status.replay.toReplay.shift();
if (action.indexOf('choices:') == 0) {
var index = action.substring(8);
if (index == "-1") index = data.choices.length - 1;
if (index == 'none' || ((index = parseInt(index)) >= 0) && index < data.choices.length) {
core.status.event.selection = index;
setTimeout(function () {
@ -1876,10 +1927,18 @@ events.prototype._action_for = function (data, x, y, prefix) {
return core.doAction();
}
var from = core.calValue(data.from);
if (typeof from != 'number') {
core.insertAction('循环遍历事件要求【起始点】仅能是数字!');
var to = core.calValue(data.to);
var step = core.calValue(data.step);
if (typeof from != 'number' || typeof to !='number' || typeof step != 'number') {
core.insertAction('循环遍历事件要求【起始点】【终止点】【每步】仅能是数字!');
return core.doAction();
}
// 首次判定
if ((step > 0 && from > to) || (step < 0 && from < to)) {
core.doAction();
return;
}
var letter = data.name.substring(5);
core.setFlag('@temp@' + letter, from);
var toName = '@temp@for-to@' + letter;
@ -1932,8 +1991,11 @@ events.prototype._precompile_forEach = function (data) {
events.prototype._action_while = function (data, x, y, prefix) {
if (core.calValue(data.condition, prefix)) {
var list = core.clone(data.data);
if (!(list instanceof Array)) list = [list];
list.push({"type": "_label"});
core.unshift(core.status.event.data.list,
{"todo": core.clone(data.data), "total": core.clone(data.data), "condition": data.condition}
{"todo": list, "total": core.clone(list), "condition": data.condition}
);
}
core.doAction();
@ -1946,8 +2008,11 @@ events.prototype._precompile_while = function (data) {
}
events.prototype._action_dowhile = function (data, x, y, prefix) {
var list = core.clone(data.data);
if (!(list instanceof Array)) list = [list];
list.push({"type": "_label"});
core.unshift(core.status.event.data.list,
{"todo": core.clone(data.data), "total": core.clone(data.data), "condition": data.condition}
{"todo": list, "total": core.clone(list), "condition": data.condition}
);
core.doAction();
}
@ -1959,16 +2024,19 @@ events.prototype._precompile_dowhile = function (data) {
}
events.prototype._action_break = function (data, x, y, prefix) {
core.status.event.data.list.shift();
if (core.status.event.data.list.length > 1)
core.status.event.data.list.shift();
core.doAction();
}
events.prototype._action_continue = function (data, x, y, prefix) {
if (core.calValue(core.status.event.data.list[0].condition, prefix)) {
core.status.event.data.list[0].todo = core.clone(core.status.event.data.list[0].total);
}
else {
core.status.event.data.list.shift();
if (core.status.event.data.list.length > 1) {
if (core.calValue(core.status.event.data.list[0].condition, prefix)) {
core.status.event.data.list[0].todo = core.clone(core.status.event.data.list[0].total);
}
else {
core.status.event.data.list.shift();
}
}
core.doAction();
}
@ -2634,7 +2702,7 @@ events.prototype.closeDoor = function (x, y, id, callback) {
}
// 关门动画
core.playSound(doorInfo.closeDoor);
core.playSound(doorInfo.closeSound);
var blockInfo = core.getBlockInfo(id);
var image = blockInfo.image, posY = blockInfo.posY, height = blockInfo.height;
@ -2856,10 +2924,12 @@ events.prototype.eventMoveHero = function(steps, time, callback) {
var step = 0, moveSteps = (steps||[]).filter(function (t) {
return ['up','down','left','right','forward','backward'].indexOf(t)>=0;
});
core.status.heroMoving = -1;
var animate=window.setInterval(function() {
if (moveSteps.length==0) {
delete core.animateFrame.asyncId[animate];
clearInterval(animate);
core.status.heroMoving = 0;
core.drawHero();
if (callback) callback();
}
@ -2902,7 +2972,6 @@ events.prototype.jumpHero = function (ex, ey, time, callback) {
var sx=core.status.hero.loc.x, sy=core.status.hero.loc.y;
if (!core.isset(ex)) ex=sx;
if (!core.isset(ey)) ey=sy;
core.playSound('jump.mp3');
var jumpInfo = core.maps.__generateJumpInfo(sx, sy, ex, ey, time || 500);
jumpInfo.icon = core.material.icons.hero[core.getHeroLoc('direction')];
jumpInfo.width = core.material.icons.hero.width || 32;
@ -2912,6 +2981,7 @@ events.prototype.jumpHero = function (ex, ey, time, callback) {
}
events.prototype._jumpHero_doJump = function (jumpInfo, callback) {
core.status.heroMoving = -1;
var animate = window.setInterval(function () {
if (jumpInfo.jump_count > 0)
core.events._jumpHero_jumping(jumpInfo)
@ -2940,6 +3010,7 @@ events.prototype._jumpHero_finished = function (animate, ex, ey, callback) {
clearInterval(animate);
core.setHeroLoc('x', ex);
core.setHeroLoc('y', ey);
core.status.heroMoving = 0;
core.drawHero();
if (callback) callback();
}
@ -2972,7 +3043,7 @@ events.prototype.checkLvUp = function () {
}
events.prototype._checkLvUp_check = function () {
if (core.flags.statusBarItems.indexOf('enableLevelUp')>=0 || !core.firstData.levelUp
if (core.flags.statusBarItems.indexOf('enableLevelUp')<0 || !core.firstData.levelUp
|| core.status.hero.lv >= core.firstData.levelUp.length) return null;
// 计算下一个所需要的数值
var next = (core.firstData.levelUp[core.status.hero.lv] || {});

View File

@ -391,14 +391,3 @@ items.prototype.quickLoadEquip = function (index) {
core.drawTip("成功换上" + index + "号套装");
}
////// 获得装备直接增加的属性数据 //////
items.prototype.getEquippedStatus = function (name) {
var value = 0;
core.status.hero.equipment.forEach(function (v) {
if (!v || !(core.material.items[v] || {}).equip) return;
if (core.material.items[v].equip.percentage) return;
value += core.material.items[v].equip[name] || 0;
});
return value;
}

View File

@ -301,8 +301,8 @@ loader.prototype._loadAnimates_sync = function () {
this._setStartLoadTipText("正在加载动画文件...");
core.animates.forEach(function (t) {
core.http('GET', 'project/animates/' + t + ".animate?v=" + main.version, null, function (content) {
core.loader._loadAnimate(t, content);
core.http('GET', 'project/animates/' + t + ".animate?v=" + main.version, null, function (content) {
core.material.animates[t] = core.loader._loadAnimate(content);
}, function (e) {
main.log(e);
core.material.animates[t] = null;
@ -316,14 +316,14 @@ loader.prototype._loadAnimates_async = function (onprogress, onfinished) {
if (name.endsWith(".animate")) {
var t = name.substring(0, name.length - 8);
if (core.animates.indexOf(t) >= 0)
core.loader._loadAnimate(t, animates[name]);
core.material.animates[t] = core.loader._loadAnimate(animates[name]);
}
}
onfinished();
}, null, true, onprogress);
}
loader.prototype._loadAnimate = function (name, content) {
loader.prototype._loadAnimate = function (content) {
try {
content = JSON.parse(content);
var data = {};
@ -362,12 +362,12 @@ loader.prototype._loadAnimate = function (name, content) {
})
})
data.frames.push(info);
})
core.material.animates[name] = data;
});
return data;
}
catch (e) {
main.log(e);
core.material.animates[name] = null;
return null;
}
}

View File

@ -61,7 +61,7 @@ maps.prototype.loadFloor = function (floorId, map) {
}
/// 根据需求解析出blocks
maps.prototype.extractBlocks = function (map) {
maps.prototype.extractBlocks = function (map, flags) {
map = map || core.status.floorId;
if (typeof map == 'string') map = (core.status.maps||{})[map];
if (!map) return;
@ -71,16 +71,16 @@ maps.prototype.extractBlocks = function (map) {
return;
}
var floorId = map.floorId;
map.blocks = this._mapIntoBlocks(this.decompressMap(map.map, floorId), core.floors[floorId], floorId);
map.blocks = this._mapIntoBlocks(this.decompressMap(map.map, floorId), core.floors[floorId], floorId, flags);
}
maps.prototype._mapIntoBlocks = function (map, floor, floorId) {
maps.prototype._mapIntoBlocks = function (map, floor, floorId, flags) {
var blocks = [];
var mw = core.floors[floorId].width;
var mh = core.floors[floorId].height;
for (var i = 0; i < mh; i++) {
for (var j = 0; j < mw; j++) {
var block = this.initBlock(j, i, (map[i] || [])[j], true, floor);
var block = this.initBlock(j, i, (map[i] || [])[j], true, floor, flags);
if (block.id != 0 || block.event.trigger)
blocks.push(block);
}
@ -129,18 +129,18 @@ maps.prototype.getIdOfThis = function (id) {
}
////// 数字和ID的对应关系 //////
maps.prototype.initBlock = function (x, y, id, addInfo, eventFloor) {
maps.prototype.initBlock = function (x, y, id, addInfo, eventFloor, flags) {
var disable = null;
id = "" + (id || 0);
if (id.endsWith(":f")) disable = true;
if (id.endsWith(":t")) disable = false;
id = parseInt(id);
if (eventFloor != null) {
if (flags == null) flags = (core.status.hero || {}).flags || {};
disable = flags[[eventFloor.floorId, x, y, 'md'].join('@')];
}
var block = {'x': x, 'y': y, 'id': id};
if (disable != null) block.disable = disable;
if (id == 17) block.event = {"cls": "terrains", "id": "airwall", "noPass": true, "cannotIn":["up", "down", "left", "right"]};
if (id == 17) block.event = {"cls": "terrains", "id": "airwall", "cannotIn":["up", "down", "left", "right"]};
else if (id in this.blocksInfo) block.event = JSON.parse(JSON.stringify(this.blocksInfo[id]));
else if (core.icons.getTilesetOffset(id)) block.event = {"cls": "tileset", "id": "X" + id, "noPass": true};
else if (core.icons.getTilesetOffset(id)) block.event = {"cls": "tileset", "id": "X" + id};
else block.event = {'cls': 'terrains', 'id': 'none', 'noPass': false};
if (block.event.noPass == null) {
@ -221,30 +221,9 @@ maps.prototype._initMaps = function () {
return maps;
}
maps.prototype._initFloorMap = function (floorId) {
var map = core.clone(core.floors[floorId].map);
var mw = core.floors[floorId].width;
var mh = core.floors[floorId].height;
for (var x = 0; x < mh; x++) {
if (map[x] == null) map[x] = [];
for (var y = 0; y < mw; y++) {
if (map[x][y] == null) map[x][y] = 0;
// check "disable"
var event = core.floors[floorId].events[y + "," + x];
if (event && event.enable === false && main.mode == 'play') {
map[x][y] += ":f";
}
}
}
return map;
}
////// 压缩地图
maps.prototype.compressMap = function (mapArr, floorId) {
var floorMap = this._initFloorMap(floorId);
var floorMap = core.floors[floorId].map;
if (core.utils.same(mapArr, floorMap)) return null;
var mw = core.floors[floorId].width;
@ -268,14 +247,14 @@ maps.prototype.compressMap = function (mapArr, floorId) {
////// 解压缩地图
maps.prototype.decompressMap = function (mapArr, floorId) {
var floorMap = this._initFloorMap(floorId);
if (!mapArr) return floorMap;
var floorMap = core.floors[floorId].map;
if (!mapArr) return core.clone(floorMap);
var mw = core.floors[floorId].width;
var mh = core.floors[floorId].height;
for (var x = 0; x < mh; x++) {
if (mapArr[x] === 0) {
mapArr[x] = floorMap[x];
mapArr[x] = core.clone(floorMap[x]);
}
else {
for (var y = 0; y < mw; y++) {
@ -307,7 +286,7 @@ maps.prototype.saveMap = function (floorId) {
var map = maps[floorId];
var thisFloor = this._compressFloorData(map, core.floors[floorId]);
if (map.blocks) {
var mapArr = this.compressMap(this._getMapArrayFromBlocks(map.blocks, map.width, map.height, true), floorId);
var mapArr = this.compressMap(this._getMapArrayFromBlocks(map.blocks, map.width, map.height), floorId);
if (mapArr != null) thisFloor.map = mapArr;
}
return thisFloor;
@ -359,29 +338,21 @@ maps.prototype.resizeMap = function (floorId) {
}
////// 将当前地图重新变成二维数组形式 //////
maps.prototype.getMapArray = function (floorId, showDisable) {
maps.prototype.getMapArray = function (floorId) {
floorId = floorId || core.status.floorId;
var map = core.status.maps[floorId];
if (!map.blocks) return map.map;
return this._getMapArrayFromBlocks(map.blocks, map.width, map.height, showDisable);
return this._getMapArrayFromBlocks(map.blocks, map.width, map.height);
}
maps.prototype._getMapArrayFromBlocks = function (blockArray, width, height, showDisable) {
maps.prototype._getMapArrayFromBlocks = function (blockArray, width, height) {
var blocks = [];
var allzero = [];
for (var y = 0; y < width; y++) allzero.push(0);
for (var x = 0; x < height; x++) blocks.push(core.clone(allzero));
blockArray.forEach(function (block) {
var x = block.x, y = block.y;
if (block.disable) {
if (showDisable) blocks[y][x] = block.id + ":f";
}
else {
blocks[y][x] = block.id;
if (showDisable && block.disable === false)
blocks[y][x] = block.id + ":t";
}
blocks[block.y][block.x] = block.id;
});
return blocks;
}
@ -414,8 +385,8 @@ maps.prototype._getBgFgMapArray = function (name, floorId, noCache) {
for (var x = 0; x < width; x++) {
for (var y = 0; y < height; y++) {
arr[y] = arr[y] || [];
var flag = "__" + name + "Map__" + floorId + "_" + x + "_" + y;
var vFlag = "__" + name + "Value__" + floorId + "_" + x + "_" + y;
var flag = [floorId, x, y, name+'_disable'].join('@');
var vFlag = [floorId, x, y, name+'_value'].join('@');
if (core.hasFlag(flag)) arr[y][x] = 0;
else arr[y][x] = core.getFlag(vFlag, arr[y][x] || 0);
if (main.mode == 'editor') arr[y][x] = arr[y][x].idnum || arr[y][x] || 0;
@ -511,9 +482,9 @@ maps.prototype._canMoveHero_checkPoint = function (x, y, direction, floorId, ext
return false;
// 3. 检查是否能进将死的领域
if (floorId == core.status.floorId
&& core.status.hero.hp <= (core.status.checkBlock.damage[nx + "," + ny]||0)
&& !core.flags.canGoDeadZone && extraData.eventArray[ny][nx] == 0)
if (floorId == core.status.floorId && !core.flags.canGoDeadZone &&
core.status.hero.hp <= (core.status.checkBlock.damage[nx + "," + ny]||0)
&& extraData.eventArray[ny][nx] == 0)
return false;
return true;
@ -1437,12 +1408,17 @@ maps.prototype.showBlock = function (x, y, floorId) {
// 本身是禁用事件,启用之
if (block.disable) {
block.disable = false;
core.setFlag([floorId, x, y, 'md'].join('@'), false);
// 在本层,添加动画
if (floorId == core.status.floorId) {
core.drawBlock(block);
core.addGlobalAnimate(block);
if (block.event.cls == 'autotile') {
core.drawMap();
} else {
core.drawBlock(block);
core.addGlobalAnimate(block);
core.updateStatusBar();
}
}
core.updateStatusBar();
}
}
@ -1454,17 +1430,10 @@ maps.prototype.hideBlock = function (x, y, floorId) {
var block = core.getBlock(x, y, floorId, true);
if (block == null) return; // 不存在
// 删除动画,清除地图
if (floorId == core.status.floorId) {
core.removeGlobalAnimate(x, y);
core.clearMap('event', x * 32, y * 32, 32, 32);
var height = block.block.event.height || 32;
if (height > 32)
core.clearMap('event2', x * 32, y * 32 + 32 - height, 32, height - 32);
}
core.hideBlockByIndex(block.index, floorId);
core.updateStatusBar();
// 删除动画,清除地图
this._removeBlockFromMap(floorId, block.block);
}
////// 根据图块的索引来隐藏图块 //////
@ -1474,6 +1443,7 @@ maps.prototype.hideBlockByIndex = function (index, floorId) {
core.extractBlocks(floorId);
var blocks = core.status.maps[floorId].blocks, block = blocks[index];
block.disable = true;
core.setFlag([floorId, block.x, block.y, 'md'].join('@'), true);
}
////// 一次性隐藏多个block //////
@ -1485,6 +1455,21 @@ maps.prototype.hideBlockByIndexes = function (indexes, floorId) {
});
}
maps.prototype._removeBlockFromMap = function (floorId, block) {
if (floorId != core.status.floorId) return;
if (block.event.cls == 'autotile') {
core.drawMap();
} else {
var x = block.x, y = block.y;
core.removeGlobalAnimate(x, y);
core.clearMap('event', x * 32, y * 32, 32, 32);
var height = block.event.height || 32;
if (height > 32)
core.clearMap('event2', x * 32, y * 32 + 32 - height, 32, height - 32);
core.updateStatusBar();
}
}
////// 删除某个图块 //////
maps.prototype.removeBlock = function (x, y, floorId) {
floorId = floorId || core.status.floorId;
@ -1493,17 +1478,10 @@ maps.prototype.removeBlock = function (x, y, floorId) {
var block = core.getBlock(x, y, floorId, true);
if (block == null) return false; // 不存在
// 删除动画,清除地图
if (floorId == core.status.floorId) {
core.removeGlobalAnimate(x, y);
core.clearMap('event', x * 32, y * 32, 32, 32);
var height = block.block.event.height || 32;
if (height > 32)
core.clearMap('event2', x * 32, y * 32 + 32 - height, 32, height - 32);
}
core.removeBlockByIndex(block.index, floorId);
core.updateStatusBar();
// 删除动画,清除地图
this._removeBlockFromMap(floorId, block.block);
return true;
}
@ -1514,6 +1492,7 @@ maps.prototype.removeBlockByIndex = function (index, floorId) {
core.extractBlocks(floorId);
var blocks = core.status.maps[floorId].blocks, block = blocks[index];
blocks.splice(index, 1);
core.setFlag([floorId, block.x, block.y, 'md'].join('@'), true);
}
////// 一次性删除多个block //////
@ -1547,7 +1526,7 @@ maps.prototype._triggerBgFgMap = function (type, name, loc, floorId, callback) {
if (loc.length == 0) return;
loc.forEach(function (t) {
var x = t[0], y = t[1];
var flag = "__" + name + "Map__" + floorId + "_" + x + "_" + y;
var flag = [floorId, x, y, name+"_disable"].join('@');
if (type == 'hide') core.setFlag(flag, true);
else core.removeFlag(flag);
})
@ -1612,28 +1591,31 @@ maps.prototype.setBlock = function (number, x, y, floorId) {
return;
}
var originBlock = core.getBlock(x, y, floorId, true);
if (floorId == core.status.floorId) {
core.removeGlobalAnimate(x, y);
core.clearMap('event', x * 32, y * 32, 32, 32);
if (originBlock != null) {
var height = (originBlock.block.event || {}).height || 32;
if (height > 32)
core.clearMap('event2', x * 32, y * 32 + 32 - height, 32, height - 32);
}
}
var originEvent = originBlock == null ? null : originBlock.block.event;
if (originBlock == null) {
core.status.maps[floorId].blocks.push(block);
core.setFlag([floorId, x, y, 'md'].join('@'), false);
delete block.disable;
}
else {
originBlock.block.id = number;
originBlock.block.event = block.event;
block = originBlock.block;
}
if (floorId == core.status.floorId && !block.disable) {
core.drawBlock(block);
if (block.event.cls != 'autotile')
core.addGlobalAnimate(block);
core.updateStatusBar();
if (floorId == core.status.floorId) {
// 有任何一个是autotile直接重绘地图
if ((originEvent != null && originEvent.cls == 'autotile') || block.event.cls == 'autotile') {
core.drawMap();
} else {
if (originEvent != null) {
this._removeBlockFromMap(floorId, {x: x, y: y, event: originEvent});
}
if (!block.disable) {
core.drawBlock(block);
core.addGlobalAnimate(block);
core.updateStatusBar();
}
}
}
}
@ -1786,7 +1768,7 @@ maps.prototype.setBgFgBlock = function (name, number, x, y, floorId) {
else number = core.getNumberById(number);
}
var vFlag = "__" + name + "Value__" + floorId + "_" + x + "_" + y;
var vFlag = [floorId, x, y, name + "_value"].join('@');
core.setFlag(vFlag, number);
core.status[name + "maps"][floorId] = null;
@ -1805,6 +1787,10 @@ maps.prototype.resetMap = function (floorId) {
var needRefresh = false;
floorId.forEach(function (t) {
core.status.maps[t] = core.maps.loadFloor(t);
// 重置本层的全部独立事件
Object.keys(core.status.hero.flags).forEach(function (one) {
if (one.startsWith(floorId + '@')) delete core.status.hero.flags[one];
})
if (t == core.status.floorId) needRefresh = true;
});
if (needRefresh) this.drawMap();
@ -1990,7 +1976,6 @@ maps.prototype.jumpBlock = function (sx, sy, ex, ey, time, keep, callback) {
var block = blockArr[0], blockInfo = blockArr[1];
var canvases = this._initDetachedBlock(blockInfo, sx, sy, block.event.animate !== false);
this._moveDetachedBlock(blockInfo, 32 * sx, 32 * sy, 1, canvases);
core.playSound('jump.mp3');
var jumpInfo = this.__generateJumpInfo(sx, sy, ex, ey, time);
jumpInfo.keep = keep;
@ -2178,7 +2163,7 @@ maps.prototype.drawBoxAnimate = function () {
core.clearMap('ui', obj.bgx, obj.bgy, obj.bgWidth, obj.bgHeight);
core.fillRect('ui', obj.bgx, obj.bgy, obj.bgWidth, obj.bgHeight, core.material.groundPattern);
core.drawImage('ui', obj.image, core.status.globalAnimateStatus % obj.animate * 32, obj.pos,
32, obj.height, obj.x, obj.y, 32, obj.height);
32, obj.height, obj.x, obj.y, obj.dw || 32, obj.dh || obj.height);
});
}
@ -2242,32 +2227,34 @@ maps.prototype.drawHeroAnimate = function (name, callback) {
}
////// 绘制动画的某一帧 //////
maps.prototype._drawAnimateFrame = function (animate, centerX, centerY, index) {
var frame = animate.frames[index];
maps.prototype._drawAnimateFrame = function (name, animate, centerX, centerY, index) {
var ctx = core.getContextByName(name);
if (!ctx) return;
var frame = animate.frames[index % animate.frame];
var ratio = animate.ratio;
frame.forEach(function (t) {
var image = animate.images[t.index];
if (!image) return;
var realWidth = image.width * ratio * t.zoom / 100;
var realHeight = image.height * ratio * t.zoom / 100;
core.setAlpha('animate', t.opacity / 255);
core.setAlpha(ctx, t.opacity / 255);
var cx = centerX + t.x, cy = centerY + t.y;
if (!t.mirror && !t.angle) {
core.drawImage('animate', image, cx - realWidth / 2 - core.bigmap.offsetX, cy - realHeight / 2 - core.bigmap.offsetY, realWidth, realHeight);
core.drawImage(ctx, image, cx - realWidth / 2 - core.bigmap.offsetX, cy - realHeight / 2 - core.bigmap.offsetY, realWidth, realHeight);
}
else {
core.saveCanvas('animate');
core.canvas.animate.translate(cx, cy);
core.saveCanvas(ctx);
ctx.translate(cx, cy);
if (t.angle)
core.canvas.animate.rotate(-t.angle * Math.PI / 180);
ctx.rotate(-t.angle * Math.PI / 180);
if (t.mirror)
core.canvas.animate.scale(-1, 1);
core.drawImage('animate', image, -realWidth / 2 - core.bigmap.offsetX, -realHeight / 2 - core.bigmap.offsetY, realWidth, realHeight);
core.loadCanvas('animate');
ctx.scale(-1, 1);
core.drawImage(ctx, image, -realWidth / 2 - core.bigmap.offsetX, -realHeight / 2 - core.bigmap.offsetY, realWidth, realHeight);
core.loadCanvas(ctx);
}
core.setAlpha('animate', 1);
core.setAlpha(ctx, 1);
})
}

View File

@ -77,10 +77,10 @@ ui.prototype.fillText = function (name, text, x, y, style, font, maxWidth) {
var ctx = this.getContextByName(name);
if (ctx) {
// 如果存在最大宽度
if (maxWidth != null)
this._fillTextWithMaxWidth(ctx, text, x, y, maxWidth);
else
ctx.fillText(text, x, y);
if (maxWidth != null) {
this.setFontForMaxWidth(ctx, text, maxWidth);
}
ctx.fillText(text, x, y);
}
}
@ -90,16 +90,15 @@ ui.prototype._uievent_fillText = function (data) {
}
////// 自适配字体大小
ui.prototype._fillTextWithMaxWidth = function (ctx, text, x, y, maxWidth) {
// 获得当前字体
ui.prototype.setFontForMaxWidth = function (name, text, maxWidth, font) {
var ctx = this.getContextByName(name);
if (font) core.setFont(name, font);
var font = ctx.font, u = /(\d+)px/.exec(font);
if (u == null) return ctx.fillText(text, x, y);
if (u == null) return;
for (var font_size = parseInt(u[1]); font_size >= 8; font_size--) {
ctx.font = font.replace(/(\d+)px/, font_size+"px");
if (ctx.measureText(text).width <= maxWidth) break;
if (ctx.measureText(text).width <= maxWidth) return;
}
ctx.fillText(text, x, y);
ctx.font = font;
}
////// 在某个canvas上绘制粗体 //////
@ -126,61 +125,103 @@ ui.prototype._uievent_fillBoldText = function (data) {
}
////// 在某个canvas上绘制一个矩形 //////
ui.prototype.fillRect = function (name, x, y, width, height, style) {
ui.prototype.fillRect = function (name, x, y, width, height, style, angle) {
if (style) core.setFillStyle(name, style);
var ctx = this.getContextByName(name);
if (ctx) ctx.fillRect(x, y, width, height);
if (ctx) {
if (angle) {
ctx.save();
ctx.translate(x + width / 2, y + height / 2);
ctx.rotate(angle);
ctx.translate(-x - width / 2, -y - height / 2);
}
ctx.fillRect(x, y, width, height);
if (angle) {
ctx.restore();
}
}
}
ui.prototype._uievent_fillRect = function (data) {
this._createUIEvent();
if (data.radius) {
this.fillRoundRect('uievent', core.calValue(data.x), core.calValue(data.y), core.calValue(data.width), core.calValue(data.height), core.calValue(data.radius), data.style);
this.fillRoundRect('uievent', core.calValue(data.x), core.calValue(data.y), core.calValue(data.width), core.calValue(data.height),
core.calValue(data.radius), data.style, (core.calValue(data.angle) || 0) * Math.PI / 180);
} else {
this.fillRect('uievent', core.calValue(data.x), core.calValue(data.y), core.calValue(data.width), core.calValue(data.height), data.style);
this.fillRect('uievent', core.calValue(data.x), core.calValue(data.y), core.calValue(data.width), core.calValue(data.height),
data.style, (core.calValue(data.angle) || 0) * Math.PI / 180);
}
}
////// 在某个canvas上绘制一个矩形的边框 //////
ui.prototype.strokeRect = function (name, x, y, width, height, style, lineWidth) {
ui.prototype.strokeRect = function (name, x, y, width, height, style, lineWidth, angle) {
if (style) core.setStrokeStyle(name, style);
if (lineWidth) core.setLineWidth(name, lineWidth);
var ctx = this.getContextByName(name);
if (ctx) ctx.strokeRect(x, y, width, height);
if (ctx) {
if (angle) {
ctx.save();
ctx.translate(x + width / 2, y + height / 2);
ctx.rotate(angle);
ctx.translate(-x - width / 2, -y - height / 2);
}
ctx.strokeRect(x, y, width, height);
if (angle) {
ctx.restore();
}
}
}
ui.prototype._uievent_strokeRect = function (data) {
this._createUIEvent();
if (data.radius) {
this.strokeRoundRect('uievent', core.calValue(data.x), core.calValue(data.y), core.calValue(data.width), core.calValue(data.height),
core.calValue(data.radius), data.style, data.lineWidth);
core.calValue(data.radius), data.style, data.lineWidth, (core.calValue(data.angle) || 0) * Math.PI / 180);
} else {
this.strokeRect('uievent', core.calValue(data.x), core.calValue(data.y), core.calValue(data.width), core.calValue(data.height), data.style, data.lineWidth);
this.strokeRect('uievent', core.calValue(data.x), core.calValue(data.y), core.calValue(data.width), core.calValue(data.height),
data.style, data.lineWidth, (core.calValue(data.angle) || 0) * Math.PI / 180);
}
}
////// 在某个canvas上绘制一个圆角矩形 //////
ui.prototype.fillRoundRect = function (name, x, y, width, height, radius, style) {
ui.prototype.fillRoundRect = function (name, x, y, width, height, radius, style, angle) {
if (style) core.setFillStyle(name, style);
var ctx = this.getContextByName(name);
if (ctx) {
if (angle) {
ctx.save();
ctx.translate(x + width / 2, y + height / 2);
ctx.rotate(angle);
ctx.translate(-x - width / 2, -y - height / 2);
}
this._roundRect_buildPath(ctx, x, y, width, height, radius);
ctx.fill();
if (angle) {
ctx.restore();
}
}
}
////// 在某个canvas上绘制一个圆角矩形的边框 //////
ui.prototype.strokeRoundRect = function (name, x, y, width, height, radius, style, lineWidth) {
ui.prototype.strokeRoundRect = function (name, x, y, width, height, radius, style, lineWidth, angle) {
if (style) core.setStrokeStyle(name, style);
if (lineWidth) core.setLineWidth(name, lineWidth);
var ctx = this.getContextByName(name);
if (ctx) {
if (angle) {
ctx.save();
ctx.translate(x + width / 2, y + height / 2);
ctx.rotate(angle);
ctx.translate(-x - width / 2, -y - height / 2);
}
this._roundRect_buildPath(ctx, x, y, width, height, radius);
ctx.stroke();
if (angle) {
ctx.restore();
}
}
}
ui.prototype._roundRect_buildPath = function (ctx, x, y, width, height, radius) {
ctx.beginPath();
ctx.moveTo(x + radius, y);
@ -504,7 +545,7 @@ ui.prototype.splitLines = function (name, text, maxWidth, font) {
}
////// 绘制一张图片 //////
ui.prototype.drawImage = function (name, image, x, y, w, h, x1, y1, w1, h1) {
ui.prototype.drawImage = function (name, image, x, y, w, h, x1, y1, w1, h1, angle) {
// 检测文件名以 :x, :y, :o 结尾,表示左右翻转,上下翻转和中心翻转
var ctx = this.getContextByName(name);
if (!ctx) return;
@ -516,7 +557,7 @@ ui.prototype.drawImage = function (name, image, x, y, w, h, x1, y1, w1, h1) {
}
image = core.getMappedName(image);
image = core.material.images.images[image];
if (!image || !(image instanceof Image)) return;
if (!image) return;
}
var scale = {
@ -533,23 +574,25 @@ ui.prototype.drawImage = function (name, image, x, y, w, h, x1, y1, w1, h1) {
h = image.height;
}
if (x1 != null && y1 != null && w1 != null && h1 != null) {
if (reverse == null) {
if (!reverse && !angle) {
ctx.drawImage(image, x, y, w, h, x1, y1, w1, h1);
} else {
ctx.save();
ctx.translate(x1 + w1 / 2, y1 + h1 / 2);
ctx.scale(scale[reverse][0], scale[reverse][1]);
if (reverse) ctx.scale(scale[reverse][0], scale[reverse][1]);
if (angle) ctx.rotate(angle);
ctx.drawImage(image, x, y, w, h, -w1 / 2, -h1 / 2, w1, h1);
ctx.restore();
}
return;
}
if (reverse == null) {
if (!reverse && !angle) {
ctx.drawImage(image, x, y, w, h);
} else {
ctx.save();
ctx.translate(x + w / 2, y + h / 2);
ctx.scale(scale[reverse][0], scale[reverse][1]);
if (reverse) ctx.scale(scale[reverse][0], scale[reverse][1]);
if (angle) ctx.rotate(angle);
ctx.drawImage(image, -w / 2, -h / 2, w, h);
ctx.restore();
}
@ -560,7 +603,7 @@ ui.prototype.drawImage = function (name, image, x, y, w, h, x1, y1, w1, h1) {
ui.prototype._uievent_drawImage = function (data) {
this._createUIEvent();
this.drawImage('uievent', data.image + (data.reverse || ''), core.calValue(data.x), core.calValue(data.y), core.calValue(data.w), core.calValue(data.h),
core.calValue(data.x1), core.calValue(data.y1), core.calValue(data.w1), core.calValue(data.h1));
core.calValue(data.x1), core.calValue(data.y1), core.calValue(data.w1), core.calValue(data.h1), (core.calValue(data.angle) || 0) * Math.PI / 180);
}
ui.prototype.drawIcon = function (name, id, x, y, w, h, frame) {
@ -1304,9 +1347,11 @@ ui.prototype._drawTextBox_drawImages = function (content) {
core.drawImage('ui', ss[0], parseFloat(ss[1]), parseFloat(ss[2]));
else if (ss.length==5)
core.drawImage('ui', ss[0], parseFloat(ss[1]), parseFloat(ss[2]), parseFloat(ss[3]), parseFloat(ss[4]));
else if (ss.length==9 || ss.length==10) {
if (ss.length==10) core.setAlpha('ui', parseFloat(ss[9]));
core.drawImage('ui', ss[0], parseFloat(ss[1]), parseFloat(ss[2]), parseFloat(ss[3]), parseFloat(ss[4]), parseFloat(ss[5]), parseFloat(ss[6]), parseFloat(ss[7]), parseFloat(ss[8]));
else if (ss.length >= 9) {
if (ss.length >= 10) core.setAlpha('ui', parseFloat(ss[9]));
var angle = (parseFloat(ss[10]) || 0) * Math.PI / 180;
core.drawImage('ui', ss[0], parseFloat(ss[1]), parseFloat(ss[2]), parseFloat(ss[3]), parseFloat(ss[4]),
parseFloat(ss[5]), parseFloat(ss[6]), parseFloat(ss[7]), parseFloat(ss[8]), angle);
core.setAlpha('ui', 1);
}
return "";
@ -1326,6 +1371,9 @@ ui.prototype._drawTextBox_getHorizontalPosition = function (content, titleInfo,
var min_width = 220 - paddingLeft, max_width = validWidth;
// 无行走图或头像则可以适当缩小min_width
if (titleInfo.image == null) min_width = 160;
if (titleInfo.title) {
min_width = core.clamp(core.calWidth('ui', titleInfo.title, this._buildFont(core.status.textAttribute.titlefont, true)), min_width, max_width);
}
validWidth = this._calTextBoxWidth('ui', realContent, min_width, max_width, this._buildFont());
width = validWidth + paddingLeft + paddingRight;
left = core.clamp(32 * posInfo.px + 16 - width / 2 - core.bigmap.offsetX, left, right - width);
@ -1867,26 +1915,58 @@ ui.prototype._drawBook_drawBox = function (index, enemy, top, pageinfo) {
var img_top = border_top + 5, img_left = border_left + 5;
core.strokeRect('ui', 22, border_top, 42, 42, '#DDDDDD', 2);
var blockInfo = core.getBlockInfo(enemy.id);
core.status.boxAnimateObjs.push({
'bgx': border_left, 'bgy': border_top, 'bgWidth': 42, 'bgHeight': 42,
'x': img_left, 'y': img_top, 'height': 32, 'animate': blockInfo.animate,
'image': blockInfo.image, 'pos': blockInfo.posY * blockInfo.height
});
if (blockInfo.height >= 42) {
var drawWidth = 42 * 32 / blockInfo.height;
core.status.boxAnimateObjs.push({
'bgx': border_left, 'bgy': border_top, 'bgWidth': 42, 'bgHeight': 42,
'x': img_left - 5 + (42 - drawWidth) / 2, 'y': img_top - 5, 'dw': drawWidth, 'dh': 42,
'height': blockInfo.height, 'animate': blockInfo.animate,
'image': blockInfo.image, 'pos': blockInfo.posY * blockInfo.height
});
} else {
core.status.boxAnimateObjs.push({
'bgx': border_left, 'bgy': border_top, 'bgWidth': 42, 'bgHeight': 42,
'x': img_left, 'y': img_top, 'height': 32, 'animate': blockInfo.animate,
'image': blockInfo.image, 'pos': blockInfo.posY * blockInfo.height
});
}
}
ui.prototype._drawBook_drawName = function (index, enemy, top, left, width) {
// 绘制第零列(名称和特殊属性)
// 如果需要添加自己的比如怪物的称号等,也可以在这里绘制
core.setTextAlign('ui', 'center');
if (enemy.specialText=='') {
if (enemy.specialText.length == 0) {
core.fillText('ui', enemy.name, left + width / 2,
top + 35, '#DDDDDD', this._buildFont(17, true), width);
}
else {
core.fillText('ui', enemy.name, left + width / 2,
top + 28, '#DDDDDD', this._buildFont(17, true), width);
core.fillText('ui', enemy.specialText, left + width / 2,
top + 50, '#FF6A6A', this._buildFont(15, true), width);
switch (enemy.specialText.length) {
case 1:
core.fillText('ui', enemy.specialText[0], left + width / 2,
top + 50, core.arrayToRGBA((enemy.specialColor || [])[0] || '#FF6A6A'),
this._buildFont(15, true), width);
break;
case 2:
// Step 1: 计算字体
var text = enemy.specialText[0] + " " + enemy.specialText[1];
core.setFontForMaxWidth('ui', text, width, this._buildFont(15, true));
// Step 2: 计算总宽度
var totalWidth = core.calWidth('ui', text);
var leftWidth = core.calWidth('ui', enemy.specialText[0]);
var rightWidth = core.calWidth('ui', enemy.specialText[1]);
// Step 3: 绘制
core.fillText('ui', enemy.specialText[0], left + (width + leftWidth - totalWidth) / 2,
top+50, core.arrayToRGBA((enemy.specialColor || [])[0] || '#FF6A6A'));
core.fillText('ui', enemy.specialText[1], left + (width + totalWidth - rightWidth) / 2,
top+50, core.arrayToRGBA((enemy.specialColor || [])[1] || '#FF6A6A'));
break;
default:
core.fillText('ui', '多属性...', left + width / 2,
top + 50, '#FF6A6A', this._buildFont(15, true), width);
}
}
}
@ -2090,15 +2170,15 @@ ui.prototype._drawBookDetail_hatred = function (enemy, texts) {
}
ui.prototype._drawBookDetail_turnAndCriticals = function (enemy, floorId, texts) {
var damageInfo = core.getDamageInfo(enemy, null, null, null, floorId);
var damageInfo = core.getDamageInfo(enemy.id, null, null, null, floorId);
texts.push("\r[#FF6A6A]\\d战斗回合数\\d\r[]"+((damageInfo||{}).turn||0));
// 临界表
var criticals = core.enemys.nextCriticals(enemy, 8, null, null, floorId).map(function (v) {
var criticals = core.enemys.nextCriticals(enemy.id, 8, null, null, floorId).map(function (v) {
return core.formatBigNumber(v[0])+":"+core.formatBigNumber(v[1]);
});
while (criticals[0]=='0:0') criticals.shift();
texts.push("\r[#FF6A6A]\\d临界表\\d\r[]"+JSON.stringify(criticals));
var prevInfo = core.getDamageInfo(enemy, {atk: core.status.hero.atk-1}, null, null, floorId);
var prevInfo = core.getDamageInfo(enemy.id, {atk: core.status.hero.atk-1}, null, null, floorId);
if (prevInfo != null && damageInfo != null) {
if (damageInfo.damage != null) damageInfo = damageInfo.damage;
if (prevInfo.damage != null) prevInfo = prevInfo.damage;
@ -2504,15 +2584,16 @@ ui.prototype._drawEquipbox_drawStatusChanged = function (info, y, equip, equipTy
if (typeof core.status.hero[name] != 'number') continue;
var nowValue = core.getRealStatus(name);
// 查询新值
var newValue = (core.getStatus(name) + (compare.value[name] || 0))
* (core.getBuff(name) + (compare.percentage[name] || 0) / 100);
var newValue = Math.floor((core.getStatus(name) + (compare.value[name] || 0))
* (core.getBuff(name) * 100 + (compare.percentage[name] || 0)) / 100);
if (nowValue == newValue) continue;
var text = this._drawEquipbox_getStatusName(name);
this._drawEquipbox_drawStatusChanged_draw(text + " ", '#CCCCCC', obj);
var color = newValue>nowValue?'#00FF00':'#FF0000';
nowValue = core.formatBigNumber(nowValue);
newValue = core.formatBigNumber(newValue);
this._drawEquipbox_drawStatusChanged_draw(nowValue+"->", '#CCCCCC', obj);
this._drawEquipbox_drawStatusChanged_draw(newValue, newValue>nowValue?'#00FF00':'#FF0000', obj);
this._drawEquipbox_drawStatusChanged_draw(newValue, color, obj);
obj.drawOffset += 8;
}
}
@ -2644,14 +2725,14 @@ ui.prototype._drawSLPanel_drawRecord = function(title, data, x, y, size, cho, hi
core.strokeRect('ui', x-size/2, y+15, size, size, cho?strokeColor:'#FFFFFF', cho?6:2);
if (data && data.floorId) {
var map = core.maps.loadMap(data.maps, data.floorId);
core.extractBlocks(map);
core.extractBlocks(map, data.hero.flags);
core.drawThumbnail(data.floorId, map.blocks, {
heroLoc: data.hero.loc, heroIcon: data.hero.image, flags: data.hero.flags
}, {
ctx: 'ui', x: x-size/2, y: y+15, size: size, centerX: data.hero.loc.x, centerY: data.hero.loc.y
});
if (core.isPlaying() && core.getFlag("hard") != data.hero.flags.hard) {
core.fillRect('ui', x-size/2, y+15, size, size, [0, 0, 0, 0.4], 2);
core.fillRect('ui', x-size/2, y+15, size, size, [0, 0, 0, 0.4]);
core.fillText('ui', data.hard, x, parseInt(y+22+size/2), data.hero.flags.__hardColor__ || 'red', this._buildFont(30,true));
}
var v = core.formatBigNumber(data.hero.hp,true)+"/"+core.formatBigNumber(data.hero.atk,true)+"/"+core.formatBigNumber(data.hero.def,true);
@ -2661,8 +2742,8 @@ ui.prototype._drawSLPanel_drawRecord = function(title, data, x, y, size, cho, hi
core.fillText('ui', core.formatDate(new Date(data.time)), x, y+43+size, data.hero.flags.debug?'#FF6A6A':'#FFFFFF');
}
else {
core.fillRect('ui', x-size/2, y+15, size, size, '#333333', 2);
core.fillText('ui', '空', x, parseInt(y+22+size/2), '#FFFFFF', this._buildFont(30,true));
core.fillRect('ui', x-size/2, y+15, size, size, '#333333');
core.fillText('ui', '空', x, parseInt(y+22+size/2), '#FFFFFF', this._buildFont(30, true));
}
}
@ -2853,6 +2934,8 @@ ui.prototype._drawStatistics_items = function (floorId, floor, id, obj) {
def = core.status.hero.def - temp.def;
mdef = core.status.hero.mdef - temp.mdef;
core.status.hero = temp;
window.hero = core.status.hero;
window.flags = core.status.hero.flags;
}
else if (obj.cls[id]=='equips') {
var values = core.material.items[id].equip || {};
@ -2919,7 +3002,7 @@ ui.prototype.drawHelp = function () {
core.status.event.id = 'help';
core.lockControl();
core.setAlpha('ui', 1);
core.fillRect('ui', 0, 0, this.PIXEL, this.PIXEL, '#FFFFFF');
core.fillRect('ui', 0, 0, this.PIXEL, this.PIXEL, '#000000');
core.drawImage('ui', core.material.images.keyboard, 32 * (this.HSIZE - 6), 32 * (this.HSIZE - 6));
}
else {

View File

@ -401,7 +401,7 @@ utils.prototype.formatSize = function (size) {
utils.prototype.formatBigNumber = function (x, onMap) {
x = Math.floor(parseFloat(x));
if (!core.isset(x)) return '???';
if (x > 1e24 || x < -1e24) return x;
if (x > 1e24 || x < -1e24) return x.toExponential(2);
var c = x < 0 ? "-" : "";
x = Math.abs(x);
@ -498,7 +498,7 @@ utils.prototype._encodeRoute_encodeOne = function (t) {
else if (t.indexOf('choices:') == 0)
return "C" + t.substring(8);
else if (t.indexOf('shop:') == 0)
return "S" + t.substring(5);
return "S" + t.substring(5) + ":";
else if (t == 'turn')
return 'T';
else if (t.indexOf('turn:') == 0)
@ -606,6 +606,19 @@ utils.prototype._decodeRoute_decodeOne = function (decodeObj, c) {
break;
case "S":
decodeObj.ans.push("shop:" + nxt);
// V266->V2.7商店录像兼容性
if (core.initStatus.shops[nxt]) {
if (!isNaN(decodeObj.route.charAt(decodeObj.index))) {
var selections = this._decodeRoute_getNumber(decodeObj, true);
// 只接普通商店
if (!core.initStatus.shops[nxt].item && !core.initStatus.shops[nxt].commonEvent) {
decodeObj.ans = decodeObj.ans.concat(selections.split("").map(function (one) {
return 'choices:' + one;
}));
decodeObj.ans.push("choices:-1");
}
}
}
break;
case "T":
decodeObj.ans.push("turn");

View File

@ -45,12 +45,6 @@ if (functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a.events.setInitData || !plugin
<li>部分方框进行了合并,请一个个仔细检查是否存在问题。</li>
</ul>
</li>
<li>下拉框切到「楼层属性」,并注意以下内容:
<ul>
<li><code>item_ratio</code>被重命名为<code>ratio</code>,请自行修改。</li>
<li>楼层贴图的结构在V2.7中被修改;请重新制作。</li>
</ul>
</li>
<li>素材区的如下图块有所变动:
<ul>
<li>三色墙和六色门从terrains中解除引用请用animates中的进行绘制。</li>
@ -61,6 +55,13 @@ if (functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a.events.setInitData || !plugin
<li>npc48的默认动画帧数<code>null</code>改回为4如需静止状态请手动改成1。</li>
</ul>
</li>
<li>下拉框切到「楼层属性」,并注意以下内容:
<ul>
<li><code>item_ratio</code>被重命名为<code>ratio</code>,请自行修改。</li>
<li>(你也可以直接改宝石和血瓶的效果,将<code>core.status.thisMap.ratio</code>改成<code>core.status.thisMap.item_ratio</code>。)</li>
<li>楼层贴图的结构在V2.7中被修改;请重新制作。</li>
</ul>
</li>
<li>下拉框切换到「脚本编辑」并请重新编辑各个自己改过的函数可以双开一个原版V266项目和当前接档的项目进行处理
<ul>
<li>请注意V2.7中的经验全部从<code>experience</code>替换成简写的<code>exp</code>;写伤害计算等时请尤其注意。</li>
@ -83,6 +84,11 @@ if (functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a.events.setInitData || !plugin
<li>「绘制圆」「绘制圆边框」「重启当前事件」已经被删除,并且无法再在游戏中使用,请替换成等价的写法。</li>
</ul>
</li>
<li>其他
<ul>
<li>V2.7默认采用新版图标;如果觉得不合适可以将<code>materials</code>目录下的<code>icons_old.png</code>替换掉<code>icons.png</code>以使用原版图标。</li>
</ul>
</li>
<li><b style='color:red'>接档后请做好充分的测试!最好能跑通录像以确认接档无误!</b></li>
</ol>
</p>
@ -111,6 +117,10 @@ function encode(str) {
}))
}
function random_string() {
return (Math.random()+"_"+Math.random()).replace(/\./g, "");
}
// 接档全局属性
function action_data(callback) {
var data = data_a1e2fb4a_e986_4524_b0da_9b7ba7c0874d;
@ -118,7 +128,7 @@ function action_data(callback) {
// Step 0: 移动目录
// materials
['animates', 'enemys', 'items', 'npcs', 'terrains', 'enemy48', 'npc48', 'icons', 'airwall', 'fog', 'keyboard'].forEach(function (one) {
['animates', 'enemys', 'items', 'npcs', 'terrains', 'enemy48', 'npc48', 'airwall', 'fog', 'keyboard'].forEach(function (one) {
fs.moveFile('project/images/'+one+".png", 'project/materials/'+one+'.png', function (e, d) {});
});
main.tilesets.forEach(function (one) {
@ -176,6 +186,11 @@ function action_data(callback) {
delete values.greenJewel;
delete values.moveSpeed;
delete values.floorChangeTime;
if (flags.enableExperience != null) {
flags.enableExp = flags.enableExperience;
delete flags.enableExperience;
}
var statusList = [
"enableFloor",
"enableName",
@ -203,6 +218,7 @@ function action_data(callback) {
});
}
statusList.forEach(function (one) { delete flags[one]; });
delete flags.enableExperience;
delete flags.pickaxeFourDirections;
delete flags.bombFourDirections;
delete flags.snowFourDirections;
@ -213,6 +229,7 @@ function action_data(callback) {
delete flags.betweenAttackCeil;
delete flags.startDirectly;
delete flags.enableDisabledShop;
delete flags.potionWhileRouting;
delete flags.checkConsole;
// 写入
@ -241,7 +258,7 @@ function action_enemys(callback) {
var estr = JSON.stringify(enemy, function (k, t) {
if (t && t.hp != null) {
delete t.id;
var id_ = ":" + k + ":";
var id_ = random_string();
emap[id_] = JSON.stringify(t);
return id_;
} else return t;
@ -335,7 +352,7 @@ function action_items(callback) {
"text": "可以打开一扇红门",
"hideInToolbox": true
},
"redGem": {
"redJewel": {
"cls": "items",
"name": "红宝石",
"text": "攻击+${core.values.redGem}",
@ -344,7 +361,7 @@ function action_items(callback) {
"useItemEffect": "core.status.hero.atk += core.values.redGem",
"canUseItemEffect": "true"
},
"blueGem": {
"blueJewel": {
"cls": "items",
"name": "蓝宝石",
"text": ",防御+${core.values.blueGem}",
@ -353,7 +370,7 @@ function action_items(callback) {
"useItemEffect": "core.status.hero.def += core.values.blueGem",
"canUseItemEffect": "true"
},
"greenGem": {
"greenJewel": {
"cls": "items",
"name": "绿宝石",
"text": ",护盾+${core.values.greenGem}",
@ -362,7 +379,7 @@ function action_items(callback) {
"useItemEffect": "core.status.hero.mdef += core.values.greenGem",
"canUseItemEffect": "true"
},
"yellowGem": {
"yellowJewel": {
"cls": "items",
"name": "黄宝石",
"text": "可以进行加点",
@ -508,12 +525,11 @@ function action_items(callback) {
for (var id in data) {
items[id] = data[id];
}
delete items.snow;
var datastr = 'var items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a = \n';
datastr += JSON.stringify(items, function (k, v) {
if (v && v.id != null) delete v.id;
return v;
}, '\t');
for (var id in items) delete items[id].id;
datastr += JSON.stringify(items, null, '\t');
fs.writeFile('project/items.js', encode(datastr), 'base64', function (err, data) {
if (err) {
alert('items接档失败请查看控制台报错并刷新重试。');
@ -565,7 +581,7 @@ function action_maps(callback) {
var emap = {};
var estr = JSON.stringify(maps, function (k, v) {
if (v && v.id != null) {
var id_ = ':' + v.id + ':';
var id_ = random_string();
emap[id_] = JSON.stringify(v);
return id_;
} else return v

View File

@ -48,15 +48,10 @@ var enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80 =
"ghostWarrior": {"name":"冥队长","hp":100,"atk":120,"def":0,"money":8,"exp":0,"point":0,"special":7},
"whiteSlimeman": {"name":"水银战士","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"slimeman": {"name":"影子战士","hp":100,"atk":0,"def":0,"money":11,"exp":0,"point":0,"special":[10,21],"atkValue":2,"defValue":3},
"yellowGT": {"name":"初级卫兵","hp":100,"atk":120,"def":0,"money":10,"exp":0,"point":0,"special":0},
"blueGT": {"name":"中级卫兵","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"redGT": {"name":"高级卫兵","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"blackMS": {"name":"黑衣魔王","hp":1000,"atk":500,"def":0,"money":1000,"exp":1000,"point":0,"special":0,"notBomb":true},
"yellowMS": {"name":"黄衣魔王","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"greenMS": {"name":"青衣武士","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"yellowGateKeeper": {"name":"初级卫兵","hp":100,"atk":120,"def":0,"money":10,"exp":0,"point":0,"special":0},
"blueGateKeeper": {"name":"中级卫兵","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"redGateKeeper": {"name":"高级卫兵","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"magicMaster": {"name":"黑暗大法师","hp":100,"atk":120,"def":0,"money":12,"exp":0,"point":0,"special":11,"value":0.3333333333333333,"add":true,"notBomb":true},
"blueMS": {"name":"白衣武士","hp":100,"atk":120,"def":0,"money":17,"exp":0,"point":0,"special":16},
"redMS": {"name":"红衣魔王","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"devilWarrior": {"name":"魔神武士","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"fairyEnemy": {"name":"仙子","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"dragon": {"name":"魔龙","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
@ -73,12 +68,17 @@ var enemys_fcae963b_31c9_42b4_b48c_bb48d09f3f80 =
"greenKnight": {"name":"强盾骑士","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"bowman": {"name":"弓兵","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"liteBowman": {"name":"精锐弓兵","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"crismonZombie": {"name":"红兽人","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"crimsonZombie": {"name":"红兽人","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"watcherSlime": {"name":"邪眼怪","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"mutantSlimeman": {"name":"变异战士","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"devilKnight": {"name":"恶灵骑士","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"grayPriest": {"name":"混沌法师","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"greenGT": {"name":"卫兵队长","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"greenGateKeeper": {"name":"卫兵队长","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"ghostSoldier": {"name":"冥队长","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"frostBat": {"name":"寒蝙蝠","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0}
"frostBat": {"name":"寒蝙蝠","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"blackKing": {"name":"黑衣魔王","hp":1000,"atk":500,"def":0,"money":1000,"exp":1000,"point":0,"special":0,"notBomb":true},
"yellowKing": {"name":"黄衣魔王","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"greenKing": {"name":"青衣武士","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"redKing": {"name":"红衣魔王","hp":0,"atk":0,"def":0,"money":0,"exp":0,"point":0,"special":0},
"blueKing": {"name":"白衣武士","hp":100,"atk":120,"def":0,"money":17,"exp":0,"point":0,"special":16}
}

View File

@ -37,8 +37,8 @@ main.floors.sample0=
],
"events": {
"10,9": [
"\t[老人,man]这些是本样板支持的所有的道具。\n\n道具分为四类items, constants, toolsequips。\nitems 为即捡即用类道具,例如宝石、血瓶、剑盾等。\nconstants 为永久道具,例如怪物手册、楼层传送器、幸运金币等。\ntools 为消耗类道具,例如破墙镐、炸弹、中心对称飞行器等。\nequips 为装备,例如剑盾等。",
"\t[老人,man]\b[up]有关道具效果,定义在items.js中。\n目前大多数道具已有默认行为如有自定义的需求则需在items.js中修改代码。",
"\t[老人,man]\b[down,null]这些是本样板支持的所有的道具。\n\n道具分为四类items, constants, toolsequips。\nitems 为即捡即用类道具,例如宝石、血瓶等。\nconstants 为永久道具,例如怪物手册、楼层传送器、幸运金币等。\ntools 为消耗类道具,例如破墙镐、炸弹、中心对称飞行器等。\nequips 为装备,例如剑盾等。",
"\t[老人,man]\b[up]有关道具效果,定义在project文件夹的items.js中。\n目前大多数道具已有默认行为如有自定义的需求请修改道具的图块属性。",
"\t[老人,man]\b[up]拾取道具结束后可触发 afterGetItem 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。",
{
"type": "hide",
@ -46,56 +46,59 @@ main.floors.sample0=
}
],
"10,11": [
"\t[老人,trader]这些是门,需要对应的钥匙打开。\n机关门必须使用特殊的开法。",
"\t[老人,trader]开门后可触发 afterOpenDoor 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。",
"\t[老人,trader]\b[this]这些是门,需要对应的钥匙打开。\n机关门必须使用特殊的开法。",
"\t[老人,trader]\b[this]开门后可触发 afterOpenDoor 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。",
{
"type": "hide",
"time": 500
}
],
"2,10": [
"\t[少女,npc0]这些是路障、楼梯、传送门。",
"\t[少女,npc0]血网的伤害数值、中毒后每步伤害数值、衰弱时攻防下降的数值,都在 data.js 内定义。\n\n路障同样会尽量被自动寻路绕过。",
"\t[少女,npc0]楼梯和传送门需要在changeFloor中定义目标楼层和位置可参见样板里已有的的写法。",
{
"type": "hide",
"time": 500
}
],
"2,8": [
"\t[老人,wizard]这些都是各种各样的怪物所有怪物的数据都在enemys.js中设置。",
"\t[老人,wizard]这批怪物分别为普通、先攻、魔攻、坚固、2连击、3连击、4连击、破甲、反击、净化。",
"\t[老人,wizard]打败怪物后可触发 afterBattle 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。",
"\t[少女,npc0]\b[this]这些是路障、楼梯、传送门。",
"\t[少女,npc1]\b[this]血网的伤害数值、中毒后每步伤害数值、衰弱时攻防下降的数值都在全塔属性快捷键B的全局数值values内定义。\n\n路障同样会尽量被自动寻路绕过。",
"\t[少女,npc2]\b[this]楼梯和传送门需要在地图选点快捷键X的“楼层转换”中定义目标楼层和位置可参见样板里已有的的写法。",
{
"type": "hide",
"time": 500
}
],
"2,5": [
"\t[老人,wizard]模仿、吸血、中毒、衰弱、诅咒。\n\n请注意吸血怪需要设置value为吸血数值可参见样板中黑暗大法师的写法。",
"\t[老人,wizard]\b[this]模仿、吸血、中毒、衰弱、诅咒。\n\n请注意吸血怪需要设置value为吸血数值可参见样板中黑暗大法师的写法。",
{
"type": "hide",
"time": 500
}
],
"2,3": [
"\t[老人,wizard]领域、夹击。\n请注意领域怪需要设置value为伤害数值可参见样板中初级巫师的写法。",
"\t[老人,wizard]夹击和领域同时发生时先计算领域,再夹击。\n自动寻路同样会尽量绕过你设置的这些点。",
"\t[老人,wizard]\b[this]领域、夹击。\n请注意领域怪需要设置value为伤害数值可参见样板中初级巫师的写法。",
"\t[老人,wizard]\b[this]夹击和领域同时发生时先计算领域,再夹击。\n自动寻路同样会尽量绕过你设置的这些点。",
{
"type": "hide",
"time": 500
}
],
"12,10": {
"trigger": null,
"enable": false,
"noPass": null,
"displayDamage": true,
"data": [
"\t[仙子,fairy]只有楼上启用事件后,才能看到我并可以和我对话来触发事件。",
"\t[仙子,fairy]\b[this]只有楼上启用事件后,才能看到我并可以和我对话来触发事件。",
{
"type": "hide",
"time": 500
}
]
}
},
"2,8": [
"\t[老人,wizard]\b[this]这些都是各种各样的怪物所有怪物的数据都在project文件夹的enemys.js中设置。",
"\t[老人,wizard]\b[this]这批怪物分别为普通、先攻、魔攻、坚固、2连击、3连击、4连击、破甲、反击、净化。",
"\t[老人,wizard]\b[this]打败怪物后可触发 afterBattle 事件。\n\n有关事件的各种信息在下一层会有更为详细的说明。",
{
"type": "hide",
"time": 500
}
]
},
"changeFloor": {
"6,0": {
@ -165,46 +168,46 @@ main.floors.sample0=
},
"afterBattle": {
"2,6": [
"\t[ghostSkeleton]不可能,你怎么可能打败我!\n一个打败怪物触发的事件"
"\t[ghostSoldier]\b[this]不可能,你怎么可能打败我!\n一个打败怪物触发的事件"
]
},
"afterGetItem": {
"11,8": [
"由于状态栏放不下,绿钥匙和铁门钥匙均视为tools放入工具栏中。\n碰到绿门和铁门仍然会自动使用开门。"
"由于状态栏放不下,铁门钥匙(根据全塔属性的系统开关勾选与否,可能还有绿钥匙)会被放入道具栏中。\n碰到绿门和铁门仍然会自动使用钥匙(根据全塔属性的系统开关勾选与否,铁门可能不需要钥匙)开门。"
],
"8,6": [
"由于吸血和夹击等的存在,血瓶默认自动被绕路。\n你可以修改data.js中的系统Flag来设置这一项。"
"由于吸血、夹击和净化等的存在,玩家可能希望自动寻路能尽量绕开血瓶和绿宝石,\n他们可以自行在游戏设置中开关这一功能。"
],
"8,7": [
"如需修改消耗品的效果,请前往 data.js 找到并修改values内对应的具体数值即可。\n如果有更高级的需求如每个区域宝石数值变化详见doc文档内的做法说明。"
"如需修改消耗品的效果,请前往全塔属性快捷键B找到并修改values全局数值内对应的具体数值即可。\n如果有高级的需求如每个区域宝石数值变化请修改楼层属性快捷键V最下方的“宝石血瓶效果”。\n如果有更高级的需求请阅读帮助文档。"
],
"9,5": [
"每层楼的 canFlyTo 决定了该楼层能否被飞到。\n\n不能被飞到的楼层也无法使用楼层传送器。",
"飞行的楼层顺序由 main.js 中 floorIds 加载顺序所决定。\n\n是否必须在楼梯边使用楼传器由 data.js 中的系统Flag所决定。"
"每层楼的“可楼传”勾选框决定了该楼层能否被飞到。\n\n勇士在不能被飞到的楼层也无法使用楼层传送器。",
"飞行的楼层顺序由全塔属性快捷键B中的“楼层列表”所决定。\n\n是否必须在楼梯边使用楼传器由全塔属性中的系统开关所决定。"
],
"10,5": [
"破墙镐是破面前的墙壁还是四个方向的墙壁,由data.js中的系统Flag所决定。"
"破墙镐是破面前的墙壁还是四个方向的墙壁,由其图块属性快捷键C的“使用效果”决定。\n哪些图块怪物和道具除外可以被破震由该图块的图块属性中的“可破震”决定。"
],
"8,4": [
"炸弹是只能炸面前的怪物还是四个方向的怪物,由data.js中的系统Flag所决定。\n如只能炸前方怪物则和上面的圣锤等价。\n不能被炸的怪物在enemys中可以定义,可参见样板里黑衣魔王和黑暗大法师的写法。"
"炸弹是只能炸面前的怪物还是四个方向的怪物,由其图块属性快捷键C中的“使用效果”决定。\n不能被炸的怪物请直接在该怪物的图块属性中勾选“不可炸”,可参见样板里黑衣魔王和黑暗大法师的写法。"
],
"10,4": [
"“上楼”和“下楼”的目标层由 main.js 的 floorIds顺序所决定。"
"“上楼”和“下楼”的目标层由全塔属性快捷键B的“楼层列表”顺序所决定。"
],
"9,2": [
"该道具默认是大黄门钥匙,如需改为钥匙盒直接修改 data.js 中的系统Flag即可。"
"该道具默认是大黄门钥匙,如需改为钥匙盒直接修改其图块属性快捷键C的“道具类别”为items即可。"
],
"10,2": [
"屠龙匕首目前未被定义,可能需要自行实现功能。\n有关如何实现一个道具功能参见doc文档。"
"屠龙匕首目前未被定义,可能需要自行实现功能。\n有关如何实现一个道具功能参见帮助文档。"
],
"12,7": [
"在 data.js 的系统Flag中设置是否启用装备栏。\n如果不启用则装备会直接增加属性。"
"剑盾的道具类别设为equips才可以装备\n如果设为items则会直接增加属性。"
],
"12,6": [
"在 data.js 的系统Flag中设置是否启用装备栏按钮。\n如果启用则装备栏按钮会替代楼传按钮。"
"在全塔属性快捷键B的系统开关中设置是否启用装备栏按钮。\n如果启用则装备栏按钮会替代楼传按钮。\n无论是否启用玩家都可以双击道具栏按钮呼出装备栏。"
],
"12,5": [
"装备的种类由全塔属性中的equipName决定,type的值就是该类型在equipName中的位次例如默认情况下equiptype为0代表武器同时只有type为0的装备的animate属性生效"
"装备的种类由全塔属性快捷键B中的“装备孔”决定每件装备的“类型”就是在“装备孔”中的索引\n例如默认情况下0代表武器。同时只有第一个装备孔中的装备其“普攻动画”属性才会生效。"
]
},
"afterOpenDoor": {

View File

@ -27,54 +27,37 @@ main.floors.sample1=
[152,152,152,152,121,152,152,152, 0, 0,229, 0, 0],
[ 43, 33, 44,151, 0, 0, 0,152,165,161, 0,163,165],
[ 21, 22, 21,151, 0, 0, 0,152,166,165, 0,165,166],
[151,245,151,151, 0, 87, 0,152,152,152, 85,153,153],
[ 0,246, 0,151, 0, 0, 0,152,152,221, 0,221,153],
[246, 0,246,151, 0, 0, 0,121, 85, 0, 0, 0,153],
[151,246,151,151, 0,153,153,153,153,153,153,153,153],
[151, 0,151,151, 0, 87, 0,152,152,152, 85,153,153],
[ 0, 0, 0,151, 0, 0, 0,152,152,221, 0,221,153],
[ 0, 0, 0,151, 0, 0, 0,121, 0, 0, 0, 0,153],
[151, 0,151,151, 0,153,153,153,153,153,153,153,153],
[ 0, 0, 0, 0, 0, 0, 0,164, 0, 0,163, 0, 0],
[ 1, 1, 1, 1, 0, 20, 0, 0, 0,162, 0,161, 0],
[ 1, 0,123, 1, 0, 20,124, 0,121, 0,122, 0,126],
[ 1, 0, 0, 1, 88, 20, 86, 0, 0, 0, 0, 0, 0]
[ 1, 0, 0, 1, 88, 20, 0, 0, 0, 0, 0, 0, 0]
],
"firstArrive": [],
"events": {
"4,10": [
"\t[样板提示]本层楼将会对各类事件进行介绍。",
"左边是一个仿50层的陷阱做法上方是商店、快捷商店的使用方法右上是一个典型的杀怪开门的例子右下是各类可能的NPC事件。",
"左边是一个仿51层的陷阱做法上方是商店、快捷商店的使用方法右上是一个典型的杀怪开门的例子右下是各类可能的NPC事件。",
"本样板目前支持的事件列表大致有:\ntext: 显示一段文字(比如你现在正在看到的)\ntip: 左上角显示提示\nshow: 使一个事件有效(可见、可被交互)\nhide: 使一个事件失效(不可见、不可被交互)\ntrigger: 触发另一个地点的事件\nanimate: 显示动画\nbattle: 强制和某怪物战斗\nopenDoor: 无需钥匙开门(例如机关门、暗墙)",
"openShop: 打开一个全局商店\ndisableShop: 禁用一个全局商店\nchangeFloor: 传送勇士到某层某位置\nchangePos: 传送勇士到当层某位置;转向\nshowImage: 显示图片\nsetFg: 更改画面色调\nsetWeather: 更改天气\nmove: 移动事件效果\nmoveHero: 移动勇士效果\nplayBgm: 播放某个背景音乐\npauseBgm: 暂停背景音乐\nresumeBgm: 恢复背景音乐的播放\nplaySound: 播放某个音频",
"openShop: 打开一个全局商店\ndisableShop: 禁用一个全局商店\nchangeFloor: 传送勇士到某层某位置\nchangePos: 传送勇士到当层某位置;转向\nshowImage: 显示图片\nsetCurtain: 更改画面色调\nsetWeather: 更改天气\nmove: 移动事件效果\nmoveHero: 移动勇士效果\nplayBgm: 播放某个背景音乐\npauseBgm: 暂停背景音乐\nresumeBgm: 恢复背景音乐的播放\nplaySound: 播放某个音频",
"if: 条件判断\nchoices: 提供选项\nsetValue: 设置勇士属性道具,或某个变量/flag\nupdate: 更新状态栏和地图显伤\nwin: 获得胜利(游戏通关)\nlose: 游戏失败\nsleep: 等待多少毫秒\nexit: 立刻结束当前事件\nfunction: 自定义JS脚本\n\n更多支持的事件还在编写中欢迎您宝贵的意见。",
"有关各事件的样例可参见本层一些NPC的写法。\n所有事件样例本层都有介绍。\n\n一个自定义事件处理完后需要调用{\"type\": \"hide\"}该事件才不会再次出现。",
{
"type": "hide"
}
],
"1,5": {
"enable": false,
"data": []
},
"1,6": {
"enable": false,
"data": []
},
"0,7": {
"enable": false,
"data": []
},
"2,7": {
"enable": false,
"data": []
},
"1,8": {
"enable": false,
"data": []
},
"1,7": [
{
"type": "show",
"type": "setBlock",
"number": "redKing",
"loc": [
1,
5
[
1,
5
]
],
"time": 1500
},
@ -82,9 +65,10 @@ main.floors.sample1=
"type": "sleep",
"time": 500
},
"\t[redKing]欢迎来到魔塔,你是第一百位挑战者。\n若你能打败我所有的手下我就与你一对一的决斗。\n现在你必须接受我的安排。",
"\t[redKing]\b[this,1,5]欢迎来到魔塔,你是第一百位挑战者。\n若你能打败我所有的手下我就与你一对一的决斗。\n现在你必须接受我的安排。",
{
"type": "show",
"type": "setBlock",
"number": "blueKing",
"loc": [
[
1,
@ -105,10 +89,11 @@ main.floors.sample1=
],
"time": 500
},
"\t[hero]什么?",
"\t[hero]\b[hero]什么?",
{
"type": "playSound",
"name": "attack.mp3"
"type": "animate",
"name": "hand",
"loc": "hero"
},
{
"type": "setValue",
@ -141,13 +126,16 @@ main.floors.sample1=
1,
8
]
]
],
"time": 500
},
{
"type": "hide",
"loc": [
1,
5
[
1,
5
]
],
"time": 500
},
@ -186,13 +174,13 @@ main.floors.sample1=
}
],
"2,11": [
"\t[杰克,thief]喂!醒醒!快醒醒!",
"\t[杰克,thief]\b[this]喂!醒醒!快醒醒!",
{
"type": "setCurtain",
"time": 1500
},
"\t[hero]额,我这是在什么地方?",
"\t[杰克,thief]你被魔王抓了起来扔进了监狱,和我关在了一起,但是幸运的是我在昨天刚刚挖好一条越狱的暗道!",
"\t[hero]\b[hero]额,我这是在什么地方?",
"\t[杰克,thief]\b[this]你被魔王抓了起来扔进了监狱,和我关在了一起,但是幸运的是我在昨天刚刚挖好一条越狱的暗道!",
{
"type": "openDoor",
"loc": [
@ -204,7 +192,7 @@ main.floors.sample1=
"type": "sleep",
"time": 300
},
"\t[杰克,thief]我先走了,祝你好运!",
"\t[杰克,thief]\b[this]我先走了,祝你好运!",
{
"type": "move",
"time": 750,
@ -215,14 +203,14 @@ main.floors.sample1=
]
},
"上面是个move事件可以对NPC等进行移动。\n详见样板中小偷事件的写法。",
"\t[hero]怎么跑的这么快..."
"\t[hero]\b[hero]怎么跑的这么快..."
],
"4,2": [
"\t[老人,man]本塔的商店有两类,全局商店和非全局商店。\n\n所谓非全局商店就类似于右下角那个卖钥匙的老人一样一定要碰到才能触发事件。\n\n而全局商店则能在快捷商店中直接使用。",
"\t[老人,man]要注册一个全局商店,你需要在 data.js 中,找到 shops,并在内添加你的商店信息。",
"\t[老人,man]商店信息添加后,可以在需要的事件处调用{\"type\": \"openShop\"}来打开你添加的全局商店。",
"\t[老人,man]在上面的例子里左边是一个仿50层的金币商店右边是一个仿24层的经验商店。\n\n商店被访问后即可在快捷商店中进行使用。",
"\t[老人,man]如果你需要在某层暂时禁用快捷商店可以在data.js中设置cannotUseQuickShop。\n如果需要永久禁用商店,请使用{\"type\":\"disableShop\"}",
"\t[老人,man]\b[this]本塔的商店有两类,全局商店和非全局商店。\n\n所谓非全局商店就类似于右下角那个卖钥匙的老人一样一定要碰到才能触发事件。\n\n而全局商店则能在快捷商店中直接使用。",
"\t[老人,man]\b[this]要注册一个全局商店,你需要在全塔属性中,找到“全局商店”,并在内添加你的商店信息。",
"\t[老人,man]\b[this]商店信息添加后,可以在需要的事件处调用{\"type\": \"openShop\"}来打开你添加的全局商店。",
"\t[老人,man]\b[this]在上面的例子里左边是一个仿51层的金币商店右边是一个仿24层的经验商店。\n\n商店被访问后即可在快捷商店中进行使用。",
"\t[老人,man]\b[this]如果你需要在某层禁用快捷商店,可以在其楼层属性中设置“快捷商店”。\n如果需要永久禁用商店直到重新通过触碰NPC打开,请使用{\"type\":\"disableShop\"}",
{
"type": "hide",
"time": 500
@ -243,18 +231,17 @@ main.floors.sample1=
}
],
"7,7": [
"\t[老人,man]这是一个典型的杀怪开门、强制战斗事件。",
"\t[老人,man]\b[this]这是一个典型的杀怪开门、强制战斗事件。",
"\t[老人,man]\b[this]下面的那四个箭头表示单向通行,画在任何一个图层都有效。",
{
"type": "hide"
"type": "hide",
"time": 500
}
],
"8,7": {
"enable": false,
"data": []
},
"9,7": [
{
"type": "show",
"type": "closeDoor",
"id": "specialDoor",
"loc": [
8,
7
@ -265,16 +252,12 @@ main.floors.sample1=
}
],
"10,4": [
"\t[blackMS]你终于还是来了。",
"\t[hero]放开我们的公主!",
"\t[blackMS]如果我不愿意呢?",
"\t[hero]无需多说,拔剑吧!",
"\t[blackKing]\b[this]你终于还是来了。",
"\t[hero]\b[hero]放开我们的公主!",
"\t[blackKing]\b[this]如果我不愿意呢?",
"\t[hero]\b[hero]无需多说,拔剑吧!",
{
"type": "battle",
"id": "blackMS"
},
{
"type": "hide",
"loc": [
10,
2
@ -287,34 +270,31 @@ main.floors.sample1=
7
]
},
"\t[blackMS]没想到你已经变得这么强大了... 算你厉害。\n公主就交给你了请好好对她。",
"\t[blackKing]没想到你已经变得这么强大了... 算你厉害。\n公主就交给你了请好好对她。",
{
"type": "hide"
}
],
"10,0": [
"\t[hero]公主,我来救你了~",
"\t[公主,princess]快救我出去!我受够这里了!",
"\t[hero]公主别怕,我们走吧~",
"\t[hero]\b[hero]公主,我来救你了~",
"\t[公主,princess]\b[this]快救我出去!我受够这里了!",
"\t[hero]\b[hero]公主别怕,我们走吧~",
{
"type": "win",
"reason": "救出公主"
}
],
"6,12": {
"enable": false,
"data": []
},
"6,11": [
"\t[仙子,fairy]通过调用 {\"type\": \"show\"} 可以使隐藏的事件显示出来。\n比如我下面这个机关门。",
"\t[仙子,fairy]\b[this]通过调用 {\"type\": \"closeDoor\"} 可以在空地关上一扇门或墙。\n比如我下面这个机关门。",
{
"type": "show",
"type": "closeDoor",
"id": "steelDoor",
"loc": [
6,
12
]
},
"\t[仙子,fairy]通过调用 {\"type\": \"openDoor\"} 可以无需钥匙打开一扇门或暗墙。",
"\t[仙子,fairy]\b[this]通过调用 {\"type\": \"openDoor\"} 可以无需钥匙打开一扇门或暗墙。",
{
"type": "openDoor",
"loc": [
@ -322,7 +302,7 @@ main.floors.sample1=
12
]
},
"\t[仙子,fairy]同时,也可以对其它层进行操作,比如楼下的机关门,现在已经为你打开了。",
"\t[仙子,fairy]\b[this]同时,也可以对其它层进行操作,比如楼下的机关门,现在已经为你打开了。",
{
"type": "openDoor",
"loc": [
@ -331,13 +311,15 @@ main.floors.sample1=
],
"floorId": "sample0"
},
"\t[仙子,fairy]如果 show 或 hide 指定了 time 参数,则以动画效果显示,指定的参数作为消失时间(毫秒)来计算。",
"\t[仙子,fairy]现在到楼下来找我吧~",
"\t[仙子,fairy]\b[this]如果当前楼层的 show 或 hide 指定了 time 参数,则以动画效果显示,指定的参数作为淡入淡出时间(毫秒)来计算。",
"\t[仙子,fairy]\b[this]现在到楼下来找我吧~",
{
"type": "show",
"loc": [
12,
10
[
12,
10
]
],
"floorId": "sample0"
},
@ -353,10 +335,10 @@ main.floors.sample1=
"operator": "+=",
"value": "1"
},
"\t[老人,man]在文字中使用$+{}可以计算并显示一个表达式的结果。\n",
"\t[老人,man]例如:\n你的当前攻击力是${status:atk},防御力是${status:def}。\n攻防和的十倍是${10*(status:atk+status:def)},攻防之积是${status:atk*status:def}。\n你有${item:yellowKey}把黄钥匙,${item:blueKey}把蓝钥匙,${item:redKey}把红钥匙。\n你有${item:pickaxe}个破,${item:bomb}个炸,${item:centerFly}个飞。\n这是你第${flag:man_times}次和我对话。",
"\t[老人,man]同时,你也可以通过{\"type\": \"setValue\"}来设置一个勇士的属性、道具或某个Flag。",
"\t[老人,man]例如:\n现在我将让你的攻防提升50%,再将攻防和的十倍加到生命值上。",
"\t[老人,man]\b[this]在文字中使用$+{}可以计算并显示一个表达式的结果。\n",
"\t[老人,man]\b[this]例如:\n你的当前攻击力是${status:atk},防御力是${status:def}。\n攻防和的十倍是${10*(status:atk+status:def)},攻防之积是${status:atk*status:def}。\n你有${item:yellowKey}把黄钥匙,${item:blueKey}把蓝钥匙,${item:redKey}把红钥匙。\n你有${item:pickaxe}个破,${item:bomb}个炸,${item:centerFly}个飞。\n这是你第${flag:man_times}次和我对话。",
"\t[老人,man]\b[this]同时,你也可以通过{\"type\": \"setValue\"}来设置一个勇士的属性、道具或某个Flag。",
"\t[老人,man]\b[this]例如:\n现在我将让你的攻防提升50%,再将攻防和的十倍加到生命值上。",
{
"type": "setValue",
"name": "status:atk",
@ -375,7 +357,7 @@ main.floors.sample1=
"operator": "+=",
"value": "10*(status:atk+status:def)"
},
"\t[老人,man]再送你500金币1000经验1破2炸3飞",
"\t[老人,man]\b[this]再送你500金币1000经验1破2炸3飞",
{
"type": "setValue",
"name": "status:money",
@ -406,8 +388,8 @@ main.floors.sample1=
"operator": "+=",
"value": "3"
},
"\t[老人,man]status:xxx 代表勇士的某个属性。\n其中xxx可取hp, atk, def, mdef, money,exp这几项。\n\nitem:xxx 代表勇士的某个道具的个数。\nxxx为道具ID具体可参见items.js中的定义。\n\nflag:xxx 代表某个自定义Flag或变量。\nxxx为Flag/变量名,可以自行定义,由字母、数字和下划线组成。\n未定义过而直接取用的Flag默认值为false。",
"\t[老人,man]你现在可以重新和我进行对话,进一步看到属性值的改变。"
"\t[老人,man]\b[this]status:xxx 代表勇士的某个属性。\n其中xxx可取生命、攻击、防御、护盾、金币、经验等很多项。\n\nitem:xxx 代表勇士的某个道具的个数。\nxxx为道具ID具体可参见items.js中的定义。\n\nflag:xxx 代表某个自定义Flag或变量。\nxxx为Flag/变量名,可以自行定义,由字母、数字和下划线甚至中文组成。\n未定义过而直接取用的Flag默认值为0.",
"\t[老人,man]\b[this]你现在可以重新和我进行对话,进一步看到属性值的改变。"
],
"10,11": [
{
@ -562,15 +544,15 @@ main.floors.sample1=
}
],
"12,11": [
"\t[老人,recluse]使用 {\"type\":\"function\"} 可以写自定义的JS脚本。\n本塔支持的所有主要API会在doc文档内给出。",
"\t[老人,recluse]例如这个例子:即将弹出一个输入窗口,然后会将你的输入结果直接加到你的攻击力上。",
"\t[老人,recluse]\b[this]使用 {\"type\":\"input\"} 可以弹窗请求玩家输入数字",
"\t[老人,recluse]\b[this]例如这个例子:即将弹出一个输入窗口,然后会将你的输入结果直接加到你的攻击力上。",
{
"type": "input",
"text": "请输入你要加攻击力的数值:"
},
{
"type": "if",
"condition": "flag:input>0",
"condition": "(flag:input>0)",
"true": [
{
"type": "setValue",
@ -586,7 +568,7 @@ main.floors.sample1=
],
"false": []
},
"\t[老人,recluse]具体可参见样板中本事件的写法。"
"\t[老人,recluse]\b[this]具体可参见样板中本事件的写法。"
]
},
"changeFloor": {
@ -644,7 +626,8 @@ main.floors.sample1=
"type": "openDoor"
}
]
}
},
"1": null
}
},
"width": 13,

BIN
project/fonts/number.ttf Normal file

Binary file not shown.

View File

@ -15,6 +15,7 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
core.status.played = true;
// 初始化人物,图标,统计信息
core.status.hero = core.clone(hero);
window.hero = core.status.hero;
window.flags = core.status.hero.flags;
core.events.setHeroIcon(core.status.hero.image, true);
core.control._initStatistics(core.animateFrame.totalTime);
@ -119,6 +120,7 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
core.status.maps[floorId].blocks.forEach(function (block) {
if (block.disable && core.enemys.hasSpecial(block.event.id, 23)) {
block.disable = false;
core.setFlag([floorId, block.x, block.y, 'md'].join('@'), false);
}
});
core.control.gatherFollowers();
@ -126,6 +128,10 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
// ---------- 重绘新地图这一步将会设置core.status.floorId ---------- //
core.drawMap(floorId);
// item_ratio兼容性...
if (core.status.thisMap.ratio == null && core.status.thisMap.item_ratio != null) {
core.status.thisMap.ratio = core.status.thisMap.item_ratio;
}
// 切换楼层BGM
if (core.status.maps[floorId].bgm) {
@ -188,6 +194,9 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
if (core.flags.flyRecordPosition) {
loc = core.getFlag("__leaveLoc__", {})[toId] || null;
}
if (core.status.maps[toId].flyPoint != null && core.status.maps[toId].flyPoint.length == 2) {
loc = {x: core.status.maps[toId].flyPoint[0], y: core.status.maps[toId].flyPoint[1]};
}
if (loc == null) {
// 获得两个楼层的索引,以决定是上楼梯还是下楼梯
var fromIndex = core.floorIds.indexOf(fromId),
@ -219,7 +228,7 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
if (guards.length > 0) {
// 记录flag当前要参与支援的怪物
core.setFlag("__guards__" + x + "_" + y, guards);
var actions = [];
var actions = [{ "type": "playSound", "name": "jump.mp3" }];
// 增加支援的特效动画(图块跳跃)
guards.forEach(function (g) {
core.push(actions, { "type": "jump", "from": [g[0], g[1]], "to": [x, y], "time": 300, "keep": false, "async": true });
@ -353,7 +362,9 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
}
// 如果有加点
var point = core.material.enemys[enemyId].point;
var point = guards.reduce(function (curr, g) {
return curr + core.material.enemys[g[2]].point;
}, enemy.point) || 0;
if (core.flags.enableAddPoint && point > 0) {
core.push(todo, [{ "type": "insert", "name": "加点事件", "args": [point] }]);
}
@ -427,40 +438,42 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
}
*/
}
},
}
},
"enemys": {
"getSpecials": function () {
// 获得怪物的特殊属性,每一行定义一个特殊属性。
// 分为三项,第一项为该特殊属性的数字,第二项为特殊属性的名字,第三项为特殊属性的描述
// 可以直接写字符串也可以写个function将怪物传进去
// 分为五项,第一项为该特殊属性的数字,第二项为特殊属性的名字,第三项为特殊属性的描述
// 第四项为该特殊属性的颜色,可以写十六进制 #RRGGBB 或者 [r,g,b,a] 四元数组
// 第五项为该特殊属性的标记;目前 1 代表是地图类技能(需要进行遍历全图)
// 名字和描述可以直接写字符串也可以写个function将怪物传进去
return [
[1, "先攻", "怪物首先攻击"],
[2, "魔攻", "怪物无视勇士的防御"],
[3, "坚固", "怪物防御不小于勇士攻击-1"],
[2, "魔攻", "怪物无视勇士的防御", "#b6b0ff"],
[3, "坚固", "怪物防御不小于勇士攻击-1", "#b9822d"],
[4, "2连击", "怪物每回合攻击2次"],
[5, "3连击", "怪物每回合攻击3次"],
[6, function (enemy) { return (enemy.n || '') + "连击"; }, function (enemy) { return "怪物每回合攻击" + (enemy.n || 4) + "次"; }],
[7, "破甲", "战斗前,怪物附加角色防御的" + Math.floor(100 * core.values.breakArmor || 0) + "%作为伤害"],
[8, "反击", "战斗时,怪物每回合附加角色攻击的" + Math.floor(100 * core.values.counterAttack || 0) + "%作为伤害,无视角色防御"],
[9, "净化", "战斗前,怪物附加勇士护盾的" + core.values.purify + "倍作为伤害"],
[10, "模仿", "怪物的攻防和勇士攻防相等"],
[11, "吸血", function (enemy) { return "战斗前,怪物首先吸取角色的" + Math.floor(100 * enemy.value || 0) + "%生命(约" + Math.floor((enemy.value || 0) * core.getStatus('hp')) + "点)作为伤害" + (enemy.add ? ",并把伤害数值加到自身生命上" : ""); }],
[12, "中毒", "战斗后,勇士陷入中毒状态,每一步损失生命" + core.values.poisonDamage + "点"],
[13, "衰弱", "战斗后,勇士陷入衰弱状态,攻防暂时下降" + (core.values.weakValue >= 1 ? core.values.weakValue + "点" : parseInt(core.values.weakValue * 100) + "%")],
[14, "诅咒", "战斗后,勇士陷入诅咒状态,战斗无法获得金币和经验"],
[7, "破甲", function (enemy) { return "战斗前,怪物附加角色防御的" + Math.floor(100 * (enemy.defValue || core.values.breakArmor || 0)) + "%作为伤害"; }, "#b30000"],
[8, "反击", function (enemy) { return "战斗时,怪物每回合附加角色攻击的" + Math.floor(100 * (enemy.atkValue || core.values.counterAttack || 0)) + "%作为伤害,无视角色防御"; }, "#bd26ce"],
[9, "净化", function (enemy) { return "战斗前,怪物附加勇士护盾的" + (enemy.n || core.values.purify) + "倍作为伤害"; }, "#00d2d4"],
[10, "模仿", "怪物的攻防和勇士攻防相等", "#ff00d2"],
[11, "吸血", function (enemy) { return "战斗前,怪物首先吸取角色的" + Math.floor(100 * enemy.value || 0) + "%生命(约" + Math.floor((enemy.value || 0) * core.getStatus('hp')) + "点)作为伤害" + (enemy.add ? ",并把伤害数值加到自身生命上" : ""); }, "#ff00d2"],
[12, "中毒", "战斗后,勇士陷入中毒状态,每一步损失生命" + core.values.poisonDamage + "点", "#4aff60"],
[13, "衰弱", "战斗后,勇士陷入衰弱状态,攻防暂时下降" + (core.values.weakValue >= 1 ? core.values.weakValue + "点" : parseInt(core.values.weakValue * 100) + "%"), "#feccd0"],
[14, "诅咒", "战斗后,勇士陷入诅咒状态,战斗无法获得金币和经验", "#747dff"],
[15, "领域", function (enemy) { return "经过怪物周围" + (enemy.zoneSquare ? "九宫格" : "十字") + "范围内" + (enemy.range || 1) + "格时自动减生命" + (enemy.value || 0) + "点"; }],
[16, "夹击", "经过两只相同的怪物中间,勇士生命值变成一半"],
[16, "夹击", "经过两只相同的怪物中间,勇士生命值变成一半", "#ff00d2"],
[17, "仇恨", "战斗前,怪物附加之前积累的仇恨值作为伤害;战斗后,释放一半的仇恨值。(每杀死一个怪物获得" + (core.values.hatred || 0) + "点仇恨值)"],
[18, "阻击", function (enemy) { return "经过怪物的十字领域时自动减生命" + (enemy.value || 0) + "点,同时怪物后退一格"; }],
[19, "自爆", "战斗后勇士的生命值变成1"],
[20, "无敌", "勇士无法打败怪物,除非拥有十字架"],
[21, "退化", function (enemy) { return "战斗后勇士永久下降" + (enemy.atkValue || 0) + "点攻击和" + (enemy.defValue || 0) + "点防御"; }],
[19, "自爆", "战斗后勇士的生命值变成1", "#ff0000"],
[20, "无敌", "勇士无法打败怪物,除非拥有十字架", "#fbff00"],
[21, "退化", function (enemy) { return "战斗后勇士永久下降" + (enemy.atkValue || 0) + "点攻击和" + (enemy.defValue || 0) + "点防御"; }, "#ff0000"],
[22, "固伤", function (enemy) { return "战斗前,怪物对勇士造成" + (enemy.damage || 0) + "点固定伤害,无视勇士护盾。"; }],
[23, "重生", "怪物被击败后,角色转换楼层则怪物将再次出现"],
[24, "激光", function (enemy) { return "经过怪物同行或同列时自动减生命" + (enemy.value || 0) + "点"; }],
[25, "光环", function (enemy) { return "同楼层所有怪物生命提升" + (enemy.value || 0) + "%,攻击提升" + (enemy.atkValue || 0) + "%,防御提升" + (enemy.defValue || 0) + "%" + (enemy.add ? "可叠加" : "不可叠加"); }],
[26, "支援", "当周围一圈的怪物受到攻击时将上前支援,并组成小队战斗。"],
[25, "光环", function (enemy) { return "同楼层所有怪物生命提升" + (enemy.value || 0) + "%,攻击提升" + (enemy.atkValue || 0) + "%,防御提升" + (enemy.defValue || 0) + "%" + (enemy.add ? "可叠加" : "不可叠加"); }, "#fff900", 1],
[26, "支援", "当周围一圈的怪物受到攻击时将上前支援,并组成小队战斗。", "#fff900", 1],
[27, "捕捉", "当走到怪物周围十字时会强制进行战斗。"]
];
},
@ -497,26 +510,19 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
mon_def = hero_atk - 1;
}
// ------ 支援 ------
var guards = [];
// 光环检查
// 在这里判定是否需要遍历全图(由于光环需要遍历全图,应尽可能不需要以减少计算量,尤其是大地图)
var query = function () {
var floorIds = ["MTx"]; // 在这里给出所有需要遍历的楼层(即有光环或支援等)
return core.inArray(floorIds, floorId); // 也可以写其他的判定条件
}
// 光环和支援检查
if (!core.status.checkBlock) core.status.checkBlock = {};
if (query()) {
if (core.status.checkBlock.needCache || floorId != core.status.floorId) {
// 从V2.5.4开始,对光环效果增加缓存,以解决多次重复计算的问题,从而大幅提升运行效率。
// 检查当前楼层所有光环怪物数字25
var hp_buff = 0,
atk_buff = 0,
def_buff = 0,
cnt = 0;
// 检查光环缓存
// 检查光环和支援的缓存
var index = x != null && y != null ? (x + "," + y) : "floor";
if (!core.status.checkBlock) core.status.checkBlock = {};
if (!core.status.checkBlock.cache) core.status.checkBlock.cache = {};
var cache = core.status.checkBlock.cache[index];
if (!cache) {
@ -527,17 +533,27 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
// 获得该图块的ID
var id = block.event.id,
enemy = core.material.enemys[id];
// 检查是不是怪物,且是否拥有该特殊属性
// 检查【光环】技能数字25
if (enemy && core.hasSpecial(enemy.special, 25)) {
// 检查是否是范围光环
var inRange = enemy.range == null;
if (enemy.range != null && x != null && y != null) {
var dx = Math.abs(block.x - x),
dy = Math.abs(block.y - y);
// 检查十字和九宫格光环
if (dx + dy <= enemy.range) inRange = true;
if (enemy.zoneSquare && dx <= enemy.range && dy <= enemy.range) inRange = true;
}
// 检查是否可叠加
if (enemy.add || cnt == 0) {
if (inRange && (enemy.add || cnt == 0)) {
hp_buff += enemy.value || 0;
atk_buff += enemy.atkValue || 0;
def_buff += enemy.defValue || 0;
cnt++;
}
}
// 检查【支援】技能
// 检查【支援】技能数字26
if (enemy && core.hasSpecial(enemy.special, 26) &&
// 检查支援条件坐标存在距离为1且不能是自己
// 其他类型的支援怪,比如十字之类的话.... 看着做是一样的
@ -547,6 +563,7 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
}
// TODO如果有其他类型光环怪物在这里仿照添加检查
// 注新增新的类光环属性需要遍历全图的需要在特殊属性定义那里的第五项写1参见光环和支援的特殊属性定义。
}
});
@ -658,18 +675,19 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
// 每回合的反击伤害;反击是按照勇士的攻击次数来计算回合
var counterDamage = 0;
if (core.hasSpecial(mon_special, 8)) counterDamage += Math.floor(core.values.counterAttack * hero_atk);
if (core.hasSpecial(mon_special, 8))
counterDamage += Math.floor((enemy.atkValue || core.values.counterAttack) * hero_atk);
// 先攻
if (core.hasSpecial(mon_special, 1)) init_damage += per_damage;
// 破甲
if (core.hasSpecial(mon_special, 7))
init_damage += Math.floor(core.values.breakArmor * hero_def);
init_damage += Math.floor((enemy.defValue || core.values.breakArmor) * hero_def);
// 净化
if (core.hasSpecial(mon_special, 9))
init_damage += Math.floor(core.values.purify * hero_mdef);
init_damage += Math.floor((enemy.n || core.values.purify) * hero_mdef);
// 勇士每回合对怪物造成的伤害
var hero_per_damage = Math.max(hero_atk - mon_def, 0);
@ -933,7 +951,7 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
// 读档操作;从存储中读取了内容后的行为
// 重置游戏和路线
core.resetGame(data.hero, data.hard, data.floorId, core.maps.loadMap(data.maps), data.values);
core.resetGame(data.hero, data.hard, data.floorId, core.maps.loadMap(data.maps, null, data.hero.flags), data.values);
core.status.route = core.decodeRoute(data.route);
// 文字属性,全局属性
core.status.textAttribute = core.getFlag('textAttribute', core.status.textAttribute);
@ -1060,6 +1078,9 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
type = {}, // 每个点的伤害类型
repulse = {}, // 每个点的阻击怪信息
ambush = {}; // 每个点的捕捉信息
var needCache = false;
var canGoDeadZone = core.flags.canGoDeadZone;
core.flags.canGoDeadZone = true;
// 计算血网和领域、阻击、激光的伤害,计算捕捉信息
for (var loc in blocks) {
@ -1116,9 +1137,9 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
var rdir = core.turnDirection(":back", dir);
// 检查下一个点是否存在事件(从而判定是否移动)
var rnx = x + core.utils.scan[rdir].x,
var rnx = x + core.utils.scan[rdir].x,
rny = y + core.utils.scan[rdir].y;
if (rnx >= 0 && rnx < width && rny >= 0 && rny < height && core.getBlock(rnx, rny, floorId) == null) {
if (core.canMoveHero(x, y, rdir, floorId) && core.getBlock(rnx, rny, floorId) == null) {
repulse[currloc] = (repulse[currloc] || []).concat([
[x, y, id, rdir]
]);
@ -1161,6 +1182,10 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
]);
}
}
// 检查地图范围类技能
var specialFlag = core.getSpecialFlag(enemy);
if (specialFlag & 1) needCache = true;
}
// 更新夹击伤害
@ -1170,7 +1195,8 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
for (var y = 0; y < height; y++) {
var loc = x + "," + y;
// 夹击怪物的ID
var enemyId1 = null, enemyId2 = null;
var enemyId1 = null,
enemyId2 = null;
// 检查左右夹击
var leftBlock = blocks[(x - 1) + "," + y],
rightBlock = blocks[(x + 1) + "," + y];
@ -1211,11 +1237,13 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a =
}
}
core.flags.canGoDeadZone = canGoDeadZone;
core.status.checkBlock = {
damage: damage,
type: type,
repulse: repulse,
ambush: ambush,
needCache: needCache,
cache: {} // clear cache
};
},

View File

@ -183,15 +183,10 @@ var icons_4665ee12_3a1f_44a4_bea3_0fccba634dc1 =
"goldSlimelord": 61,
"whiteSlimeman": 54,
"slimeman": 15,
"yellowGT": 20,
"blueGT": 21,
"redGT": 22,
"blackMS": 28,
"yellowMS": 29,
"greenMS": 30,
"yellowGateKeeper": 20,
"blueGateKeeper": 21,
"redGateKeeper": 22,
"magicMaster": 46,
"blueMS": 45,
"redMS": 44,
"devilWarrior": 41,
"fairyEnemy": 58,
"dragon": 56,
@ -208,15 +203,20 @@ var icons_4665ee12_3a1f_44a4_bea3_0fccba634dc1 =
"greenKnight": 65,
"bowman": 66,
"liteBowman": 67,
"crismonZombie": 68,
"crimsonZombie": 68,
"watcherSlime": 70,
"mutantSlimeman": 71,
"frostBat": 72,
"devilKnight": 73,
"grayPriest": 74,
"greenGT": 75,
"greenGateKeeper": 75,
"ghostSoldier": 11,
"evilHero": 40
"evilHero": 40,
"blackKing": 28,
"yellowKing": 29,
"greenKing": 30,
"redKing": 44,
"blueKing": 45
},
"enemy48": {
"angel": 0,

View File

@ -296,7 +296,10 @@ var items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a =
"cls": "items",
"name": "圣水",
"itemEffect": "core.status.hero.hp *= 2",
"itemEffectTip": ",生命值翻倍"
"itemEffectTip": ",生命值翻倍",
"useItemEffect": "core.status.hero.hp *= 2;",
"canUseItemEffect": "true",
"text": "生命值翻倍"
},
"silverCoin": {
"cls": "items",
@ -495,7 +498,7 @@ var items_296f5d02_12fd_4166_a7c1_b5e830c9ee3a =
"cls": "tools",
"name": "跳跃靴",
"text": "能跳跃到前方两格处",
"useItemEffect": "core.insertAction({ \"type\": \"jumpHero\", \"loc\": [core.nextX(2), core.nextY(2)] });",
"useItemEffect": "core.playSound(\"jump.mp3\"); core.insertAction({ \"type\": \"jumpHero\", \"loc\": [core.nextX(2), core.nextY(2)] });",
"canUseItemEffect": "(function () {\n\tvar nx = core.nextX(2),\n\t\tny = core.nextY(2);\n\treturn nx >= 0 && nx < core.bigmap.width && ny >= 0 && ny < core.bigmap.height && core.getBlockId(nx, ny) == null;\n})();"
},
"skill1": {

View File

@ -160,17 +160,17 @@ var maps_90f36752_8815_4be8_b32b_d7fad1d0542e =
"218": {"cls":"enemys","id":"redPriest"},
"219": {"cls":"enemys","id":"brownWizard"},
"220": {"cls":"enemys","id":"redWizard"},
"221": {"cls":"enemys","id":"yellowGT"},
"222": {"cls":"enemys","id":"blueGT"},
"223": {"cls":"enemys","id":"redGT"},
"221": {"cls":"enemys","id":"yellowGateKeeper"},
"222": {"cls":"enemys","id":"blueGateKeeper"},
"223": {"cls":"enemys","id":"redGateKeeper"},
"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":"blackMS"},
"230": {"cls":"enemys","id":"yellowMS"},
"231": {"cls":"enemys","id":"greenMS"},
"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"},
@ -184,8 +184,8 @@ var maps_90f36752_8815_4be8_b32b_d7fad1d0542e =
"242": {"cls":"enemys","id":"devilWarrior"},
"243": {"cls":"enemys","id":"demonPriest"},
"244": {"cls":"enemys","id":"goldHornSlime"},
"245": {"cls":"enemys","id":"redMS"},
"246": {"cls":"enemys","id":"blueMS"},
"245": {"cls":"enemys","id":"redKing"},
"246": {"cls":"enemys","id":"blueKing"},
"247": {"cls":"enemys","id":"magicMaster"},
"248": {"cls":"enemys","id":"silverSlime"},
"249": {"cls":"enemys","id":"blademaster"},
@ -212,14 +212,14 @@ var maps_90f36752_8815_4be8_b32b_d7fad1d0542e =
"270": {"cls":"enemys","id":"greenKnight"},
"271": {"cls":"enemys","id":"bowman"},
"272": {"cls":"enemys","id":"liteBowman"},
"273": {"cls":"enemys","id":"crismonZombie"},
"273": {"cls":"enemys","id":"crimsonZombie"},
"274": {"cls":"enemys","id":"frozenSkeleton"},
"275": {"cls":"enemys","id":"watcherSlime"},
"276": {"cls":"enemys","id":"mutantSlimeman"},
"277": {"cls":"enemys","id":"frostBat"},
"278": {"cls":"enemys","id":"devilKnight"},
"279": {"cls":"enemys","id":"grayPriest"},
"280": {"cls":"enemys","id":"greenGT"},
"280": {"cls":"enemys","id":"greenGateKeeper"},
"300": {"cls":"terrains","id":"ground"},
"301": {"cls":"terrains","id":"grass"},
"302": {"cls":"terrains","id":"grass2"},

Binary file not shown.

Before

Width:  |  Height:  |  Size: 34 KiB

After

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 69 KiB

After

Width:  |  Height:  |  Size: 68 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 8.6 KiB

After

Width:  |  Height:  |  Size: 8.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 18 KiB

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 26 KiB

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 20 KiB

After

Width:  |  Height:  |  Size: 20 KiB

View File

@ -113,7 +113,7 @@ var plugins_bb40132b_638b_4a9f_b028_d3fe47acc8d1 =
return;
}
if (shop.commonEvent) {
core.insertAction({ "type": "insert", "name": shop.commonEvent, "args": shop.args });
core.insertCommonEvent(shop.commonEvent, shop.args);
return;
}
@ -280,6 +280,272 @@ var plugins_bb40132b_638b_4a9f_b028_d3fe47acc8d1 =
}
}
}
},
"fiveLayers": function () {
// 是否启用五图层增加背景2层和前景2层 将__enableFiveLayers置为true即会启用启用后请保存后刷新编辑器
// 背景层2将会覆盖背景层 被事件层覆盖 前景层2将会覆盖前景层
// 另外 请注意加入两个新图层 会让大地图的性能降低一些
// 插件作者ad
var __enableFiveLayers = false;
if (!__enableFiveLayers) return;
// 创建新图层
function createCanvas(name, zIndex) {
if (!name) return;
var canvas = document.createElement('canvas');
canvas.id = name;
canvas.className = 'gameCanvas';
canvas.width = canvas.height = core.__PIXELS__;
// 编辑器模式下设置zIndex会导致加入的图层覆盖优先级过高
if (main.mode != "editor") canvas.style.zIndex = zIndex || 0;
// 将图层插入进游戏内容
document.getElementById('gameDraw').appendChild(canvas);
var ctx = canvas.getContext('2d');
core.canvas[name] = ctx;
return canvas;
}
var bg2Canvas = createCanvas('bg2', 20);
var fg2Canvas = createCanvas('fg2', 63);
// 大地图适配
core.bigmap.canvas = ["bg2", "fg2", "bg", "event", "event2", "fg", "damage"];
if (main.mode == 'editor') {
/*插入编辑器的图层 不做此步新增图层无法在编辑器显示*/
// 编辑器图层覆盖优先级 eui > efg > fg(前景层) > event2(48*32图块的事件层) > event(事件层) > bg(背景层)
// 背景层2(bg2) 插入事件层(event)之前(即bg与event之间)
document.getElementById('mapEdit').insertBefore(bg2Canvas, document.getElementById('event'));
// 前景层2(fg2) 插入编辑器前景(efg)之前(即fg之后)
document.getElementById('mapEdit').insertBefore(fg2Canvas, document.getElementById('efg'));
// 原本有三个图层 从4开始添加
var num = 4;
// 新增图层存入editor.dom中
editor.dom.bg2c = core.canvas.bg2.canvas;
editor.dom.bg2Ctx = core.canvas.bg2;
editor.dom.fg2c = core.canvas.fg2.canvas;
editor.dom.fg2Ctx = core.canvas.fg2;
editor.dom.maps.push('bg2map', 'fg2map');
editor.dom.canvas.push('bg2', 'fg2');
// 默认全空
var defaultMap = [];
for (var i = 0; i < core.__SIZE__; ++i) {
var row = [];
for (var j = 0; j < core.__SIZE__; ++j) {
row.push(0);
}
defaultMap.push(row);
}
// 创建编辑器上的按钮
var createCanvasBtn = function (name) {
// 电脑端创建按钮
var input = document.createElement('input');
// layerMod4/layerMod5
var id = 'layerMod' + num++;
// bg2map/fg2map
var value = name + 'map';
input.type = 'radio';
input.name = 'layerMod';
input.id = id;
input.value = value;
editor.dom[id] = input;
input.onchange = function () {
editor.uifunctions.setLayerMod(value);
}
editor[value] = editor[value] || defaultMap;
return input;
};
var createCanvasBtn_mobile = function (name) {
// 手机端往选择列表中添加子选项
var input = document.createElement('option');
var id = 'layerMod' + num++;
var value = name + 'map';
input.name = 'layerMod';
input.value = value;
editor.dom[id] = input;
editor[value] = editor[value] || defaultMap;
return input;
};
if (!editor.isMobile) {
var input = createCanvasBtn('bg2');
var input2 = createCanvasBtn('fg2');
// 获取事件层及其父节点
var child = document.getElementById('layerMod'),
parent = child.parentNode;
// 背景层2插入事件层前
parent.insertBefore(input, child);
// 不能直接更改背景层2的innerText 所以创建文本节点
var txt = document.createTextNode('背景层2');
// 插入事件层前(即新插入的背景层2前)
parent.insertBefore(txt, child);
// 向最后插入前景层2(即插入前景层后)
parent.appendChild(input2);
var txt2 = document.createTextNode('前景层2');
parent.appendChild(txt2);
} else {
var input = createCanvasBtn_mobile('bg2');
var input2 = createCanvasBtn_mobile('fg2');
// 手机端因为是选项 所以可以直接改innerText
input.innerText = '背景层2';
input2.innerText = '前景层2';
var parent = document.getElementById('layerMod');
parent.insertBefore(input, parent.children[1]);
parent.appendChild(input2);
}
}
////// 绘制背景层 //////
core.maps.drawBg = function (floorId, ctx) {
floorId = floorId || core.status.floorId;
var onMap = ctx == null;
if (onMap) {
ctx = core.canvas.bg;
core.clearMap(ctx);
core.status.floorAnimateObjs = this._getFloorImages(floorId);
}
core.maps._drawBg_drawBackground(floorId, ctx);
// ------ 调整这两行的顺序来控制是先绘制贴图还是先绘制背景图块;后绘制的覆盖先绘制的。
core.maps._drawFloorImages(floorId, ctx, 'bg');
core.maps._drawBgFgMap(floorId, ctx, 'bg', onMap);
// 绘制背景层2
core.maps._drawBgFgMap(floorId, ctx, 'bg2', onMap);
};
////// 绘制前景层 //////
core.maps.drawFg = function (floorId, ctx) {
floorId = floorId || core.status.floorId;
var onMap = ctx == null;
if (onMap) {
ctx = core.canvas.fg;
core.status.floorAnimateObjs = this._getFloorImages(floorId);
}
// ------ 调整这两行的顺序来控制是先绘制贴图还是先绘制前景图块;后绘制的覆盖先绘制的。
this._drawFloorImages(floorId, ctx, 'fg');
this._drawBgFgMap(floorId, ctx, 'fg', onMap);
// 绘制前景层2
this._drawBgFgMap(floorId, ctx, 'fg2', onMap);
};
/* cannotIn/cannotOut适配 start*/
core.maps.generateMovableArray = function (floorId, x, y, direction) {
floorId = floorId || core.status.floorId;
if (!floorId) return null;
var width = core.floors[floorId].width,
height = core.floors[floorId].height;
var bgArray = this.getBgMapArray(floorId),
bg2Array = this._getBgFgMapArray('bg2', floorId),
fgArray = this.getFgMapArray(floorId),
fg2Array = this._getBgFgMapArray('fg2', floorId),
eventArray = this.getMapArray(floorId);
var generate = function (x, y, direction) {
if (direction != null) {
return core.maps._canMoveHero_checkPoint(x, y, direction, floorId, {
bgArray: bgArray,
fgArray: fgArray,
bg2Array: bg2Array,
fg2Array: fg2Array,
eventArray: eventArray
});
}
return ["left", "down", "up", "right"].filter(function (direction) {
return core.maps._canMoveHero_checkPoint(x, y, direction, floorId, {
bgArray: bgArray,
fgArray: fgArray,
bg2Array: bg2Array,
fg2Array: fg2Array,
eventArray: eventArray
});
});
};
if (x != null && y != null) return generate(x, y, direction);
var array = [];
for (var x = 0; x < width; x++) {
array[x] = [];
for (var y = 0; y < height; y++) {
array[x][y] = generate(x, y);
}
}
return array;
};
core.maps._canMoveHero_checkPoint = function (x, y, direction, floorId, extraData) {
// 1. 检查该点 cannotMove
if (core.inArray((core.floors[floorId].cannotMove || {})[x + "," + y], direction))
return false;
var nx = x + core.utils.scan[direction].x,
ny = y + core.utils.scan[direction].y;
if (nx < 0 || ny < 0 || nx >= core.floors[floorId].width || ny >= core.floors[floorId].height)
return false;
// 2. 检查该点素材的 cannotOut 和下一个点的 cannotIn
if (this._canMoveHero_checkCannotInOut([
extraData.bgArray[y][x], extraData.bg2Array[y][x], extraData.fgArray[y][x], extraData.fg2Array[y][x], extraData.eventArray[y][x]
], "cannotOut", direction))
return false;
if (this._canMoveHero_checkCannotInOut([
extraData.bgArray[ny][nx], extraData.bg2Array[ny][nx], extraData.fgArray[ny][nx], extraData.fg2Array[ny][nx], extraData.eventArray[ny][nx]
], "cannotIn", direction))
return false;
// 3. 检查是否能进将死的领域
if (floorId == core.status.floorId && !core.flags.canGoDeadZone &&
core.status.hero.hp <= (core.status.checkBlock.damage[nx + "," + ny] || 0) &&
extraData.eventArray[ny][nx] == 0)
return false;
return true;
};
/* cannotIn/cannotOut适配 end*/
// 前景层2与背景层2的隐藏与显示适配
// 比如:可以用core.hideBgFgMap("bg2",[x, y], floorId)隐藏当前楼层的背景层2图块
core.maps._triggerBgFgMap = function (type, name, loc, floorId, callback) {
if (type != 'show') type = 'hide';
if (!name) name = 'bg';
if (typeof loc[0] == 'number' && typeof loc[1] == 'number')
loc = [loc];
floorId = floorId || core.status.floorId;
if (!floorId) return;
if (loc.length == 0) return;
loc.forEach(function (t) {
var x = t[0],
y = t[1];
var flag = [floorId, x, y, name + '_disable'].join('@');
if (type == 'hide') core.setFlag(flag, true);
else core.removeFlag(flag);
});
core.status[name + "maps"][floorId] = null;
if (floorId == core.status.floorId) {
core.drawMap(floorId, callback);
} else {
if (callback) callback();
}
};
// 改变背景层2与前景层2图块 例:core.setBgFgBlock('fg2',312,core.nextX(),core.nextY())
core.maps.setBgFgBlock = function (name, number, x, y, floorId) {
floorId = floorId || core.status.floorId;
if (!floorId || number == null || x == null || y == null) return;
if (x < 0 || x >= core.floors[floorId].width || y < 0 || y >= core.floors[floorId].height) return;
if (name != 'bg' && name != 'fg' && name != 'bg2' && name != 'fg2') return;
if (typeof number == 'string') {
if (/^\d+$/.test(number)) number = parseInt(number);
else number = core.getNumberById(number);
}
var vFlag = [floorId, x, y, name + "_value"].join('@');
core.setFlag(vFlag, number);
core.status[name + "maps"][floorId] = null;
if (floorId == core.status.floorId) {
core.clearMap(name);
if (name.startsWith('bg')) core.drawBg(floorId);
else core.drawFg(floorId);
}
};
},
"itemShop": function () {
// 道具商店相关的插件
@ -587,8 +853,10 @@ var plugins_bb40132b_638b_4a9f_b028_d3fe47acc8d1 =
},
"smoothCamera": function () {
// 此插件开启后,大地图的瞬间移动将开启平滑镜头移动,避免突兀感
// 插件作者:老黄鸡
// 是否启用本插件,默认不启用
// 是否启用本插件,默认不启用
this.__enableSmoothCamera = false;
if (!this.__enableSmoothCamera) return;

View File

@ -17,7 +17,7 @@
#mainTips {
color: #fff;
font-size: 0.8rem;
font-size: 0.8em;
position: fixed;
top: 10px;
left: 10px;
@ -72,7 +72,7 @@
#startTopLoadTips {
color: #fff;
font-size: 0.6rem;
font-size: 0.6em;
position: absolute;
top: 10%;
left: 5%;
@ -85,7 +85,7 @@
bottom: 0;
left: 5%;
z-index: 15;
font-size: 18px;
font-size: 1.1em;
}
#startBackground {
@ -108,7 +108,7 @@
margin-top: 8%;
max-width: 100%;
text-align: center;
font: bold 4rem STXingkai;
font: bold 4em STXingkai;
}
#startTitle {
@ -120,7 +120,7 @@
width: auto;
position: absolute;
text-align: center;
font-size: 1.4rem;
font-size: 1.4em;
display: none;
z-index: 310;
bottom: 0;
@ -176,20 +176,20 @@
#logoLabel {
margin-top: 8%;
font: bold 3rem STXingkai;
font: bold 3em STXingkai;
margin-left: auto;
margin-right: auto;
}
#versionLabel {
margin-top: -3%;
font-size: 1.2rem;
font-size: 1.2em;
font-weight: bold;
}
#floorNameLabel {
margin-top: 30px;
font-size: 1.6rem;
font-size: 1.6em;
font-weight: bold;
}

View File

@ -68,9 +68,11 @@
(不处理;现在静止状态可以有帧动画了,所以不考虑行走过程动画) 行走动画
(已完成!) 合并main中一些设置内容
(已完成!) \t[this], 勇士朝下flag:arg清理瞬移扣血
(OK) 同步存档合并;(OK) 失去焦点右键;地图编辑框无效;(OK) 竖屏标题界面背景
右键反复弹出;(OK) 画上下楼梯直接绑定楼传事件;(OK) 属性框出现0问题
(OK) 同步存档合并;(OK) 失去焦点右键;(OK) 竖屏标题界面背景;(OK)商店录像bug
(OK) 右键反复弹出;(OK) 上下楼梯绑定楼传;(OK) 属性框出现0问题(OK) 上下楼点选点
(OK) 地图编辑框无效;(OK) jumpHero和帧动画冲突(OK) bookDetails重复计算buff(OK) 怪物属性多选
(OK) 图片化文本翻转;(OK) 绘制矩形(边框)旋转;
(OK) 特殊属性颜色;(OK) 光环检查;(OK) 钥匙不消耗;(OK) 录像接档问题
-------------

Binary file not shown.