[{"data":1,"prerenderedAt":172},["ShallowReactive",2],{"page-lua-1":3,"page-count-lua":171},[4],{"id":5,"title":6,"body":7,"date":147,"description":13,"extension":148,"meta":149,"navigation":152,"path":164,"seo":165,"stem":166,"tags":167,"__hash__":170},"blogs\u002F_legacy\u002F2018\u002F2018-05-09-ue4-and-sol2.md","UE4中Sol2的接入",{"type":8,"value":9,"toc":139},"minimark",[10,14,17,20,31,36,39,42,45,48,51,54,57,61,64,67,70,73,76,87,90,94,97,100,106,109,112,115,118,121,127,130],[11,12,13],"p",{},"虽然说Lua的C++接入本身在网上能找到很多示例，但是在尝试对Sol2进行接入的时候还是遇到了一些问题，所以在此进行记录。",[11,15,16],{},"当前使用的UE4版本为4.19.1。",[11,18,19],{},"Sol2是进行Lua绑定的C++类库，过程中最主要的问题是，对Lua本身一知半解，所以没有很好的理解Sol2官方文档中所描述的一些术语。",[11,21,22,23,30],{},"之所以会选择Sol2，是因为它号称自己是[",[24,25,29],"a",{"href":26,"rel":27},"http:\u002F\u002Fsol2.readthedocs.io\u002Fen\u002Flatest\u002Fbenchmarks.html",[28],"nofollow","地上最快","]的~",[32,33,35],"h2",{"id":34},"luajit","LuaJit",[11,37,38],{},"似乎lua本身的脚本解释器有两个公开的版本，一个是LuaJit，一个是vanilla Lua。",[11,40,41],{},"由于没有仔细的对这两者之间的差别进行区分，所以并不是特别清楚其中的具体区别。",[11,43,44],{},"直接Google的话，Lua是指向vanilla lua的，而且LuaJit的Lua版本也比较靠前。",[11,46,47],{},"但是由于Sol2的官方文档中说LuaJit的速度会比较快，所以就采用了LuaJit。",[11,49,50],{},"那么首先第一步就是下载LuaJit，到了这一步就比较明了了。",[11,52,53],{},"LuaJit有提供CMake的配置文件，用CMake配置一下之后就可以进行生成了。",[11,55,56],{},"对于下一步的接入需要的是生成的Lua51.lib和Lua51.dll。",[32,58,60],{"id":59},"sol2","Sol2",[11,62,63],{},"这个库本身也有提供CMake，直接使用CMake配置就好了。",[11,65,66],{},"但是遇到的主要问题是，在和LuaJit的对接上，不过实际上在对整个库进行理清之后就不会有什么问题。",[11,68,69],{},"Sol2有提供很多的Test所以在使用方面会有很多的便利。",[11,71,72],{},"不过这里用CMake进行配置其实是不必要的，Sol2本身有提供单文件版本，其实只要include就可以了。",[11,74,75],{},"但是LuaJit的话还是需要进行链接的，并且必须根据使用的Lua解释器的不同来提供不同的宏。基本这样包含就可以了：",[77,78,83],"pre",{"className":79,"code":81,"language":82},[80],"language-text","extern \"C\"\n{\n#include \u003Clua.h>\n#include \u003Clualib.h>\n#include \u003Clauxlib.h>\n}\n\n#define SOL_USING_CXX_LUA        1\n#define SOL_USING_CXX_LUAJIT    1\n#include \"sol.hpp\"\n","text",[84,85,81],"code",{"__ignoreMap":86},"",[11,88,89],{},"最主要的是前面的Extern “C”不能忘记，不然会报很多的链接错误~",[32,91,93],{"id":92},"ue4插件接入","UE4插件接入",[11,95,96],{},"据说以前Sol2接入的话会有一些问题，因为sol2本身对check有定义，所以会造成定冲突。",[11,98,99],{},"于是sol2的作者后面给出了解决方案：",[77,101,104],{"className":102,"code":103,"language":82},[80],"#if defined(UE_BUILD_DEBUG) || defined(UE_BUILD_DEVELOPMENT) || defined(UE_BUILD_TEST) || defined(UE_BUILD_SHIPPING) || defined(UE_SERVER)\n#define SOL_INSIDE_UNREAL\n#endif \u002F\u002F Unreal Engine 4 bullshit\n\n#ifdef SOL_INSIDE_UNREAL\n#ifdef check\n#define SOL_INSIDE_UNREAL_REMOVED_CHECK\n#undef check\n#endif\n#endif \u002F\u002F Unreal Engine 4 Bullshit\n",[84,105,103],{"__ignoreMap":86},[11,107,108],{},"总之就是回避了一下：D",[11,110,111],{},"不过说到UE4兼容，最近VA也新增了对UE4的特别支持。记得一开始的时候，VA经常在对UE4的函数进行跳转的时候崩掉VS，而且还有一定几率的崩掉VA建立的代码解析缓存，然后需要重新进行一次代码解析，非常的欢乐。",[11,113,114],{},"不过新增的UE4支持还没有完全的测试过，不知实际上有什么改进还不是特别的清楚呢~",[32,116,117],{"id":117},"测试",[11,119,120],{},"最后在UE4中使用蓝图函数进行了简单的测试：",[77,122,125],{"className":123,"code":124,"language":82},[80],"UE_LOG(LogTemp,Log, TEXT(\"=== basic ===\"));\n\n\u002F\u002F create an empty lua state\nsol::state lua;\n\n\u002F\u002F by default, libraries are not opened\n\u002F\u002F you can open libraries by using open_libraries\n\u002F\u002F the libraries reside in the sol::lib enum class\nlua.open_libraries(sol::lib::base);\n\u002F\u002F you can open all libraries by passing no arguments\n\u002F\u002Flua.open_libraries();\n\n\u002F\u002F call lua code directly\nlua.script(\"print('hello world')\");\n\n\u002F\u002F call lua code, and check to make sure it has loaded and run properly:\nauto handler = &sol::script_default_on_error;\nlua.script(\"print('hello again, world')\", handler);\n\n\u002F\u002F Use a custom error handler if you need it\n\u002F\u002F This gets called when the result is bad\nauto simple_handler = [](lua_State*, sol::protected_function_result result) {\n\u002F\u002F You can just pass it through to let the call-site handle it\n  return result;\n};\n\u002F\u002F the above lambda is identical to sol::simple_on_error, but it's\n\u002F\u002F shown here to show you can write whatever you like\n\n\u002F\u002F\n{\n  auto result = lua.script(\"print('hello hello again, world') \\n return 24\", simple_handler);\n  if (result.valid()) {\n    UE_LOG(LogTemp, Log, TEXT(\"the third script worked, and a double-hello statement should appear above this one!\"));\n    int value = result;\n    ensure(value == 24);\n  }\n  else {\n    UE_LOG(LogTemp, Log, TEXT(\"the third script failed, check the result type for more information!\"));\n  }\n}\n\n\u002F**    \u003CThis test will log out 0xE24C4A03 *\u002F\n{\n  auto result = lua.script(\"does.not.exist\", simple_handler);\n  if (result.valid()) {\n    UE_LOG(LogTemp, Log, TEXT(\"the fourth script worked, which it wasn't supposed to! Panic!\"));\n    int value = result;\n    ensure(value == 24);\n  }\n  else {\n    sol::error err = result;\n    UE_LOG(LogTemp, Log, TEXT(\"the fourth script failed, which was intentional! nError: %s\"), ANSI_TO_TCHAR(err.what()));\n  }\n}\n",[84,126,124],{"__ignoreMap":86},[11,128,129],{},"由于接下来还没有具体的使用计划，所以就在这里了。",[11,131,132,133,138],{},"绑定好的Sol2插件可以到Github上下载：[",[24,134,137],{"href":135,"rel":136},"https:\u002F\u002Fgithub.com\u002FArisego\u002FSol2UE4",[28],"Sol2UE4","]，这样有需要的童鞋就没有必要重新再绑一遍了~",{"title":86,"searchDepth":140,"depth":141,"links":142},2,3,[143,144,145,146],{"id":34,"depth":140,"text":35},{"id":59,"depth":140,"text":60},{"id":92,"depth":140,"text":93},{"id":117,"depth":140,"text":117},"2018-05-09","md",{"layout":150,"status":151,"published":152,"author":153,"author_login":155,"author_email":156,"wordpress_id":157,"wordpress_url":158,"date_gmt":159,"excerpt":160},"post","publish",true,{"display_name":154,"login":155,"email":156,"url":86},"风铃","flinkor","flinkor@foxmail.com",2352,"\u002F?p=2352","2018-05-09 15:25:11 +0000",{"type":8,"value":161},[162],[11,163,13],{},"\u002F2018-05-09-ue4-and-sol2",{"title":6,"description":13},"_legacy\u002F2018\u002F2018-05-09-ue4-and-sol2",[168,60,169],"UE4","lua","AN5DDWVMtt3GIYCq4gzzCGWkoUTmUT45hP9SOx1QSL0",1,1788763179258]