mirror of
https://github.com/coop-deluxe/sm64coopdx.git
synced 2026-04-05 09:46:28 +00:00
Add support for Lua functions inside parameters
This commit is contained in:
parent
816df2117f
commit
bbeec3c707
9 changed files with 85 additions and 6 deletions
|
|
@ -46,6 +46,9 @@ def translate_type_to_lvt(ptype):
|
|||
if ptype == 'float':
|
||||
return 'LVT_F32'
|
||||
|
||||
if ptype == 'LuaFunction':
|
||||
return 'LVT_LUAFUNCTION'
|
||||
|
||||
if 'struct' in ptype:
|
||||
if ptype.count('*') > 1:
|
||||
return 'LVT_???'
|
||||
|
|
@ -91,6 +94,9 @@ def translate_type_to_lot(ptype):
|
|||
if ptype == 'float':
|
||||
return 'LOT_NONE'
|
||||
|
||||
if ptype == 'LuaFunction':
|
||||
return 'LOT_NONE'
|
||||
|
||||
if 'struct' in ptype:
|
||||
if ptype.count('*') > 1:
|
||||
return 'LOT_???'
|
||||
|
|
@ -132,6 +138,9 @@ def translate_type_to_lua(ptype):
|
|||
if 'void' == ptype:
|
||||
return None, False
|
||||
|
||||
if ptype == 'LuaFunction':
|
||||
return 'LuaFunction()', False
|
||||
|
||||
if ptype.count('*') == 1 and '???' not in translate_type_to_lvt(ptype):
|
||||
ptype = ptype.replace('const', '').replace('*', '').strip()
|
||||
s = 'Pointer <%s>' % translate_type_to_lua(ptype)[0]
|
||||
|
|
|
|||
|
|
@ -71,6 +71,10 @@ override_disallowed_functions = {
|
|||
"src/game/obj_behaviors_2.c": [ "wiggler_jumped_on_attack_handler", "huge_goomba_weakly_attacked" ],
|
||||
}
|
||||
|
||||
lua_function_params = {
|
||||
"src/pc/lua/smlua_obj_utils.h::spawn_object_sync::objSetupFunction": [ "struct Object*" ]
|
||||
}
|
||||
|
||||
###########################################################
|
||||
|
||||
template = """/* THIS FILE IS AUTOGENERATED */
|
||||
|
|
@ -174,6 +178,8 @@ def build_param(param, i):
|
|||
return ' %s %s = smlua_to_number(L, %d);\n' % (ptype, pid, i)
|
||||
elif ptype == 'const char*':
|
||||
return ' %s %s = smlua_to_string(L, %d);\n' % (ptype, pid, i)
|
||||
elif ptype == 'LuaFunction':
|
||||
return ' %s %s = smlua_to_lua_function(L, %d);\n' % (ptype, pid, i)
|
||||
elif translate_type_to_lot(ptype) == 'LOT_POINTER':
|
||||
lvt = translate_type_to_lvt(ptype)
|
||||
return ' %s %s = (%s)smlua_to_cpointer(L, %d, %s);\n' % (ptype, pid, ptype, i, lvt)
|
||||
|
|
@ -354,6 +360,11 @@ def process_function(fname, line):
|
|||
if param['type'].replace(' ', '') == 's16*':
|
||||
param['type'] = 'Vec3s'
|
||||
|
||||
# remember lua function params
|
||||
lf_key = fname + '::' + function['identifier'] + '::' + param['identifier']
|
||||
if param['type'] == 'LuaFunction' and lf_key in lua_function_params:
|
||||
param['lua_function_params'] = lua_function_params[lf_key]
|
||||
|
||||
function['params'].append(param)
|
||||
param_index += 1
|
||||
|
||||
|
|
@ -405,6 +416,27 @@ def doc_function_index(processed_files):
|
|||
|
||||
return s
|
||||
|
||||
def doc_lua_func_param(param):
|
||||
s = 'LuaFunction('
|
||||
|
||||
lfp = param['lua_function_params']
|
||||
first_lfp = True
|
||||
|
||||
for lfp_type in lfp:
|
||||
if not first_lfp:
|
||||
lfp_type += ', '
|
||||
first_lfp = False
|
||||
|
||||
lfp_type, lfp_link = translate_type_to_lua(lfp_type)
|
||||
|
||||
if lfp_link:
|
||||
s += '[%s](structs.md#%s)' % (lfp_type, lfp_type)
|
||||
else:
|
||||
s += lfp_type
|
||||
|
||||
s += ')'
|
||||
return s
|
||||
|
||||
def doc_function(function):
|
||||
if not function['implemented']:
|
||||
return ''
|
||||
|
|
@ -430,6 +462,10 @@ def doc_function(function):
|
|||
ptype = param['type']
|
||||
ptype, plink = translate_type_to_lua(ptype)
|
||||
|
||||
# build lua function params
|
||||
if param['type'] == 'LuaFunction' and 'lua_function_params' in param:
|
||||
ptype = doc_lua_func_param(param)
|
||||
|
||||
if plink:
|
||||
s += '| %s | [%s](structs.md#%s) |\n' % (pid, ptype, ptype)
|
||||
continue
|
||||
|
|
|
|||
|
|
@ -8033,7 +8033,7 @@
|
|||
## [spawn_object_sync](#spawn_object_sync)
|
||||
|
||||
### Lua Example
|
||||
`local ObjectValue = spawn_object_sync(behaviorId, modelId, x, y, z)`
|
||||
`local ObjectValue = spawn_object_sync(behaviorId, modelId, x, y, z, objSetupFunction)`
|
||||
|
||||
### Parameters
|
||||
| Field | Type |
|
||||
|
|
@ -8043,12 +8043,13 @@
|
|||
| x | number |
|
||||
| y | number |
|
||||
| z | number |
|
||||
| objSetupFunction | LuaFunction([Object](structs.md#Object)) |
|
||||
|
||||
### Returns
|
||||
[Object](structs.md#Object)
|
||||
|
||||
### C Prototype
|
||||
`struct Object* spawn_object_sync(enum BehaviorId behaviorId, enum ModelExtendedId modelId, f32 x, f32 y, f32 z);`
|
||||
`struct Object* spawn_object_sync(enum BehaviorId behaviorId, enum ModelExtendedId modelId, f32 x, f32 y, f32 z, LuaFunction objSetupFunction);`
|
||||
|
||||
[:arrow_up_small:](#)
|
||||
|
||||
|
|
|
|||
|
|
@ -23,6 +23,7 @@ enum LuaValueType {
|
|||
LVT_STRING_P,
|
||||
LVT_BEHAVIORSCRIPT,
|
||||
LVT_BEHAVIORSCRIPT_P,
|
||||
LVT_LUAFUNCTION,
|
||||
LVT_POINTER,
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -5287,7 +5287,7 @@ int smlua_func_save_file_get_total_star_count(lua_State* L) {
|
|||
///////////////////////
|
||||
|
||||
int smlua_func_spawn_object_sync(lua_State* L) {
|
||||
if(!smlua_functions_valid_param_count(L, 5)) { return 0; }
|
||||
if(!smlua_functions_valid_param_count(L, 6)) { return 0; }
|
||||
|
||||
int behaviorId = smlua_to_integer(L, 1);
|
||||
if (!gSmLuaConvertSuccess) { return 0; }
|
||||
|
|
@ -5299,8 +5299,10 @@ int smlua_func_spawn_object_sync(lua_State* L) {
|
|||
if (!gSmLuaConvertSuccess) { return 0; }
|
||||
f32 z = smlua_to_number(L, 5);
|
||||
if (!gSmLuaConvertSuccess) { return 0; }
|
||||
LuaFunction objSetupFunction = smlua_to_lua_function(L, 6);
|
||||
if (!gSmLuaConvertSuccess) { return 0; }
|
||||
|
||||
smlua_push_object(L, LOT_OBJECT, spawn_object_sync(behaviorId, modelId, x, y, z));
|
||||
smlua_push_object(L, LOT_OBJECT, spawn_object_sync(behaviorId, modelId, x, y, z, objSetupFunction));
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -3,12 +3,13 @@
|
|||
#include "object_fields.h"
|
||||
#include "src/game/object_helpers.h"
|
||||
|
||||
#include "smlua.h"
|
||||
#include "smlua_obj_utils.h"
|
||||
#include "smlua_model_utils.h"
|
||||
#include "pc/debuglog.h"
|
||||
|
||||
|
||||
struct Object* spawn_object_sync(enum BehaviorId behaviorId, enum ModelExtendedId modelId, f32 x, f32 y, f32 z) {
|
||||
struct Object* spawn_object_sync(enum BehaviorId behaviorId, enum ModelExtendedId modelId, f32 x, f32 y, f32 z, LuaFunction objSetupFunction) {
|
||||
const BehaviorScript* behavior = get_behavior_from_id(behaviorId);
|
||||
if (behavior == NULL) {
|
||||
LOG_ERROR("failed to find behavior %u", behaviorId);
|
||||
|
|
@ -43,6 +44,16 @@ struct Object* spawn_object_sync(enum BehaviorId behaviorId, enum ModelExtendedI
|
|||
obj->oHomeY = y;
|
||||
obj->oHomeZ = z;
|
||||
|
||||
if (objSetupFunction != 0) {
|
||||
lua_State* L = gLuaState;
|
||||
lua_rawgeti(L, LUA_REGISTRYINDEX, objSetupFunction);
|
||||
smlua_push_object(L, LOT_OBJECT, obj);
|
||||
if (0 != lua_pcall(L, 1, 0, 0)) {
|
||||
LOG_LUA("Failed to call the callback: %u, %s", objSetupFunction, lua_tostring(L, -1));
|
||||
smlua_logline();
|
||||
}
|
||||
}
|
||||
|
||||
struct SyncObject* so = &gSyncObjects[obj->oSyncID];
|
||||
so->extendedModelId = modelId;
|
||||
so->o = obj;
|
||||
|
|
|
|||
|
|
@ -4,6 +4,6 @@
|
|||
#include "behavior_table.h"
|
||||
#include "smlua_model_utils.h"
|
||||
|
||||
struct Object* spawn_object_sync(enum BehaviorId behaviorId, enum ModelExtendedId modelId, f32 x, f32 y, f32 z);
|
||||
struct Object* spawn_object_sync(enum BehaviorId behaviorId, enum ModelExtendedId modelId, f32 x, f32 y, f32 z, LuaFunction objSetupFunction);
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -86,6 +86,23 @@ const char* smlua_to_string(lua_State* L, int index) {
|
|||
return lua_tostring(L, index);
|
||||
}
|
||||
|
||||
LuaFunction smlua_to_lua_function(lua_State* L, int index) {
|
||||
if (lua_type(L, index) == LUA_TNIL) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (lua_type(L, index) != LUA_TFUNCTION) {
|
||||
LOG_LUA("smlua_to_lua_function received improper type '%d'", lua_type(L, index));
|
||||
smlua_logline();
|
||||
gSmLuaConvertSuccess = false;
|
||||
return 0;
|
||||
}
|
||||
|
||||
gSmLuaConvertSuccess = true;
|
||||
lua_pushvalue(L, index);
|
||||
return luaL_ref(L, LUA_REGISTRYINDEX);
|
||||
}
|
||||
|
||||
void* smlua_to_cobject(lua_State* L, int index, u16 lot) {
|
||||
if (lua_type(L, index) != LUA_TTABLE) {
|
||||
LOG_LUA("smlua_to_cobject received improper type '%d'", lua_type(L, index));
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@
|
|||
#define SMLUA_UTILS_H
|
||||
|
||||
extern u8 gSmLuaConvertSuccess;
|
||||
typedef int LuaFunction;
|
||||
|
||||
f32* smlua_get_vec3f_from_buffer(void);
|
||||
s16* smlua_get_vec3s_from_buffer(void);
|
||||
|
|
@ -13,6 +14,7 @@ bool smlua_to_boolean(lua_State* L, int index);
|
|||
lua_Integer smlua_to_integer(lua_State* L, int index);
|
||||
lua_Number smlua_to_number(lua_State* L, int index);
|
||||
const char* smlua_to_string(lua_State* L, int index);
|
||||
LuaFunction smlua_to_lua_function(lua_State* L, int index);
|
||||
void* smlua_to_cobject(lua_State* L, int index, u16 lot);
|
||||
void* smlua_to_cpointer(lua_State* L, int index, u16 lvt);
|
||||
struct LSTNetworkType smlua_to_lnt(lua_State* L, int index);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue