设为首页收藏本站|繁體中文

Project1

 找回密码
 注册会员
搜索
查看: 5048|回复: 18
打印 上一主题 下一主题

[讨论] MV的代码解析【持续更新】

[复制链接]

Lv3.寻梦者

唯一的信徒

梦石
0
星屑
1665
在线时间
1357 小时
注册时间
2013-1-29
帖子
1637
跳转到指定楼层
1
发表于 2015-10-1 14:32:11 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式

加入我们,或者,欢迎回来。

您需要 登录 才可以下载或查看,没有帐号?注册会员

x
本帖最后由 LBQ 于 2015-10-3 10:27 编辑

10月3日:
有了TextManager你说我们要不要i18n
binary json可以试试
10月2日:
没有预想的那么恶心233
COFFEESCRIPT 代码复制
  1. class Scene_Crafting extends Scene_MenuBase
  2.   initialize: ->
  3.     super()
  4.   create: ->
  5.     super()
  6.     this.createBackground()
  7.     this.createWindowLayer()
  8.     this.createGoldWindow()
  9.   start: ->
  10.     super()
  11.   createGoldWindow: ->
  12.     @goldWindow = new Window_Gold(0,0)
  13.     this.addWindow(@goldWindow)


我没法用Plugin更改plugin manager
我选择死亡

pixi.js用的v2感觉很不爽,应该移植到v3的


其实重点是pixi.js啊
想想看这些可能性啊





Google closure compiler的advance编译别想了,mv代码没有预先准备最终产物没法运行
UglifyJs之类的还是可以用
Desktop版本会用Nw.js作为Js后端,可以直接开node
binary json估计是可以用


原网页:http://preorder.rpgmakerweb.com/rpg-maker-mv/



毕竟有游戏了所以解析一下吧:

1:Yanfly下手好快,现在就有脚本了是怎么回事,黑幕吗
2:渲染用的Pixi.js,我很开心

继续读代码中,游戏不知道为何玩不了只能读代码了

3:没有用npm或者commonjs之类的,直接采用的html引用脚本,这个到时候得修一下
4:主题代码被minify或者obfuscate了,不好读

5:core.js:https://www.refheap.com/110141
6:managers.js:https://www.refheap.com/110142

很明显数据库用的json
好评

7:objects.js:https://www.refheap.com/110143,太长了,refheap不知道为何不行。
objects.7z (36.89 KB, 下载次数: 60)
8:scenes.js:https://www.refheap.com/110144
9:sprites.js : https://www.refheap.com/110145
Window.prototype.initialize是什么鬼

看得出来代码是中规中矩的ruby式js....?

本来Js比Ruby更加Functional一些的,但是为了保持惯例继续用Ruby的法则...?
10:window.js:https://www.refheap.com/110146

感觉有点像用Js写Ruby代码233
还是猴子补丁,一堆猴子补丁

JAVASCRIPT 代码复制
  1. Window_BattleLog.prototype.callNextMethod = function() {
  2.     if (this._methods.length > 0) {
  3.         var method = this._methods.shift();
  4.         if (method.name && this[method.name]) {
  5.             this[method.name].apply(this, method.params)
  6.         } else {
  7.             throw new Error('Method not found: ' + method.name)
  8.         }
  9.     }
  10. };


这段代码真心诡异

全部代码打包:
mv-core-src.7z (103.88 KB, 下载次数: 78)

Scene与Scene之间切换都没有什么鬼

数据库json文件打包: data.zip (19.89 KB, 下载次数: 86)

这行走图和脸图让我蛋疼的不行

