在自己的工程中嵌入Lua脚本引擎

Lua语言被不少大软件作为脚本语言,因为通过Lua语言,可以很方便地调用大型程序中的已有函数,这样可以将业务逻辑与算法逻辑分离开。我们也可以在自己的软件中,嵌入lua语言,预留API给用户做更多的自定义操作(如脚本编辑器)。本文谈Lua源码的编译、以及如何在自己的C程序中嵌入Lua。
有正在学习Lua的朋友,可以进Q群121811911下载软件资料和视频,我们一起进步。

编译Lua

在Lua官网的http://www.lua.org/download.html页面,可以下载到各个版本的Lua源码。源码的结构分为以下几个目录:

  • doc:文档

  • etc:方便学习的lua源码,是工程级别的lua的子集,含Makefile

  • source:lua源代码,含Makefile

  • test:一些Lua脚本,用于测试

根据源文件生成Lua,最终的结果有几种选择:

  • Lua library:静态的Lua库,这样,配合Lua的头文件,就可以将Lua嵌入到自己的程序中了

  • Standalone Lua:Lua解释器,可以读取Lua脚本并执行

  • Luac:lua编译器,将Lua脚本翻译成Lua字节码,这样可以加快Lua脚本的加载速度

源码附带的Makefile,没有针对Windows VS平台的选项。不过不用担心,自己根据需要,建个空工程,再把各个文件添加进去,就可以编译成功了。其中luac与lua需要建立的是控制台空工程,静态库需要建立的是静态库空工程(链接方式不一样)。

嵌入Lua

编译好lualib后,就可以配合头文件,在自己的C++程序中调用Lua了,以下是一个简单例子,它加载并执行一个Lua脚本"hello,lua":


    extern "C" {

    #include "LuaHeader/lua.h"

    #include "LuaHeader/lualib.h"

    #include "LuaHeader/lauxlib.h"

    }

    

    int main(int argc, char *argv[])

    {

        int s = 0;

    

        lua_State *L = lua_open();

        // load the libs

        luaL_openlibs(L);

        //run a Lua scrip here

        luaL_dofile(L, "hello.lua");

    

        lua_close(L);

        return 1;

    }

因为Lua是C语言写的,为了链接正常,注意要extern "C"。以下是hello.lua脚本的内容,它也可以修改为其它符合lua语法的脚本:


    io.write("Please enter your name: ")

    name = io.read()

    io.write("Hi " .. string.format("%s",name) .. ", enjoy hacking with Lua\r\n");

用Lua中调用host程序的函数

lua常被选为各大程序的内嵌脚本语言的原因,就是它可以将host program的函数,注册为API供lua调用,这样可以使编程的逻辑易于调整。以下是一个特别简单的例子:


    // function type must be lua_CFunction

    extern "C" static int MYAPI_ShowHello(lua_State *L)

    {

        printf("Hello, World\r\n");

        return 1;

    }

    

    int main(int argc, char *argv[])

    {

        int s = 0;

    

        lua_State *lua = lua_open();

        // load the libs

        luaL_openlibs(lua);

        

        // register C function into lua

        lua_pushcclosure(lua, MYAPI_ShowHello, 0);

        lua_setglobal(lua, "myHello");

    

        //run a Lua scrip here

        luaL_dofile(lua, "hello.lua");

    

        lua_close(lua);

        return 1;

    }

通过以上pushcclosure与setglobal的注册,在lua中可以通过调用"myHello"来间接调用host程序的MYAPI_ShowHello函数。


"hello.lua"中的内容:

    myHello()

更多的内容,需要学习Lua的API。也可以进Q群121811911下载软件资料和视频。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。