×

GM教程 Gamemaker GM插件扩展脚本 玉米原创

Mage Replay回放文件生成

Mage松仁玉米 Mage松仁玉米 发表于2015-03-04 01:51:37 浏览5043 评论1

1人参与发表评论


为了方便广大青少年及劳动妇女的需要,玉米特意准备了回放文件脚本扩展函数,此款脚本可以帮助你生成回放文件,生成出的文件短小精悍,才几十到几百KB,共享方便,储存方便,随时随地欣赏自己的个人游戏技术,该脚本是你绝对不能错过的。

这个脚本对游戏编程方面做出了很大的限定,因为是回放文件,所以说不能有一帧的误差,这就对游戏的编写有了很多的强制性要求。

插件原理:记录用户按键输入、随机种子,利用数据结构列表存储数据,完成回放,必要插件:GMZ解压缩插件,以及ultracrypt文件加解密插件。

下载地址

GMZ下载:本地下载
ultracrypt下载:本地下载
源码:本地下载百度网盘

使用说明:

mg_rpy_init(verstr)

脚本的初始化函数,必须用在游戏开始的时候载入,否则其他的函数均会出现错误。

verstr:这个参数是在验证回放文件用的,可以说是你游戏的版本号,字符串形式,这就是为了要防止出现新版本的游戏更改代码后载入旧的回放文件出错的验证码,所以说,没有什么关于游戏的大更新,这个可以不用变动。如果你觉得没有必要的话,你随意填写一个字符串就可以了。

mg_rpy_reclist_create()

创建一个记录库,返回这个记录库的ID,在以后录制、回放和编辑时用。

之所以会出这个函数,是因为考虑到各位在记录按键的时候需要分拨记录,比如说,不同的关卡需要不同的记录库,播放的时候可能跳过其中一个关卡而播放另外的关卡,从而读取相对应的记录库,那么这个函数就显得尤为重要。

mg_rpy_record_init()

开始录像啦~在最开始,你需要创建一个物体是有关于录像方面的物体,如果你需要一直录像的话那这个物体必须一直保持在房间中,可以将它设置为持续。必要时再销毁,我们先设置这个物体为obj_rec。这个函数也起到了清空所有数据的做用,也就是说,如果你读取完一个回放文件之后,不可以在调用这个函数,否则会清空所有读取过的数据,重新载入回放文件才能恢复。具体的载入回放文件方法见下文。

mg_rpy_record(id)

这个函数就是主要的记录函数啦,这是一个非常重要的脚本,所以有必要详细的解释一下。

这个脚本必须放在obj_rec物体的步结束事件中!这是因为在记录按键的时候,只有放在步结束事件才可以把该帧所按下的按键全部记好。放在其他并行事件中会导致记录信息不全,或者是时间篡位等现象发生。

另外强调一点的是,这个函数不是你导入到游戏中就可以正常使用的。你必须把这个函数载入到GM中,然后进行编辑。

我们以我给出的1945的例子做个说明。

如下,是1945游戏中,该函数的代码:

if(keyboard_check(ord("W"))) global.mgrpy_button_str += "w"

if(keyboard_check(ord("S"))) global.mgrpy_button_str += "s"

if(keyboard_check(ord("A"))) global.mgrpy_button_str += "a"

if(keyboard_check(ord("D"))) global.mgrpy_button_str += "d"

if(keyboard_check(ord("U"))) global.mgrpy_button_str += "u"

if(keyboard_check(ord("I"))) global.mgrpy_button_str += "i"

ds_list_insert(global.mg_rpy_list[argument0],global.mgrpy_wz,global.mgrpy_button_str)

global.mgrpy_button_str = ""

global.mgrpy_wz += 1

1945游戏中,需要的按键事件有:键盘W事件,键盘S事件,键盘A事件,键盘D事件,键盘U事件,键盘I事件。你需要做的就是把所有有关于游戏控制方面的事件统统都写进去,然后在后面的识别字母中以一个字母、符号或数字表示出来,因为在读取回放文件中,是靠读取这些识别码来执行相应动作,必须一一对应,所以,上述代码的蓝色字体,你必须按照你的游戏重新修改,下面的红色字体不要动,这是记录回放的关键代码!要放在蓝色代码的下面。

mg_rpy_mes_write(pos,str)

在游戏的回放文件中,你可能会需要记录一些信息,比如说,回放名字,游戏者名字,游戏关卡,游戏总分等等不同的信息,你需要将他们一一的储存进入回放文件中,必要的时候读取,那么你就会用到这个函数。

这个函数的功能是在pos位置写入字符串str,第一位是0,这个函数的工作原理是使用列表记录,也就是说,他完全具有ds_list的一切性质,会自动按照插入的顺序排列等等。所以说一定要找好位置插入数据,防止在读取时发生读取错误这些不必要的麻烦。

特别要注意的是,本脚本并没有自动记录随机数种子的功能,所以记录种子的时候你比须自己做,可以用这个函数将种子数值储存到相应位置里,回放时再读取出来。你可以按照如下的做法记录随机数种子:

obj_rec的创建事件中写下(可以说是在录制刚刚开始的时候写)

mg_rpy_record_init()//初始化录制函数

global.rpyid = mg_rpy_reclist_create()//新建立一个存储库存储输入数据

randomize()//随机设置随机数种子

mg_rpy_mes_write(0,string(random_get_seed()))//将随机数种子存储到回放文件的相应位置,方便以后读取使用。

mg_rpy_save(file)

记录完所有的动作之后,你需要将他们整理起来,输出一个标准的回放文件,用于以后载入观赏。你需要用到这个函数来输出一个文件,file为输出的文件名,必须是一个完整路径的标准字符串形式。