Sprite的代码:
JAVASCRIPT 代码复制
  1. Sprite.prototype._renderWebGL = function(renderSession) {
  2.     if (this.visible && this.alpha > 0) {
  3.         var spriteBatch = renderSession.spriteBatch;
  4.         if (this._filters) {
  5.             spriteBatch.flush();
  6.             renderSession.filterManager.pushFilter(this._filterBlock);
  7.             if (this.opaque) {
  8.                 renderSession.gl.clearColor(0, 0, 0, 1);
  9.                 renderSession.gl.clear(renderSession.gl.COLOR_BUFFER_BIT)
  10.             }
  11.         }
  12.         if (this._mask) {
  13.             spriteBatch.stop();
  14.             renderSession.maskManager.pushMask(this.mask, renderSession);
  15.             spriteBatch.start()
  16.         }
  17.         spriteBatch.render(this);
  18.         for (var i = 0, j = this.children.length; i < j; i++) {
  19.             this.children[i]._renderWebGL(renderSession)
  20.         }
  21.         if (this._mask) {
  22.             spriteBatch.stop();
  23.             renderSession.maskManager.popMask(this._mask, renderSession);
  24.             spriteBatch.start()
  25.         }
  26.         if (this._filters) {
  27.             spriteBatch.stop();
  28.             renderSession.filterManager.popFilter();
  29.             spriteBatch.start()
  30.         }
  31.     }
  32. };


Pixi.js的同样的方法
JAVASCRIPT 代码复制
  1. PIXI.Sprite.prototype._renderWebGL = function(renderSession)
  2. {
  3.     // if the sprite is not visible or the alpha is 0 then no need to render this element
  4.     if(!this.visible || this.alpha <= 0)return;
  5.  
  6.     var i,j;
  7.  
  8.     // do a quick check to see if this element has a mask or a filter.
  9.     if(this._mask || this._filters)
  10.     {
  11.         var spriteBatch =  renderSession.spriteBatch;
  12.  
  13.         // push filter first as we need to ensure the stencil buffer is correct for any masking
  14.         if(this._filters)
  15.         {
  16.             spriteBatch.flush();
  17.             renderSession.filterManager.pushFilter(this._filterBlock);
  18.         }
  19.  
  20.         if(this._mask)
  21.         {
  22.             spriteBatch.stop();
  23.             renderSession.maskManager.pushMask(this.mask, renderSession);
  24.             spriteBatch.start();
  25.         }
  26.  
  27.         // add this sprite to the batch
  28.         spriteBatch.render(this);
  29.  
  30.         // now loop through the children and make sure they get rendered
  31.         for(i=0,j=this.children.length; i<j; i++)
  32.         {
  33.             this.children[i]._renderWebGL(renderSession);
  34.         }
  35.  
  36.         // time to stop the sprite batch as either a mask element or a filter draw will happen next
  37.         spriteBatch.stop();
  38.  
  39.         if(this._mask)renderSession.maskManager.popMask(this._mask, renderSession);
  40.         if(this._filters)renderSession.filterManager.popFilter();
  41.  
  42.         spriteBatch.start();
  43.     }
  44.     else
  45.     {
  46.         renderSession.spriteBatch.render(this);
  47.  
  48.         // simple render children!
  49.         for(i=0,j=this.children.length; i<j; i++)
  50.         {
  51.             this.children[i]._renderWebGL(renderSession);
  52.         }
  53.  
  54.     }
  55. };


MV这个代码真的可以去死了,


现在我才意识到Scene是Stage的一种,EB你去死吧

Pixi用的v2,应该无大碍,先这样OTL

评分

参与人数 1星屑 +45 收起 理由
Tink + 45

查看全部评分

『我只是一个正在潜心修炼的渣乐师罢了』
Dear Time\(^o^)/~


假如上面的图片挂了的话麻烦各位去发个帖 @ 一下 orzFly 让他修复 deartime

Lv5.捕梦者 (暗夜天使)

只有笨蛋才会看到

梦石
1
星屑
21484
在线时间
9389 小时
注册时间
2012-6-19
帖子
7114

开拓者短篇九导演组冠军

2
发表于 2015-10-1 15:13:33 | 只看该作者
本帖最后由 喵呜喵5 于 2015-10-1 17:21 编辑
  1. $gameParty.gainGold(65535)
复制代码
无比炸裂的加钱代码果然有效……防作弊迫在眉睫

