自定义脚本引擎开发纪实 -前序

前序

大家可能对JavaScript,VBScript,Python,Lua,Shell等脚本语言并不陌生,有时候也对Swift语言的特性表现出很大的兴趣。大家在乐此不彼的使用这些语言的时候,有没有想过要自己实现一个脚本引擎呢?(拜托,自己写的能跟那些成熟的比吗?!)话一点错没有,不过通过自己一步步实现一个引擎,从中可以学到不少的知识,也能对现在大家使用的编译器有个旁观的认识。
为了执行的性能,再加一个脚本的“汇编器”;跨平台,给自己的脚本引擎写一个虚拟机,哈哈,也是一种乐趣。

饭呢,要一口一口的吃,事呢要一步一步的做,从简单到复杂,Let’s go!

首先呢,先给要写的脚本引擎一个定位,我们要讲的这个,先定义为嵌入式脚本吧,添加的类库越来越齐全的时候,“经验值”就到了要升级的时刻了,那时,就不仅仅只做潜入式的活了。

要实现的脚本引擎具有的特性

  1. 数值运算,逻辑运算,字符串运算 ,这是基础
  2. 弱类型
  3. 与宿主语言的交互:互相传递参数,互相调用函数,这也是基础。
  4. 支持定义脚本函数
  5. 变量作用域:支持全局变量,局部变量
  6. 支持不定参数(变参
  7. 支持整数,浮点数,字符串
  8. 支持多参数,多返回值
  9. 支持if elseif else, for, foreach, while, switchgoto等指令
  10. 支持二进制数据操作
  11. 支持object,key-value对
  12. 支持struct,与宿主语言处理结构体
  13. 支持调用framework提供的dll中的函数和第三方dll中提供的函数。备注:暂不支持调用类似com导出接口的函数,因为脚本不识别头文件,但可以作为指针去获取值,然后再调用c函数处理。
  14. 方便扩展,方便使用者增加自己的函数(比如:c/c++函数)给脚本调用。
  15. 支持闭包的概念
  16. 支持对变量读写的监控(来自Swift的启发)
    伪代码:
func getter()
...
end
func setter(old_value, new_value)
...
end
script.observer("name", {
   "get"="getter", "set"="setter"})
name="xiaoming" //触发getter,setter
  1. 支持面向对象(类)【类呢,既可以用纯C/C++实现,脚本里实例化和调用方法;也可以直接脚本中定义类】
  2. 支持类变量(类似class中的static变量),类函数(static 函数)
  3. 支持类的继承和函数重写
  4. 支持嵌套子类
  5. 支持 异常机制

缘由

需求千变万化,客户端发版费时费力,无可奈何,回忆下引擎实现的点滴过程,并作为系列文章,分享给大家。

下面是使用脚本生成一个界面的脚本代码,其中files_, regs_变量的值是在客户端里面传递给脚本的

window_width=740
window_height=500
//与xml中一致
logo_ctrl_id=24003
name_ctr_id=24004
element_panel_id=24010
_temp_id=30000
text_ele_clr=0x00aaaaaa

func MakeID()
	_temp_id = _temp_id + 1
	return _temp_id
end

DT_SINGLELINE=0x00000020
DT_PATH_ELLIPSIS=0x00004000
DT_END_ELLIPSIS=0x00008000

dpi=js.system.dpi
func revert_dpi(len)
	return (len * 96 / dpi)
end

bcreate=js.ui.createwindow(window_width,window_height,window_parent);
js.logic.if(!bcreate, "js.debug.abort");

//得到标题的区域
left,_,_,top= js.ui.bound(name_ctr_id);
left = revert_dpi(left)
top = revert_dpi(top)
top = top + 8
foreach(label in labels)
	local panel_id=MakeID();
	js.ui.addpanel(0,panel_id,left,top,100,20,"",label.clr);
	local sta_id=MakeID();
	js.ui.addsta(panel_id, sta_id, left, top, 10000, 1, label.text, "", 0x00ffffff, 9);
	local width, height = js.ui.autosize(sta_id);
	width=revert_dpi(width)
	height=revert_dpi(height)
	js.ui.setrect(panel_id, left, top, width + 10, height + 6);
	js.ui.setrect(sta_id, left + 5, top + 3, width, height
  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值