mg_rpy_load(file)

载入一个回放文件,file必须是完整路径的字符串形式。当你需要播放一个回放文件时,开始就要调用这个函数,否则一些读取的函数是无法使用的。

mg_rpy_replay(id)

开始播放载入的回放文件,这个函数同mg_rpy_record一样,要求比较苛刻,你必须把他放在相关回放物体的步开始事件中,放在其他事件中会导致和mg_rpy_record一样的效果,参数id是你在储存数据的时候所返回的那个id数,所以必须要想对应,才能播放出来。你要做的也是和mg_rpy_record一样,修改并将此脚本导入到GM里。下面以1945中的该函数代码为例。

global.mgrpy_button_str =ds_list_find_value(global.mg_rpy_list[argument0],global.mgrpy_wz)

with(obj_myplane)

{

if(string_count("w",global.mgrpy_button_str) > 0) scr_move_up();

if(string_count("s",global.mgrpy_button_str) > 0) scr_move_down();

if(string_count("a",global.mgrpy_button_str) > 0) scr_move_left();

if(string_count("d",global.mgrpy_button_str) > 0) scr_move_right();

if(string_count("u",global.mgrpy_button_str) > 0) scr_p_shot();

if(string_count("i",global.mgrpy_button_str) > 0) scr_p_slow(); else scr_p_slow_else();

}

global.mgrpy_wz += 1

这个函数就比mg_rpy_record要复杂很多,红色的代码位置和写法你依然不能动,你可以改变的只有蓝色代码,其中,使用with结构来确定执行动作的物体。前面的小写wsad等就是你在录制时写下的识别码,该脚本的原理就是,识别到对应的代码,就会执行相应的动作,后面的一小段就是相应的动作,只不过在1945中我都把动作存入到了脚本当中。

上面所例举的两个代码,都只能记录键盘事件,而并非是键盘按下或者放开事件,如果你的游戏中带有键盘按下和放开事件,你就需要对上面的脚本的橙色代码区做一下修改,来检查这一帧之前的按键是否被按下或放开,然后执行相应的动作。举个例子先:

比如说,你有一个物体obj,按下键盘S键时设置变量a = 1,放开键盘S键时设置变量a=0,那么你就要在mg_rpy_record脚本中写下:

if(keyboard_check(ord("S"))) global.mgrpy_button_str += "s"

ds_list_insert(global.mg_rpy_list[argument0],global.mgrpy_wz,global.mgrpy_button_str)

global.mgrpy_button_str = ""

global.mgrpy_wz += 1

mg_rpy_replay脚本中写下:

global.mgrpy_button_str_before =ds_list_find_value(global.mg_rpy_list[argument0],global.mgrpy_wz-1)

global.mgrpy_button_str =ds_list_find_value(global.mg_rpy_list[argument0],global.mgrpy_wz)

global.mgrpy_button_str_after =ds_list_find_value(global.mg_rpy_list[argument0],global.mgrpy_wz+1)

with(obj)

{

if(string_count("s",global.mgrpy_button_str) > 0 and string_count("s",global.mgrpy_button_str_before) = 0a = 1;

If(string_count("s",global.mgrpy_button_str) > 0 and string_count("s",global.mgrpy_button_str_after) = 0) a = 0;

}

global.mgrpy_wz += 1

加入了按下和放开事件,代码就复杂了很多,但是这对熟悉GML的同学来讲没什么难度,你也可以用一个更简单的方法,在记录的时候按下或放开某按键用一个不同的识别码,然后再读取的时候读到相应的识别码就执行相应的放开或按下键盘动作,采用模拟按键或者产生事件代码,会容易许多。

mg_rpy_mes_read(pos)

这个函数则是读取回放文件中在pos位置的信息,位置与你在储存信息时的位置一样,只不过这个函数返回的是字符串形式,如果你需要读取一个实数信息,你需要用real函数将字符串转换为实数。这个我就不多解释了。该函数必须在已经载入完回放文件之后使用。

mg_rpy_cheak_end(id)

返回当前播放是否到达指定id记录库的终结,是检测是否播放完毕时使用。

mg_rpy_get_lenth()

返回载入的回放文件的时间长度,所以说你必须在载入完一个回放文件后用该函数,如果在录像时使用则会返回已经记录下多少帧。注意该函数返回的是所有记录库记录时间的总和,而并非一个记录库。如果大家需要的话,可以自行查看脚本修改使用。

mg_rpy_get_pos()

返回当前的探头点在第几帧,可以说是播放时间,如果在录像时使用会返回与mg_rpy_get_lenth一样的数值。

mg_rpy_get_total()

返回载入的录像文件一共有几个记录库。

mg_rpy_file_cheak()

检查回放文件是否符合版本号和游戏,需要在载入回放文件后使用,这是检查回放文件是否对应游戏的一个手段。

mg_rpy_get_verstr()

返回回放文件的版本号,必须在载入回放文件之后使用。

在最后说明一下,建议各位把什么按键事件什么的都以keyboard_cheak的方式写在步开始事件中,这样会录制更稳定。

以上,就是mage replay的所有函数,大家可以修改使用。因为是在测试阶段,免不了会有什么BUG出现,欢迎大家测试并反馈。也可以在原有脚本的基础上扩展更多好的功能。 
↓↓支持小站发展,点一点小广告,么么哒(づ ̄ 3 ̄)づ↓↓

BB点儿啥

访客
苏念夏 苏念夏2021-06-28 17:13:40 · 回复 下载页面404了啊啊啊啊求助
挺需要这个插件的