不止Yanfly,Yami、Galenmerth、Neonblack等国外比较有名的脚本都有出现,并且它们写的脚本将作为首波DLC公开

======================

RMVA有的RMMV都有,不如说RMMV的脚本简直就是RMVA脚本的JS化,看着非常眼熟

相比RMVA功能上有变动的地方:

使用 TouchInput.isTriggered() / TouchInput.isPressed()  响应点击事件



Manager
Cache 改名为 ImageManager,然而实际上做的还是Cache的事,图片素材上只增加了SvActor和SvEnemy这两个用在SideView模式的素材文件夹
Vocab 改名为 TextManager,各种改名Manager等,Audio也分出来作为Manager了……
插件脚本作为新节点贴在body上
  1. PluginManager.loadScript = function(name) {
  2.     var url = this._path + name;
  3.     var script = document.createElement('script');
  4.     script.type = 'text/javascript';
  5.     script.src = url;
  6.     script.async = false;
  7.     script.onerror = this.onError.bind(this);
  8.     script._url = url;
  9.     document.body.appendChild(script)
  10. };
复制代码


Scene

初始界面为Scene_Boot,负责加载并检查资源是否全部加载完毕
SceneManager.run(Scene_Boot);

SceneManager.call 由 push 代替,return由pop代替,goto仍然不变
  1. SceneManager.pop()
  2. SceneManager.goto(Scene_Gameover)
  3. SceneManager.push(Scene_Save)
复制代码
存读档界面布局调整


……………………囧
  1. this._rangeWindow.setHandler('cancel', this.popScene.bind(this));
复制代码


Game

某种程度的中文支持?还是说要出官方中文版了?
JAVASCRIPT 代码复制
  1. Game_System.prototype.isChinese = function() {
  2.     return $dataSystem.locale.match(/^zh/)
  3. };


Game_Character支持寻路了,算法为A*,没有使用二叉堆等进行优化,因此为了提高效率默认设置了寻路的限制,突破限制时停止寻路,但是可以去除
JAVASCRIPT 代码复制
  1. Game_Character.prototype.findDirectionTo = function(goalX, goalY) {
  2.     var searchLimit = this.searchLimit();
  3.     var mapWidth = $gameMap.width();
  4.     var nodeList = [];
  5.     var openList = [];
  6.     var closedList = [];
  7.     var start = {};
  8.     var best = start;
  9.     if (this.x === goalX && this.y === goalY) {
  10.         return 0
  11.     }
  12.     start.parent = null;
  13.     start.x = this.x;
  14.     start.y = this.y;
  15.     start.g = 0;
  16.     start.f = $gameMap.distance(start.x, start.y, goalX, goalY);
  17.     nodeList.push(start);
  18.     openList.push(start.y * mapWidth + start.x);
  19.     while (nodeList.length > 0) {
  20.         var bestIndex = 0;
  21.         for (var i = 0; i < nodeList.length; i++) {
  22.             if (nodeList[i].f < nodeList[bestIndex].f) {
  23.                 bestIndex = i
  24.             }
  25.         }
  26.         var current = nodeList[bestIndex];
  27.         var x1 = current.x;
  28.         var y1 = current.y;
  29.         var pos1 = y1 * mapWidth + x1;
  30.         var g1 = current.g;
  31.         nodeList.splice(bestIndex, 1);
  32.         openList.splice(openList.indexOf(pos1), 1);
  33.         closedList.push(pos1);
  34.         if (current.x === goalX && current.y === goalY) {
  35.             best = current;
  36.             goaled = true;
  37.             break
  38.         }
  39.         if (g1 >= searchLimit) {
  40.             continue
  41.         }
  42.         for (var j = 0; j < 4; j++) {
  43.             var direction = 2 + j * 2;
  44.             var x2 = $gameMap.roundXWithDirection(x1, direction);
  45.             var y2 = $gameMap.roundYWithDirection(y1, direction);
  46.             var pos2 = y2 * mapWidth + x2;
  47.             if (closedList.contains(pos2)) {
  48.                 continue
  49.             }
  50.             if (!this.canPass(x1, y1, direction)) {
  51.                 continue
  52.             }
  53.             var g2 = g1 + 1;
  54.             var index2 = openList.indexOf(pos2);
  55.             if (index2 < 0 || g2 < nodeList[index2].g) {
  56.                 var neighbor;
  57.                 if (index2 >= 0) {
  58.                     neighbor = nodeList[index2]
  59.                 } else {
  60.                     neighbor = {};
  61.                     nodeList.push(neighbor);
  62.                     openList.push(pos2)
  63.                 }
  64.                 neighbor.parent = current;
  65.                 neighbor.x = x2;
  66.                 neighbor.y = y2;
  67.                 neighbor.g = g2;
  68.                 neighbor.f = g2 + $gameMap.distance(x2, y2, goalX, goalY);
  69.                 if (!best || neighbor.f - neighbor.g < best.f - best.g) {
  70.                     best = neighbor
  71.                 }
  72.             }
  73.         }
  74.     }
  75.     var node = best;
  76.     while (node.parent && node.parent !== start) {
  77.         node = node.parent
  78.     }
  79.     var deltaX1 = $gameMap.deltaX(node.x, start.x);
  80.     var deltaY1 = $gameMap.deltaY(node.y, start.y);
  81.     if (deltaY1 > 0) {
  82.         return 2
  83.     } else if (deltaX1 < 0) {
  84.         return 4
  85.     } else if (deltaX1 > 0) {
  86.         return 6
  87.     } else if (deltaY1 < 0) {
  88.         return 8
  89.     }
  90.     var deltaX2 = this.deltaXFrom(goalX);
  91.     var deltaY2 = this.deltaYFrom(goalY);
  92.     if (Math.abs(deltaX2) > Math.abs(deltaY2)) {
  93.         return deltaX2 > 0 ? 4 : 6
  94.     } else if (deltaY2 !== 0) {
  95.         return deltaY2 > 0 ? 8 : 2
  96.     }
  97.     return 0
  98. };
  99. Game_Character.prototype.searchLimit = function() {
  100.     return 12
  101. };
