diff --git a/_server/MotaAction.g4 b/_server/MotaAction.g4 index c9b4bbd6..53195db6 100644 --- a/_server/MotaAction.g4 +++ b/_server/MotaAction.g4 @@ -731,7 +731,7 @@ nameMapImage tooltip : 映射图片 default : ['背景图', 'bg.jpg'] allImages : ['EvalString_1'] -material : ["./project/images/", "EvalString_1"] +material : ["./project/images/:images", "EvalString_1"] helpUrl : /_docs/#/instruction return ',"'+EvalString_0+'":"'+EvalString_1+'"'; */; @@ -765,6 +765,44 @@ nameMapEmpty return ' \n'; */; + +splitImages_m + : '图片切分(你可以将一张png格式的大图切分为若干小图)' BGNL? splitImagesList+ BEND + + +/* splitImages_m +tooltip: 图片裁剪 +helpUrl : /_docs/#/instruction +var code = '[\n'+splitImagesList_0+']\n'; +return code; +*/; + +splitImagesList + : splitImagesOne + | splitImagesEmpty; + + +splitImagesOne + : '图片切分项' '图片名' EvalString '每个小图宽度' Int '高度' Int '生成小图的前缀' EvalString BEND + +/* splitImagesOne +tooltip : 图片裁剪项 +helpUrl : /_docs/#/instruction +default : ['hero.png', 32, 32, 'hero_'] +material : ["./project/images/:images", "EvalString_0"] +allImages : ['EvalString_0'] +var code = '{"name": "'+EvalString_0+'", "width": '+Int_0+', "height": '+Int_1+', "prefix": "'+EvalString_1+'"},\n'; +return code; +*/; + +splitImagesEmpty + : Newline + +/* splitImagesEmpty +var code = ' \n'; +return code; +*/; + //为了避免关键字冲突,全部加了_s //动作 action @@ -1689,7 +1727,7 @@ helpUrl : /_docs/#/instruction colour : this.dataColor default : ["hero.png", false] allImages : ['EvalString_0'] -material : ["./project/images/", "EvalString_0"] +material : ["./project/images/:images", "EvalString_0"] EvalString_0 = EvalString_0 && (', "name": "'+EvalString_0+'"'); Bool_0 = Bool_0 ? (', "noDraw": true') : ''; var code = '{"type": "setHeroIcon"'+EvalString_0+Bool_0+'},\n'; @@ -1979,7 +2017,7 @@ tooltip : follow: 跟随勇士 helpUrl : /_docs/#/instruction default : ["npc.png"] allImages : ['EvalString_0'] -material : ["./project/images/", "EvalString_0"] +material : ["./project/images/:images", "EvalString_0"] colour : this.dataColor var code = '{"type": "follow", "name": "'+EvalString_0+'"},\n'; return code; @@ -1994,7 +2032,7 @@ tooltip : unfollow: 取消跟随 helpUrl : /_docs/#/instruction default : [""] allImages : ['EvalString_0'] -material : ["./project/images/", "EvalString_0"] +material : ["./project/images/:images", "EvalString_0"] colour : this.dataColor EvalString_0 = EvalString_0 ? (', "name": "' + EvalString_0 + '"') : ""; var code = '{"type": "unfollow"' + EvalString_0 + '},\n'; @@ -2101,7 +2139,7 @@ tooltip : showImage:显示图片 helpUrl : /_docs/#/instruction default : [1,"bg.jpg","null","0","0",1,0,false] allImages : ['EvalString_0'] -menu : [['选择图片','editor_blockly.selectMaterial(block, ["./project/images/", "EvalString_0"])']] +menu : [['选择图片','editor_blockly.selectMaterial(block, ["./project/images/:images", "EvalString_0"])']] previewBlock : true if (Reverse_List_0 && Reverse_List_0 != 'null') { Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"'; @@ -2122,7 +2160,7 @@ tooltip : showImage_1:显示图片 helpUrl : /_docs/#/instruction default : [1,"bg.jpg","null","0","0","","",1,"0","0","","",0,false] allImages : ['EvalString_0'] -menu : [['选择图片','editor_blockly.selectMaterial(block, ["./project/images/", "EvalString_0"])']] +menu : [['选择图片','editor_blockly.selectMaterial(block, ["./project/images/:images", "EvalString_0"])']] previewBlock : true if (Reverse_List_0 && Reverse_List_0 != 'null') { Reverse_List_0 = ', "reverse": "' + Reverse_List_0 + '"'; diff --git a/_server/MotaActionParser.js b/_server/MotaActionParser.js index c990026c..22b0b5b5 100644 --- a/_server/MotaActionParser.js +++ b/_server/MotaActionParser.js @@ -117,6 +117,15 @@ ActionParser.prototype.parse = function (obj,type) { if(!obj) obj={}; return MotaActionBlocks['faceIds_m'].xmlText([obj.down||"", obj.left||"", obj.right||"", obj.up||""]); + case 'splitImages': + if(!obj) obj=[]; + var text_choices = null; + for(var ii=obj.length-1,choice;choice=obj[ii];ii--) { + text_choices=MotaActionBlocks['splitImagesOne'].xmlText([ + choice.name, choice.width, choice.height, choice.prefix, text_choices]); + } + return MotaActionBlocks['splitImages_m'].xmlText([text_choices]); + case 'mainStyle': if(!obj) obj={}; return MotaActionBlocks['mainStyle_m'].xmlText([ diff --git a/_server/css/editor.css b/_server/css/editor.css index d8f200d5..783e27e6 100644 --- a/_server/css/editor.css +++ b/_server/css/editor.css @@ -617,15 +617,15 @@ table.row { } .etable tr > :nth-child(1) { - width: 22% + width: 24% } .etable tr > :nth-child(2) { - width: 20% + width: 19% } .etable tr > :nth-child(3) { - width: 33%; + width: 32%; } .etable tr > :nth-child(4) { diff --git a/_server/editor_blocklyconfig.js b/_server/editor_blocklyconfig.js index 9b51fceb..f7f602d5 100644 --- a/_server/editor_blocklyconfig.js +++ b/_server/editor_blocklyconfig.js @@ -91,6 +91,9 @@ editor_blocklyconfig=(function(){ MotaActionFunctions.actionParser.parse({ "背景音乐": "bgm.mp3", "确定": "confirm.mp3", "攻击": "attack.mp3", "背景图": "bg.jpg", "领域": "zone", "文件名": "file.jpg" }, 'nameMap'), + MotaActionFunctions.actionParser.parse([ + {"name": "hero.png", "width": 32, "height": 32, "prefix": "hero_"}, + ], 'splitImages'), ], '显示文字':[ MotaActionBlocks['text_0_s'].xmlText(), diff --git a/_server/editor_ui.js b/_server/editor_ui.js index 08960107..20b4d436 100644 --- a/_server/editor_ui.js +++ b/_server/editor_ui.js @@ -789,6 +789,10 @@ editor_ui_wrapper = function (editor) { // ------ 素材选择框 ------ // uievent.selectMaterial = function (value, title, directory, transform, callback) { + var one = directory.split(':'); + if (one.length > 1) directory = one[0]; + var appendedImages = one[1] == 'images' ? core.material.images.images : {}; + fs.readdir(directory, function (err, data) { if (err) { printe(directory + '不存在!'); @@ -800,6 +804,10 @@ editor_ui_wrapper = function (editor) { } value = value || []; data = (transform ? data.map(transform) : data).filter(function (one) {return one;}).sort(); + var data2 = Object.keys(appendedImages); + data2 = (transform ? data2.map(transform) : data2).filter(function (one) { + return one && data.indexOf(one) < 0; + }).sort(); uievent.isOpen = true; uievent.elements.div.style.display = 'block'; @@ -857,6 +865,16 @@ editor_ui_wrapper = function (editor) { } html += '
'; }); + data2.forEach(function (one) { + var checked = value.indexOf(one) >= 0? 'checked' : ''; + var disabled = _isTileset && value.indexOf(one) >= 0 ? 'disabled' : ''; + html += ` ${one}`; + // 预览图片 + if (one.endsWith('.png') || one.endsWith('.jpg') || one.endsWith('.jpeg') || one.endsWith('.gif')) { + html += ""; + html += '

