Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

浅谈游戏脚本系统 #27

Open
PieroCoding opened this issue May 8, 2016 · 2 comments
Open

浅谈游戏脚本系统 #27

PieroCoding opened this issue May 8, 2016 · 2 comments

Comments

@PieroCoding
Copy link
Member

PieroCoding commented May 8, 2016

最近在看《游戏脚本高级编程》,所以想向大家分享一下书里的内容。不过书已经暂时还回广图,所以我不能翻书,只能全凭记忆写这篇分享,因此如有错误敬请提出。

游戏的组成部分

一个游戏主要包括游戏引擎,游戏脚本,美术和音乐等游戏材料。

游戏引擎,是一个很复杂的系统,包括图形渲染系统、物理碰撞系统等等。而像游戏引擎里的物理碰撞系统,简单来说就是计算两个物体是否碰撞在一起,例如枪战游戏里人物是否中弹啦、哪个部位中弹啦。所以游戏引擎,就是负责一个游戏的计算和渲染的大型程序。

游戏脚本,就是控制剧情和每一个游戏角色行为的背后程序。例如一个NPC,他的行为就是不断行走,然后遇到人就说:“你好。“这就是背后一个程序脚本来控制他的行为。又例如,你已经把小boss打败,下面该打大boss了,剧情脚本就会控制切换画面、更换音乐、导入大boos的脚本。所以游戏脚本,就是控制剧情和控制人物的行为的多个程序。

为什么需要脚本系统

现在多数游戏引擎都由C++写出,当你把一个人物的所有属性都写进游戏引擎时,你编译整个游戏程序将耗费大量时间,所以解决办法就是把各个部分都分离,把一个游戏变成一个个互不相同的模块。于是细分下去,就把剧情任务、人物行为这一部分和游戏引擎那一部分分离了开来。

而且,因为已经有了游戏引擎,若想增加新的剧情,你就可以只写游戏脚本,这样游戏公司就降低了很多成本。就例如有些游戏发布一些新的副本。

虚拟机实现与动态链接程序实现

对于脚本系统,最流行的实现方法有两种,一是像python一样的运行在虚拟机上的动态语言,二是利用游戏引擎提供的接口控制游戏的二进制dll动态链接程序。

对于第一种实现方法,例子有《梦幻西游》。《梦幻西游》的游戏脚本语言是云风修改lua源码后得到的一种lua方言,所以它和正版lua不兼容,又因为lua是一种小众语言,所以使得开发外挂变得困难,这在当时是很成功的。这种实现方法,所有游戏脚本程序都是运行在虚拟机上面的,并不是运行在本地电脑上的二进制程序。

对于第二种实现方法,例子有经典游戏CS。CS是由外国玩家写的mod,他利用《半条命》提供的接口构造了另一种玩法,而这个mod本身是运行在本地电脑上的二进制程序,所以就是相当于插件一样。还有一个著名例子就是Dota啦。

对于虚拟机的实现方法,在运行速度上肯定比不过动态链接程序。但是在编写上更容易,因为虚拟机上运行的是解释型的语言,所以修改后不用编译就马上可以看到改动效果,而动态链接程序还需要编译时间。

在安全性上,动态链接程序因为运行在本地电脑上,所以这个程序的作者可以写一些恶意的代码,例如去扫描你的所有文件,也可以去攻击服务器。同时如果代码质量差,动态链接程序还会容易奔溃,影响到本地电脑。所以动态链接程序安全性应该说是比较差的。

而对于虚拟机的实现方法,因为脚本都运行在虚拟机里,是比较安全的。因为虚拟机可以禁止脚本去访问那些不能访问的地方,而且如果脚本奔溃了还可以没有负担地重启脚本。

举个栗子

例如现有一个类似C++的动态语言,写了一个箱子类
class box
{
function move(event);
function explode(event);
var x;
var y;
};
当人物行走时,游戏引擎会计算人物与箱子的距离,如果人物当前位置和箱子的位置重合了,游戏引擎就会调用箱子的move方法,向move方法发送event。event是一个结构体,是游戏引擎调用脚本方法时发送给脚本的,里面的变量告诉箱子脚本很多信息,包括碰撞力的方向与大小、发出力的物体等等。然后move方法就会根据event结构体来改变box的位置,同时调用游戏引擎的物理系统来计算轨迹,调用渲染系统来显示箱子移动的效果。而控制爆炸的方法explode也是同样的道理,只是调用渲染系统来显示的是爆炸效果,爆炸效果结束后调用渲染系统使自己不再显示,最后脚本退出。

@tangxueer
Copy link

你觉得游戏脚本高级编程这本书怎么样?(正好有朋友要去广图,或许可以借回来看看(^__^))

@PieroCoding
Copy link
Member Author

这本书其实是关于编译原理的一本书,所以我并不推荐用其来学习游戏编程。这本书前两章说了些关于游戏的一些知识(也就是我上面说的),但是后面的章节就很少涉及游戏方面的知识。这本书的组织形式是由游戏脚本编程引出编译原理,例如它后面教如何写汇编器,如何设计一门脚本语言,如何实现运行这个语言的虚拟机等等。

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants