mirror of
https://github.com/MaSzyna-EU07/maszyna.git
synced 2026-03-22 15:05:03 +01:00
basic lua support
This commit is contained in:
@@ -65,6 +65,7 @@ set(SOURCES
|
||||
"mouseinput.cpp"
|
||||
"translation.cpp"
|
||||
"material.cpp"
|
||||
"lua.cpp"
|
||||
)
|
||||
|
||||
if (WIN32)
|
||||
@@ -125,5 +126,10 @@ find_package(libsndfile REQUIRED)
|
||||
include_directories(${LIBSNDFILE_INCLUDE_DIR})
|
||||
target_link_libraries(${PROJECT_NAME} ${LIBSNDFILE_LIBRARY})
|
||||
|
||||
#set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=address")
|
||||
set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=undefined -g")
|
||||
find_package(LuaJIT REQUIRED)
|
||||
include_directories(${LUAJIT_INCLUDE_DIR})
|
||||
target_link_libraries(${PROJECT_NAME} ${LUAJIT_LIBRARIES})
|
||||
|
||||
if (UNIX)
|
||||
set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=undefined")
|
||||
endif()
|
||||
|
||||
81
CMake_modules/FindLuaJIT.cmake
Normal file
81
CMake_modules/FindLuaJIT.cmake
Normal file
@@ -0,0 +1,81 @@
|
||||
# Locate Lua library
|
||||
# This module defines
|
||||
# LUAJIT_FOUND, if false, do not try to link to Lua
|
||||
# LUAJIT_LIBRARIES
|
||||
# LUAJIT_INCLUDE_DIR, where to find lua.h
|
||||
# LUAJIT_VERSION_STRING, the version of Lua found (since CMake 2.8.8)
|
||||
#
|
||||
# Note that the expected include convention is
|
||||
# #include "lua.h"
|
||||
# and not
|
||||
# #include <lua/lua.h>
|
||||
# This is because, the lua location is not standardized and may exist
|
||||
# in locations other than lua/
|
||||
|
||||
#=============================================================================
|
||||
# Copyright 2007-2009 Kitware, Inc.
|
||||
#
|
||||
# Distributed under the OSI-approved BSD License (the "License");
|
||||
# see accompanying file Copyright.txt for details.
|
||||
#
|
||||
# This software is distributed WITHOUT ANY WARRANTY; without even the
|
||||
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
# See the License for more information.
|
||||
#=============================================================================
|
||||
# (To distribute this file outside of CMake, substitute the full
|
||||
# License text for the above reference.)
|
||||
|
||||
find_path(LUAJIT_INCLUDE_DIR luajit.h
|
||||
HINTS
|
||||
$ENV{LUA_DIR}
|
||||
PATH_SUFFIXES include/luajit-2.0 include
|
||||
PATHS
|
||||
~/Library/Frameworks
|
||||
/Library/Frameworks
|
||||
/sw # Fink
|
||||
/opt/local # DarwinPorts
|
||||
/opt/csw # Blastwave
|
||||
/opt
|
||||
)
|
||||
|
||||
find_library(LUAJIT_LIBRARY
|
||||
NAMES luajit luajit-5.1
|
||||
HINTS
|
||||
$ENV{LUA_DIR}
|
||||
PATH_SUFFIXES lib64 lib
|
||||
PATHS
|
||||
~/Library/Frameworks
|
||||
/Library/Frameworks
|
||||
/sw
|
||||
/opt/local
|
||||
/opt/csw
|
||||
/opt
|
||||
)
|
||||
|
||||
if (LUAJIT_LIBRARY)
|
||||
# include the math library for Unix
|
||||
if (UNIX AND NOT APPLE)
|
||||
find_library(LUAJIT_MATH_LIBRARY m)
|
||||
set(LUAJIT_LIBRARIES "${LUAJIT_LIBRARY};${LUAJIT_MATH_LIBRARY}" CACHE STRING "Lua Libraries")
|
||||
# For Windows and Mac, don't need to explicitly include the math library
|
||||
else ()
|
||||
set(LUAJIT_LIBRARIES "${LUAJIT_LIBRARY}" CACHE STRING "Lua Libraries")
|
||||
endif ()
|
||||
endif ()
|
||||
|
||||
if(LUAJIT_INCLUDE_DIR AND EXISTS "${LUAJIT_INCLUDE_DIR}/lua.h")
|
||||
file(STRINGS "${LUAJIT_INCLUDE_DIR}/lua.h" luajit_version_str REGEX "^#define[ \t]+LUA_RELEASE[ \t]+\"Lua .+\"")
|
||||
|
||||
string(REGEX REPLACE "^#define[ \t]+LUA_RELEASE[ \t]+\"Lua ([^\"]+)\".*" "\\1" LUAJIT_VERSION_STRING "${luajit_version_str}")
|
||||
unset(luajit_version_str)
|
||||
endif()
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
# handle the QUIETLY and REQUIRED arguments and set LUAJIT_FOUND to TRUE if
|
||||
# all listed variables are TRUE
|
||||
find_package_handle_standard_args(LuaJIT
|
||||
REQUIRED_VARS LUAJIT_LIBRARIES LUAJIT_INCLUDE_DIR
|
||||
VERSION_VAR LUAJIT_VERSION_STRING)
|
||||
|
||||
mark_as_advanced(LUAJIT_INCLUDE_DIR LUAJIT_LIBRARIES LUAJIT_LIBRARY LUAJIT_MATH_LIBRARY)
|
||||
|
||||
7
EU07.cpp
7
EU07.cpp
@@ -365,7 +365,7 @@ int main(int argc, char *argv[])
|
||||
}
|
||||
catch (std::runtime_error e)
|
||||
{
|
||||
WriteLog(e.what());
|
||||
ErrorLog(e.what());
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -406,6 +406,11 @@ int main(int argc, char *argv[])
|
||||
ErrorLog( "Critical error, memory allocation failure: " + std::string( Error.what() ) );
|
||||
return -1;
|
||||
}
|
||||
catch (std::runtime_error e)
|
||||
{
|
||||
ErrorLog(e.what());
|
||||
return -1;
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
Console::Off(); // wyłączenie konsoli (komunikacji zwrotnej)
|
||||
|
||||
3
Event.h
3
Event.h
@@ -39,7 +39,8 @@ enum TEventType {
|
||||
tp_Visible,
|
||||
tp_Voltage,
|
||||
tp_Message,
|
||||
tp_Friction
|
||||
tp_Friction,
|
||||
tp_Lua
|
||||
};
|
||||
|
||||
const int update_memstring = 0x0000001; // zmodyfikować tekst (UpdateValues)
|
||||
|
||||
139
Ground.cpp
139
Ground.cpp
@@ -1761,6 +1761,72 @@ void TGround::FirstInit()
|
||||
WriteLog("FirstInit is done");
|
||||
};
|
||||
|
||||
void TGround::add_event(TEvent *tmp)
|
||||
{
|
||||
if (tmp->Type == tp_Unknown)
|
||||
delete tmp;
|
||||
else
|
||||
{ // najpierw sprawdzamy, czy nie ma, a potem dopisujemy
|
||||
TEvent *found = FindEvent(tmp->asName);
|
||||
if (found)
|
||||
{ // jeśli znaleziony duplikat
|
||||
auto const size = tmp->asName.size();
|
||||
if( tmp->asName[0] == '#' ) // zawsze jeden znak co najmniej jest
|
||||
{
|
||||
delete tmp;
|
||||
tmp = nullptr;
|
||||
} // utylizacja duplikatu z krzyżykiem
|
||||
else if( ( size > 8 )
|
||||
&& ( tmp->asName.substr( 0, 9 ) == "lineinfo:" ))
|
||||
// tymczasowo wyjątki
|
||||
{
|
||||
delete tmp;
|
||||
tmp = nullptr;
|
||||
} // tymczasowa utylizacja duplikatów W5
|
||||
else if( ( size > 8 )
|
||||
&& ( tmp->asName.substr( size - 8 ) == "_warning"))
|
||||
// tymczasowo wyjątki
|
||||
{
|
||||
delete tmp;
|
||||
tmp = nullptr;
|
||||
} // tymczasowa utylizacja duplikatu z trąbieniem
|
||||
else if( ( size > 4 )
|
||||
&& ( tmp->asName.substr( size - 4 ) == "_shp" ))
|
||||
// nie podlegają logowaniu
|
||||
{
|
||||
delete tmp;
|
||||
tmp = NULL;
|
||||
} // tymczasowa utylizacja duplikatu SHP
|
||||
if (tmp) // jeśli nie został zutylizowany
|
||||
if (Global::bJoinEvents)
|
||||
found->Append(tmp); // doczepka (taki wirtualny multiple bez warunków)
|
||||
else
|
||||
{
|
||||
ErrorLog("Duplicated event: " + tmp->asName);
|
||||
found->Append(tmp); // doczepka (taki wirtualny multiple bez warunków)
|
||||
found->Type = tp_Ignored; // dezaktywacja pierwotnego - taka proteza na
|
||||
// wsteczną zgodność
|
||||
// SafeDelete(tmp); //bezlitośnie usuwamy wszelkie duplikaty, żeby nie
|
||||
// zaśmiecać drzewka
|
||||
}
|
||||
}
|
||||
if ( nullptr != tmp )
|
||||
{ // jeśli nie duplikat
|
||||
tmp->evNext2 = RootEvent; // lista wszystkich eventów (m.in. do InitEvents)
|
||||
RootEvent = tmp;
|
||||
if (!found)
|
||||
{ // jeśli nazwa wystąpiła, to do kolejki i wyszukiwarki dodawany jest tylko pierwszy
|
||||
if( ( RootEvent->Type != tp_Ignored )
|
||||
&& ( RootEvent->asName.find( "onstart" ) != std::string::npos ) ) {
|
||||
// event uruchamiany automatycznie po starcie
|
||||
AddToQuery( RootEvent, NULL ); // dodanie do kolejki
|
||||
}
|
||||
m_eventmap.emplace( tmp->asName, tmp ); // dodanie do wyszukiwarki
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool TGround::Init(std::string File)
|
||||
{ // główne wczytywanie scenerii
|
||||
if (ToLower(File).substr(0, 7) == "scenery")
|
||||
@@ -1920,68 +1986,14 @@ bool TGround::Init(std::string File)
|
||||
{
|
||||
TEvent *tmp = new TEvent();
|
||||
tmp->Load(&parser, &pOrigin);
|
||||
if (tmp->Type == tp_Unknown)
|
||||
delete tmp;
|
||||
else
|
||||
{ // najpierw sprawdzamy, czy nie ma, a potem dopisujemy
|
||||
TEvent *found = FindEvent(tmp->asName);
|
||||
if (found)
|
||||
{ // jeśli znaleziony duplikat
|
||||
auto const size = tmp->asName.size();
|
||||
if( tmp->asName[0] == '#' ) // zawsze jeden znak co najmniej jest
|
||||
{
|
||||
delete tmp;
|
||||
tmp = nullptr;
|
||||
} // utylizacja duplikatu z krzyżykiem
|
||||
else if( ( size > 8 )
|
||||
&& ( tmp->asName.substr( 0, 9 ) == "lineinfo:" ))
|
||||
// tymczasowo wyjątki
|
||||
{
|
||||
delete tmp;
|
||||
tmp = nullptr;
|
||||
} // tymczasowa utylizacja duplikatów W5
|
||||
else if( ( size > 8 )
|
||||
&& ( tmp->asName.substr( size - 8 ) == "_warning"))
|
||||
// tymczasowo wyjątki
|
||||
{
|
||||
delete tmp;
|
||||
tmp = nullptr;
|
||||
} // tymczasowa utylizacja duplikatu z trąbieniem
|
||||
else if( ( size > 4 )
|
||||
&& ( tmp->asName.substr( size - 4 ) == "_shp" ))
|
||||
// nie podlegają logowaniu
|
||||
{
|
||||
delete tmp;
|
||||
tmp = NULL;
|
||||
} // tymczasowa utylizacja duplikatu SHP
|
||||
if (tmp) // jeśli nie został zutylizowany
|
||||
if (Global::bJoinEvents)
|
||||
found->Append(tmp); // doczepka (taki wirtualny multiple bez warunków)
|
||||
else
|
||||
{
|
||||
ErrorLog("Duplicated event: " + tmp->asName);
|
||||
found->Append(tmp); // doczepka (taki wirtualny multiple bez warunków)
|
||||
found->Type = tp_Ignored; // dezaktywacja pierwotnego - taka proteza na
|
||||
// wsteczną zgodność
|
||||
// SafeDelete(tmp); //bezlitośnie usuwamy wszelkie duplikaty, żeby nie
|
||||
// zaśmiecać drzewka
|
||||
}
|
||||
}
|
||||
if ( nullptr != tmp )
|
||||
{ // jeśli nie duplikat
|
||||
tmp->evNext2 = RootEvent; // lista wszystkich eventów (m.in. do InitEvents)
|
||||
RootEvent = tmp;
|
||||
if (!found)
|
||||
{ // jeśli nazwa wystąpiła, to do kolejki i wyszukiwarki dodawany jest tylko pierwszy
|
||||
if( ( RootEvent->Type != tp_Ignored )
|
||||
&& ( RootEvent->asName.find( "onstart" ) != std::string::npos ) ) {
|
||||
// event uruchamiany automatycznie po starcie
|
||||
AddToQuery( RootEvent, NULL ); // dodanie do kolejki
|
||||
}
|
||||
m_eventmap.emplace( tmp->asName, tmp ); // dodanie do wyszukiwarki
|
||||
}
|
||||
}
|
||||
}
|
||||
add_event(tmp);
|
||||
}
|
||||
else if (str == "lua")
|
||||
{
|
||||
parser.getTokens();
|
||||
std::string file;
|
||||
parser >> file;
|
||||
m_lua.interpret(subpath + file);
|
||||
}
|
||||
else if (str == "rotate")
|
||||
{
|
||||
@@ -3445,6 +3457,9 @@ bool TGround::CheckQuery()
|
||||
break;
|
||||
case tp_Message: // wyświetlenie komunikatu
|
||||
break;
|
||||
case tp_Lua:
|
||||
((lua::eventhandler_t)tmpEvent->Params[0].asPointer)(tmpEvent, tmpEvent->Activator);
|
||||
break;
|
||||
} // switch (tmpEvent->Type)
|
||||
} // if (tmpEvent->bEnabled)
|
||||
} // while
|
||||
|
||||
4
Ground.h
4
Ground.h
@@ -20,6 +20,7 @@ http://mozilla.org/MPL/2.0/.
|
||||
#include "Float3d.h"
|
||||
#include "Names.h"
|
||||
#include "lightarray.h"
|
||||
#include "lua.h"
|
||||
|
||||
typedef int TGroundNodeType;
|
||||
// Ra: zmniejszone liczby, aby zrobić tabelkę i zoptymalizować wyszukiwanie
|
||||
@@ -260,6 +261,7 @@ class TGround
|
||||
event_map m_eventmap;
|
||||
TNames<TGroundNode *> m_trackmap;
|
||||
light_array m_lights; // collection of dynamic light sources present in the scene
|
||||
lua m_lua;
|
||||
|
||||
vector3 pOrigin;
|
||||
vector3 aRotate;
|
||||
@@ -342,6 +344,8 @@ class TGround
|
||||
void IsolatedBusyList();
|
||||
void IsolatedBusy(const std::string t);
|
||||
void Silence(vector3 gdzie);
|
||||
|
||||
void add_event(TEvent *event);
|
||||
};
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
3
World.h
3
World.h
@@ -121,7 +121,6 @@ private:
|
||||
|
||||
TCamera Camera;
|
||||
TCamera DebugCamera;
|
||||
TGround Ground;
|
||||
world_environment Environment;
|
||||
TTrain *Train;
|
||||
TDynamicObject *pDynamicNearest;
|
||||
@@ -147,6 +146,8 @@ private:
|
||||
void CabChange(TDynamicObject *old, TDynamicObject *now);
|
||||
// handles vehicle change flag
|
||||
void ChangeDynamic();
|
||||
|
||||
TGround Ground; //m7todo: tmp
|
||||
};
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
@@ -15,5 +15,7 @@ cmake ../.. -T v140_xp ^
|
||||
-DOPENAL_INCLUDE_DIR=%DEPS_DIR%/openal/include ^
|
||||
-DOPENAL_LIBRARY=%DEPS_DIR%/openal/lib/win32/OpenAL32.lib ^
|
||||
-DLIBSNDFILE_INCLUDE_DIR=%DEPS_DIR%/libsndfile/include ^
|
||||
-DLIBSNDFILE_LIBRARY=%DEPS_DIR%/libsndfile/lib/win32/libsndfile-1.lib
|
||||
-DLIBSNDFILE_LIBRARY=%DEPS_DIR%/libsndfile/lib/win32/libsndfile-1.lib ^
|
||||
-DLUAJIT_INCLUDE_DIR=%DEPS_DIR%/luajit/include ^
|
||||
-DLUAJIT_LIBRARIES=%DEPS_DIR%/luajit/lib/win32/lua51.lib
|
||||
popd
|
||||
@@ -15,5 +15,7 @@ cmake ../.. -A x64 ^
|
||||
-DOPENAL_INCLUDE_DIR=%DEPS_DIR%/openal/include ^
|
||||
-DOPENAL_LIBRARY=%DEPS_DIR%/openal/lib/win64/OpenAL32.lib ^
|
||||
-DLIBSNDFILE_INCLUDE_DIR=%DEPS_DIR%/libsndfile/include ^
|
||||
-DLIBSNDFILE_LIBRARY=%DEPS_DIR%/libsndfile/lib/win64/libsndfile-1.lib
|
||||
-DLIBSNDFILE_LIBRARY=%DEPS_DIR%/libsndfile/lib/win64/libsndfile-1.lib ^
|
||||
-DLUAJIT_INCLUDE_DIR=%DEPS_DIR%/luajit/include ^
|
||||
-DLUAJIT_LIBRARIES=%DEPS_DIR%/luajit/lib/win64/lua51.lib
|
||||
popd
|
||||
@@ -1,2 +1,2 @@
|
||||
powershell "$wc = New-Object System.Net.WebClient; $wc.DownloadFile(\"https://milek7.pl/.stuff/eu07exe/builddep2.zip\", \"%cd%\deps_win.zip\")"
|
||||
powershell "$s = New-Object -ComObject shell.application; $z = $s.Namespace(\"%cd%\deps_win.zip\"); foreach ($i in $z.items()) { $s.Namespace(\"%cd%\").CopyHere($i) }"
|
||||
powershell "$wc = New-Object System.Net.WebClient; $wc.DownloadFile(\"https://milek7.pl/.stuff/eu07exe/builddep3.zip\", \"%cd%\deps_win.zip\")"
|
||||
powershell "$s = New-Object -ComObject shell.application; $z = $s.Namespace(\"%cd%\deps_win.zip\"); foreach ($i in $z.items()) { $s.Namespace(\"%cd%\").CopyHere($i) }"
|
||||
|
||||
170
lua.cpp
Normal file
170
lua.cpp
Normal file
@@ -0,0 +1,170 @@
|
||||
#include "stdafx.h"
|
||||
#include "lua.h"
|
||||
#include "Event.h"
|
||||
#include "Logs.h"
|
||||
#include "MemCell.h"
|
||||
#include "World.h"
|
||||
#include "Driver.h"
|
||||
#include "lua_ffi.h"
|
||||
|
||||
extern TWorld World;
|
||||
|
||||
lua::lua()
|
||||
{
|
||||
state = luaL_newstate();
|
||||
if (!state)
|
||||
throw std::runtime_error("cannot create lua state");
|
||||
lua_atpanic(state, atpanic);
|
||||
luaL_openlibs(state);
|
||||
|
||||
lua_getglobal(state, "package");
|
||||
lua_pushstring(state, "preload");
|
||||
lua_gettable(state, -2);
|
||||
lua_pushcclosure(state, openffi, 0);
|
||||
lua_setfield(state, -2, "eu07.events");
|
||||
lua_settop(state, 0);
|
||||
}
|
||||
|
||||
lua::~lua()
|
||||
{
|
||||
lua_close(state);
|
||||
state = nullptr;
|
||||
}
|
||||
|
||||
void lua::interpret(std::string file)
|
||||
{
|
||||
if (luaL_dofile(state, file.c_str()))
|
||||
throw std::runtime_error(lua_tostring(state, -1));
|
||||
}
|
||||
|
||||
// NOTE: we cannot throw exceptions in callbacks
|
||||
// because it is not supported by LuaJIT on x86 windows
|
||||
|
||||
int lua::atpanic(lua_State *s)
|
||||
{
|
||||
ErrorLog(std::string(lua_tostring(s, -1)));
|
||||
return 0;
|
||||
}
|
||||
|
||||
int lua::openffi(lua_State *s)
|
||||
{
|
||||
if (luaL_dostring(s, lua_ffi))
|
||||
{
|
||||
ErrorLog(std::string(lua_tostring(s, -1)));
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
extern "C"
|
||||
{
|
||||
TEvent* scriptapi_event_create(const char* name, lua::eventhandler_t handler, double delay)
|
||||
{
|
||||
TEvent *event = new TEvent();
|
||||
event->bEnabled = true;
|
||||
event->Type = tp_Lua;
|
||||
event->asName = std::string(name);
|
||||
event->fDelay = delay;
|
||||
event->Params[0].asPointer = (void*)handler;
|
||||
World.Ground.add_event(event);
|
||||
return event;
|
||||
}
|
||||
|
||||
TEvent* scriptapi_event_find(const char* name)
|
||||
{
|
||||
std::string str(name);
|
||||
TEvent *e = World.Ground.FindEvent(str);
|
||||
if (e)
|
||||
return e;
|
||||
else
|
||||
WriteLog("missing event: " + str);
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
TTrack* scriptapi_track_find(const char* name)
|
||||
{
|
||||
std::string str(name);
|
||||
TGroundNode *n = World.Ground.FindGroundNode(str, TP_TRACK);
|
||||
if (n)
|
||||
return n->pTrack;
|
||||
else
|
||||
WriteLog("missing track: " + str);
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
bool scriptapi_track_isoccupied(TTrack* track)
|
||||
{
|
||||
if (track)
|
||||
return !track->IsEmpty();
|
||||
return false;
|
||||
}
|
||||
|
||||
const char* scriptapi_event_getname(TEvent *e)
|
||||
{
|
||||
if (e)
|
||||
return e->asName.c_str();
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
const char* scriptapi_train_getname(TDynamicObject *dyn)
|
||||
{
|
||||
if (dyn && dyn->Mechanik)
|
||||
return dyn->Mechanik->TrainName().c_str();
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void scriptapi_event_dispatch(TEvent *e, TDynamicObject *activator)
|
||||
{
|
||||
if (e)
|
||||
World.Ground.AddToQuery(e, activator);
|
||||
}
|
||||
|
||||
double scriptapi_random(double a, double b)
|
||||
{
|
||||
return Random(a, b);
|
||||
}
|
||||
|
||||
void scriptapi_writelog(const char* txt)
|
||||
{
|
||||
WriteLog("lua log: " + std::string(txt));
|
||||
}
|
||||
|
||||
struct memcell_values { const char *str; double num1; double num2; };
|
||||
|
||||
TMemCell* scriptapi_memcell_find(const char *name)
|
||||
{
|
||||
std::string str(name);
|
||||
TGroundNode *n = World.Ground.FindGroundNode(str, TP_MEMCELL);
|
||||
if (n)
|
||||
return n->MemCell;
|
||||
else
|
||||
WriteLog("missing memcell: " + str);
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
memcell_values scriptapi_memcell_read(TMemCell *mc)
|
||||
{
|
||||
if (!mc)
|
||||
return { nullptr, 0.0, 0.0 };
|
||||
return { mc->Text().c_str(), mc->Value1(), mc->Value2() };
|
||||
}
|
||||
|
||||
void scriptapi_memcell_update(TMemCell *mc, const char *str, double num1, double num2)
|
||||
{
|
||||
if (!mc)
|
||||
return;
|
||||
mc->UpdateValues(std::string(str), num1, num2,
|
||||
update_memstring | update_memval1 | update_memval2);
|
||||
}
|
||||
|
||||
void scriptapi_dynobj_putvalues(TDynamicObject *dyn, const char *str, double num1, double num2)
|
||||
{
|
||||
if (!dyn)
|
||||
return;
|
||||
TLocation loc;
|
||||
if (dyn->Mechanik)
|
||||
dyn->Mechanik->PutCommand(std::string(str), num1, num2, nullptr);
|
||||
else
|
||||
dyn->MoverParameters->PutCommand(std::string(str), num1, num2, loc);
|
||||
}
|
||||
}
|
||||
21
lua.h
Normal file
21
lua.h
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <lua.hpp>
|
||||
|
||||
class TEvent;
|
||||
class TDynamicObject;
|
||||
|
||||
class lua
|
||||
{
|
||||
lua_State *state;
|
||||
|
||||
static int atpanic(lua_State *s);
|
||||
static int openffi(lua_State *s);
|
||||
|
||||
public:
|
||||
lua();
|
||||
~lua();
|
||||
|
||||
void interpret(std::string file);
|
||||
|
||||
typedef void (*eventhandler_t)(TEvent*, TDynamicObject*);
|
||||
};
|
||||
78
lua_ffi.h
Normal file
78
lua_ffi.h
Normal file
@@ -0,0 +1,78 @@
|
||||
const char lua_ffi[] = "local ffi = require(\"ffi\")\n"
|
||||
"ffi.cdef[[\n"
|
||||
"struct memcell_values { const char *str; double num1; double num2; };\n"
|
||||
"\n"
|
||||
"typedef struct TEvent TEvent;\n"
|
||||
"typedef struct TTrack TTrack;\n"
|
||||
"typedef struct TDynamicObject TDynamicObject;\n"
|
||||
"typedef struct TMemCell TMemCell;\n"
|
||||
"typedef struct memcell_values memcell_values;\n"
|
||||
"\n"
|
||||
"TEvent* scriptapi_event_create(const char* name, void (*handler)(TEvent*, TDynamicObject*), double delay);\n"
|
||||
"TEvent* scriptapi_event_find(const char* name);\n"
|
||||
"const char* scriptapi_event_getname(TEvent *e);\n"
|
||||
"void scriptapi_event_dispatch(TEvent *e, TDynamicObject *activator);\n"
|
||||
"\n"
|
||||
"TTrack* scriptapi_track_find(const char* name);\n"
|
||||
"bool scriptapi_track_isoccupied(TTrack *track);\n"
|
||||
"\n"
|
||||
"const char* scriptapi_train_getname(TDynamicObject *dyn);\n"
|
||||
"void scriptapi_dynobj_putvalues(TDynamicObject *dyn, const char *str, double num1, double num2);\n"
|
||||
"\n"
|
||||
"TMemCell* scriptapi_memcell_find(const char *name);\n"
|
||||
"memcell_values scriptapi_memcell_read(TMemCell *mc);\n"
|
||||
"void scriptapi_memcell_update(TMemCell *mc, const char *str, double num1, double num2);\n"
|
||||
"\n"
|
||||
"double scriptapi_random(double a, double b);\n"
|
||||
"void scriptapi_writelog(const char* txt);\n"
|
||||
"]]\n"
|
||||
"\n"
|
||||
"local ns = ffi.C\n"
|
||||
"\n"
|
||||
"local module = {}\n"
|
||||
"\n"
|
||||
"module.event_create = ns.scriptapi_event_create\n"
|
||||
"module.event_find = ns.scriptapi_event_find\n"
|
||||
"function module.event_getname(a)\n"
|
||||
" return ffi.string(ns.scriptapi_event_getname(a))\n"
|
||||
"end\n"
|
||||
"module.event_dispatch = ns.scriptapi_event_dispatch\n"
|
||||
"function module.event_dispatch_n(a, b)\n"
|
||||
" ns.scriptapi_event_dispatch(ns.scriptapi_event_find(a), b)\n"
|
||||
"end\n"
|
||||
"\n"
|
||||
"module.track_find = ns.scriptapi_track_find\n"
|
||||
"module.track_isoccupied = ns.scriptapi_track_isoccupied\n"
|
||||
"function module.track_isoccupied_n(a)\n"
|
||||
" return ns.scriptapi_track_isoccupied(ns.scriptapi_track_find(a))\n"
|
||||
"end\n"
|
||||
"\n"
|
||||
"function module.train_getname(a)\n"
|
||||
" return ffi.string(ns.scriptapi_train_getname(a))\n"
|
||||
"end\n"
|
||||
"function module.dynobj_putvalues(a, b)\n"
|
||||
" ns.scriptapi_dynobj_putvalues(a, b.str, b.num1, b.num2)\n"
|
||||
"end\n"
|
||||
"\n"
|
||||
"module.memcell_find = ns.scriptapi_memcell_find\n"
|
||||
"function module.memcell_read(a)\n"
|
||||
" native = ns.scriptapi_memcell_read(a)\n"
|
||||
" mc = { }\n"
|
||||
" mc.str = ffi.string(native.str)\n"
|
||||
" mc.num1 = native.num1\n"
|
||||
" mc.num2 = native.num2\n"
|
||||
" return mc\n"
|
||||
"end\n"
|
||||
"function module.memcell_read_n(a)\n"
|
||||
" return module.memcell_read(ns.scriptapi_memcell_find(a))\n"
|
||||
"end\n"
|
||||
"function module.memcell_update(a, b)\n"
|
||||
" ns.scriptapi_memcell_update(a, b.str, b.num1, b.num2)\n"
|
||||
"end\n"
|
||||
"function module.memcell_update_n(a, b)\n"
|
||||
" ns.scriptapi_memcell_update(ns.scriptapi_memcell_find(a), b.str, b.num1, b.num2)\n"
|
||||
"end\n"
|
||||
"\n"
|
||||
"module.random = ns.scriptapi_random\n"
|
||||
"module.writelog = ns.scriptapi_writelog\n"
|
||||
"\nreturn module\n";
|
||||
Reference in New Issue
Block a user