'; + } + }) html += "

"; html += "

如果文件未在此列表显示,请检查文件名是否合法(只能由数字字母下划线横线和点组成),后缀名是否正确。

"; uievent.elements.extraBody.innerHTML = html; @@ -884,6 +902,19 @@ editor_ui_wrapper = function (editor) { } } + uievent._previewMaterialImage2 = function (button) { + var br = button.nextElementSibling; + if (br.style.display == 'none') { + button.innerText = '折叠'; + br.style.display = 'block'; + br.parentElement.insertBefore(core.material.images.images[br.getAttribute('key')], br.nextElementSibling); + } else { + button.innerText = '预览'; + br.style.display = 'none'; + br.parentElement.removeChild(core.material.images.images[br.getAttribute('key')]); + } + } + uievent._previewMaterialAudio = function (button) { var span = button.nextElementSibling.nextElementSibling; var br = span.nextElementSibling; diff --git a/_server/table/comment.js b/_server/table/comment.js index 298507be..17fb1ccb 100644 --- a/_server/table/comment.js +++ b/_server/table/comment.js @@ -145,7 +145,7 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = { "bigImage": { "_leaf": true, "_type": "material", - "_directory": "./project/images/", + "_directory": "./project/images/:images", "_transform": (function (one) { if (one.endsWith('.png')) return one; return null; @@ -401,7 +401,7 @@ var comment_c456ea59_6018_45ef_8bcc_211a24c627dc = { "bigImage": { "_leaf": true, "_type": "material", - "_directory": "./project/images/", + "_directory": "./project/images/:images", "_transform": (function (one) { if (one.endsWith('.png')) return one; return null; diff --git a/_server/table/data.comment.js b/_server/table/data.comment.js index 3508accc..81b08345 100644 --- a/_server/table/data.comment.js +++ b/_server/table/data.comment.js @@ -38,6 +38,13 @@ var data_comment_c456ea59_6018_45ef_8bcc_211a24c627dc = { "_docs": "使用图片", "_data": "在此存放所有可能使用的图片(tilesets除外) \n图片可以被作为背景图(的一部分),也可以直接用自定义事件进行显示。 \n 图片名不能使用中文,不能带空格或特殊字符;可以直接改名拼音就好 \n 建议对于较大的图片,在网上使用在线的“图片压缩工具(http://compresspng.com/zh/)”来进行压缩,以节省流量 \n 依次向后添加", }, + "splitImages": { + "_leaf": true, + "_type": "event", + "_event": "splitImages", + "_docs": "图片切分", + "_data": "可以在这里对使用到的图片进行按照一定宽高切分,生成若干新的小图供使用" + }, "tilesets": { "_leaf": true, "_type": "material", diff --git a/libs/core.js b/libs/core.js index 3c108ad0..3f498417 100644 --- a/libs/core.js +++ b/libs/core.js @@ -472,6 +472,23 @@ core.prototype._afterLoadResources = function (callback) { // 初始化地图 core.initStatus.maps = core.maps._initMaps(); core.control._setRequestAnimationFrame(); + // 图片裁剪 + (main.splitImages || []).forEach(function (one) { + var name = core.getMappedName(one.name); + if (!core.material.images.images[name]) { + console.warn('找不到图片:' + name + ',无法裁剪'); + return; + } + if (!name.endsWith('.png')) { + console.warn('无法裁剪非png格式图片:' + name); + return; + } + var arr = core.splitImage(core.material.images.images[name], one.width, one.height); + for (var i = 0; i < arr.length; ++i) { + core.material.images.images[(one.prefix||"") + i + '.png'] = arr[i]; + } + }); + if (core.plugin._afterLoadResources) core.plugin._afterLoadResources(); core.showStartAnimate(); diff --git a/project/plugins.js b/project/plugins.js index 5a6a3465..10be4bb0 100644 --- a/project/plugins.js +++ b/project/plugins.js @@ -11,14 +11,8 @@ var plugins_bb40132b_638b_4a9f_b028_d3fe47acc8d1 = this._afterLoadResources = function () { // 本函数将在所有资源加载完毕后,游戏开启前被执行 - // 可以在这个函数里面对资源进行一些操作,比如切分图片等。 - - // 这是一个将assets.png拆分成若干个32x32像素的小图片并保存的样例。 - // var arr = core.splitImage("assets.png", 32, 32); - // for (var i = 0; i < arr.length; i++) { - // core.material.images.images["asset"+i+".png"] = arr[i]; - // } - + // 可以在这个函数里面对资源进行一些操作。 + // 若需要进行切分图片,可以使用 core.splitImage() 函数,或直接在全塔属性-图片切分中操作 } // 可以在任何地方(如afterXXX或自定义脚本事件)调用函数,方法为 core.plugin.xxx();