视频格式可以使用webm和mp4了(需设备支持)
JAVASCRIPT 代码复制
  1. Game_Interpreter.prototype.videoFileExt = function() {
  2.     if (Graphics.canPlayVideoType('video/webm') && !Utils.isMobileDevice()) {
  3.         return '.webm'
  4.     } else {
  5.         return '.mp4'
  6.     }
  7. };


可以通过事件指令直接获取玩家的战斗胜利和逃跑次数了

用来扩展事件指令功能增加任意个新指令的?
JAVASCRIPT 代码复制
  1. Game_Interpreter.prototype.command356 = function() {
  2.     var args = this._params[0].split(" ");
  3.     var command = args.shift();
  4.     this.pluginCommand(command, args);
  5.     return true
  6. };
  7. Game_Interpreter.prototype.pluginCommand = function(command, args) {};


……

读累了,之后再去看还没读的Window代码吧

点评

同求  发表于 2015-10-2 14:29
请问mv是在哪下得?好多大神都有。  发表于 2015-10-1 17:38

评分

参与人数 2星屑 +320 收起 理由
Tink + 20
taroxd + 300 头像丧失!(重点错

查看全部评分

回复 支持 反对

使用道具 举报

Lv4.逐梦者

梦石
0
星屑
9280
在线时间
2504 小时
注册时间
2011-5-20
帖子
15389

开拓者

3
发表于 2015-10-1 15:15:01 | 只看该作者
喵呜喵5 发表于 2015-9-30 22:13

$gameParty?那角色用$gameActor?
[img]http://service.t.sina.com.cn/widget/qmd/5339802982/c02e16bd/7.png
回复 支持 反对

使用道具 举报

Lv3.寻梦者 (版主)

…あたしは天使なんかじゃないわ

梦石
0
星屑
2208
在线时间
4033 小时
注册时间
2010-10-4
帖子
10779

开拓者贵宾

4
发表于 2015-10-1 15:23:07 | 只看该作者
不知道为什么,看着代码就完全没有入手的欲望了

评分

参与人数 1星屑 +1 收起 理由
chd114 + 1 这代码看起来可以掰弯直男

查看全部评分

回复 支持 反对

使用道具 举报

Lv5.捕梦者 (暗夜天使)

只有笨蛋才会看到

梦石
1
星屑
21484
在线时间
9389 小时
注册时间
2012-6-19
帖子
7114

开拓者短篇九导演组冠军

5
发表于 2015-10-1 15:46:48 | 只看该作者
本帖最后由 喵呜喵5 于 2015-10-1 15:47 编辑

下载了全代码打包看了半天忽然意识到你漏了Game啊

====================

哦不对,原来Game你打包放到另一个附件里了
回复 支持 反对

使用道具 举报

Lv3.寻梦者 (版主)

…あたしは天使なんかじゃないわ

梦石
0
星屑
2208
在线时间
4033 小时
注册时间
2010-10-4
帖子
10779

开拓者贵宾

6
发表于 2015-10-1 20:59:02 | 只看该作者
喵呜喵5 发表于 2015-10-1 15:13
无比炸裂的加钱代码果然有效……防作弊迫在眉睫

不止Yanfly,Yami、Galenmerth、Neonblack等国外比较有名 ...

关于作弊啥的,你可以直接把 cookie 拿出来,base64 解了随便改
回复 支持 反对

使用道具 举报

Lv1.梦旅人

梦石
0
星屑
50
在线时间
1281 小时
注册时间
2006-8-27
帖子
590
7
发表于 2015-10-2 03:58:54 | 只看该作者
数据库没任何加密或压缩吗?
txt打开就能随便改啊

点评

参考二楼第一段代码,至少在目前官方提供的demo中,它可以顺畅的直接运行并立刻增加65535点金钱  发表于 2015-10-2 09:18
基本上rmmv制作的游戏在网页端运行时你就别指望加密了,不过也没人会去改数据库  发表于 2015-10-2 09:17
回复 支持 反对

使用道具 举报

Lv3.寻梦者 (版主)

…あたしは天使なんかじゃないわ

梦石
0
星屑
2208
在线时间
4033 小时
注册时间
2010-10-4
帖子
10779

开拓者贵宾

8
发表于 2015-10-2 08:03:44 | 只看该作者
wbsy8241 发表于 2015-10-2 03:58
数据库没任何加密或压缩吗?
txt打开就能随便改啊

数据库在服务器端,你怎么改

当然你可以把包抓下来黑了
回复 支持 反对

使用道具 举报

Lv1.梦旅人

路人党员

梦石
0
星屑
52
在线时间
2276 小时
注册时间
2010-12-30
帖子
3225
9
发表于 2015-10-2 10:13:20 | 只看该作者
真心觉得不想用MV,虽然跨平台这一点很不错,但是比起ruby,js有很多不方便的地方

点评

比如呢(纯好奇)  发表于 2015-10-2 10:33
本人擅长XP,如果有脚本或者Ruby方面的问题欢迎发电邮到[email protected]咨询,本人很少检查电邮所以不一定会及时回复,本人不会直接出手解决问题只会提供一个方向,所以谢绝伸手党
回复 支持 反对

使用道具 举报

Lv3.寻梦者 (暗夜天使)

精灵族の天使

梦石
0
星屑
1697
在线时间
3038 小时
注册时间
2007-3-16
帖子
33731

开拓者贵宾

10
发表于 2015-10-2 10:25:15 | 只看该作者
我目前ACE就足够使用了。
MV对我来说还很早。
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册会员

本版积分规则

拿上你的纸笔,建造一个属于你的梦想世界,加入吧。
 注册会员
找回密码

站长信箱:[email protected]|手机版|小黑屋|无图版|Project1游戏制作

GMT+8, 2024-10-1 23:39

Powered by Discuz! X3.1

© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表