10 #ifndef SQUIRREL_HELPER_HPP
11 #define SQUIRREL_HELPER_HPP
14 #include "../core/alloc_func.hpp"
15 #include "../economy_type.h"
16 #include "../string_func.h"
17 #include "../tile_type.h"
20 template <
class CL, ScriptType ST>
const char *GetClassName();
32 template <>
struct Return<uint8_t> {
static inline int Set(HSQUIRRELVM vm, uint8_t res) { sq_pushinteger(vm, (int32_t)res);
return 1; } };
33 template <>
struct Return<uint16_t> {
static inline int Set(HSQUIRRELVM vm, uint16_t res) { sq_pushinteger(vm, (int32_t)res);
return 1; } };
34 template <>
struct Return<uint32_t> {
static inline int Set(HSQUIRRELVM vm, uint32_t res) { sq_pushinteger(vm, (int32_t)res);
return 1; } };
35 template <>
struct Return<int8_t> {
static inline int Set(HSQUIRRELVM vm, int8_t res) { sq_pushinteger(vm, res);
return 1; } };
36 template <>
struct Return<int16_t> {
static inline int Set(HSQUIRRELVM vm, int16_t res) { sq_pushinteger(vm, res);
return 1; } };
37 template <>
struct Return<int32_t> {
static inline int Set(HSQUIRRELVM vm, int32_t res) { sq_pushinteger(vm, res);
return 1; } };
38 template <>
struct Return<int64_t> {
static inline int Set(HSQUIRRELVM vm, int64_t res) { sq_pushinteger(vm, res);
return 1; } };
39 template <>
struct Return<
Money> {
static inline int Set(HSQUIRRELVM vm,
Money res) { sq_pushinteger(vm, res);
return 1; } };
40 template <>
struct Return<
TileIndex> {
static inline int Set(HSQUIRRELVM vm,
TileIndex res) { sq_pushinteger(vm, (int32_t)res.base());
return 1; } };
41 template <>
struct Return<bool> {
static inline int Set(HSQUIRRELVM vm,
bool res) { sq_pushbool (vm, res);
return 1; } };
42 template <>
struct Return<char *> { };
43 template <>
struct Return<const char *> { };
44 template <>
struct Return<void *> {
static inline int Set(HSQUIRRELVM vm,
void *res) { sq_pushuserpointer(vm, res);
return 1; } };
45 template <>
struct Return<HSQOBJECT> {
static inline int Set(HSQUIRRELVM vm, HSQOBJECT res) { sq_pushobject(vm, res);
return 1; } };
47 template <>
struct Return<std::optional<std::string>> {
48 static inline int Set(HSQUIRRELVM vm, std::optional<std::string> res)
50 if (res.has_value()) {
51 sq_pushstring(vm, res.value(), -1);
63 template <
typename T>
struct Param;
65 template <>
struct Param<uint8_t> {
static inline uint8_t Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
66 template <>
struct Param<uint16_t> {
static inline uint16_t Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
67 template <>
struct Param<uint32_t> {
static inline uint32_t Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
68 template <>
struct Param<int8_t> {
static inline int8_t Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
69 template <>
struct Param<int16_t> {
static inline int16_t Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
70 template <>
struct Param<int32_t> {
static inline int32_t Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
71 template <>
struct Param<int64_t> {
static inline int64_t Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
72 template <>
struct Param<
TileIndex> {
static inline TileIndex Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return TileIndex((uint32_t)(int32_t)tmp); } };
73 template <>
struct Param<
Money> {
static inline Money Get(HSQUIRRELVM vm,
int index) { SQInteger tmp; sq_getinteger (vm, index, &tmp);
return tmp; } };
74 template <>
struct Param<bool> {
static inline bool Get(HSQUIRRELVM vm,
int index) { SQBool tmp; sq_getbool (vm, index, &tmp);
return tmp != 0; } };
75 template <>
struct Param<const char *> { };
76 template <>
struct Param<void *> {
static inline void *Get(HSQUIRRELVM vm,
int index) { SQUserPointer tmp; sq_getuserpointer(vm, index, &tmp);
return tmp; } };
78 template <>
struct Param<const std::string &> {
79 static inline const std::string Get(HSQUIRRELVM vm,
int index)
82 sq_tostring(vm, index);
85 sq_getstring(vm, -1, &tmp);
92 template <
typename Titem>
94 static inline Array<Titem> Get(HSQUIRRELVM vm,
int index)
97 if (sq_getsize(vm, index) > UINT16_MAX)
throw sq_throwerror(vm,
"an array used as parameter to a function is too large");
100 sq_getstackobj(vm, index, &obj);
101 sq_pushobject(vm, obj);
106 while (SQ_SUCCEEDED(sq_next(vm, -2))) {
126 template <
typename Tretval,
typename... Targs>
128 static int SQCall(
void *instance, Tretval(*func)(Targs...), HSQUIRRELVM vm)
130 return SQCall(instance, func, vm, std::index_sequence_for<Targs...>{});
134 template <
size_t... i>
135 static int SQCall(
void *, Tretval(*func)(Targs...), [[maybe_unused]] HSQUIRRELVM vm, std::index_sequence<i...>)
137 if constexpr (std::is_void_v<Tretval>) {
143 Tretval ret = (*func)(
154 template <
class Tcls,
typename Tretval,
typename... Targs>
156 static int SQCall(Tcls *instance, Tretval(Tcls:: *func)(Targs...), HSQUIRRELVM vm)
158 return SQCall(instance, func, vm, std::index_sequence_for<Targs...>{});
161 static Tcls *SQConstruct(Tcls *instance, Tretval(Tcls:: *func)(Targs...), HSQUIRRELVM vm)
163 return SQConstruct(instance, func, vm, std::index_sequence_for<Targs...>{});
167 template <
size_t... i>
168 static int SQCall(Tcls *instance, Tretval(Tcls:: *func)(Targs...), [[maybe_unused]] HSQUIRRELVM vm, std::index_sequence<i...>)
170 if constexpr (std::is_void_v<Tretval>) {
176 Tretval ret = (instance->*func)(
183 template <
size_t... i>
184 static Tcls *SQConstruct(Tcls *, Tretval(Tcls:: *)(Targs...), [[maybe_unused]] HSQUIRRELVM vm, std::index_sequence<i...>)
186 Tcls *inst =
new Tcls(
200 template <
typename Tcls,
typename Tmethod, ScriptType Ttype>
204 int nparam = sq_gettop(vm);
205 SQUserPointer ptr =
nullptr;
206 SQUserPointer real_instance =
nullptr;
213 sq_pushroottable(vm);
214 const char *className = GetClassName<Tcls, Ttype>();
215 sq_pushstring(vm, className, -1);
217 sq_pushobject(vm, instance);
218 if (sq_instanceof(vm) != SQTrue)
return sq_throwerror(vm,
"class method is non-static");
222 sq_getinstanceup(vm, 1, &real_instance,
nullptr);
224 sq_getuserdata(vm, nparam, &ptr,
nullptr);
225 if (real_instance ==
nullptr)
return sq_throwerror(vm,
"couldn't detect real instance of class for non-static call");
232 }
catch (SQInteger &e) {
242 template <
typename Tcls,
typename Tmethod, ScriptType Ttype>
246 int nparam = sq_gettop(vm);
247 SQUserPointer ptr =
nullptr;
248 SQUserPointer real_instance =
nullptr;
255 sq_pushroottable(vm);
256 const char *className = GetClassName<Tcls, Ttype>();
257 sq_pushstring(vm, className, -1);
259 sq_pushobject(vm, instance);
260 if (sq_instanceof(vm) != SQTrue)
return sq_throwerror(vm,
"class method is non-static");
264 sq_getinstanceup(vm, 1, &real_instance,
nullptr);
266 sq_getuserdata(vm, nparam, &ptr,
nullptr);
267 if (real_instance ==
nullptr)
return sq_throwerror(vm,
"couldn't detect real instance of class for non-static call");
272 return (SQInteger)(((Tcls *)real_instance)->*(*(Tmethod *)ptr))(vm);
280 template <
typename Tcls,
typename Tmethod>
284 int nparam = sq_gettop(vm);
285 SQUserPointer ptr =
nullptr;
288 sq_getuserdata(vm, nparam, &ptr,
nullptr);
293 }
catch (SQInteger &e) {
304 template <
typename Tcls,
typename Tmethod>
308 int nparam = sq_gettop(vm);
309 SQUserPointer ptr =
nullptr;
312 sq_getuserdata(vm, nparam, &ptr,
nullptr);
317 return (SQInteger)(*(*(Tmethod *)ptr))(vm);
324 template <
typename Tcls>
328 if (p !=
nullptr) ((Tcls *)p)->Release();
337 template <
typename Tcls,
typename Tmethod,
int Tnparam>
343 sq_setinstanceup(vm, -Tnparam, instance);
344 sq_setreleasehook(vm, -Tnparam, DefSQDestructorCallback<Tcls>);
347 }
catch (SQInteger &e) {
356 template <
typename Tcls>
361 int nparam = sq_gettop(vm);
364 Tcls *instance =
new Tcls(vm);
365 sq_setinstanceup(vm, -nparam, instance);
366 sq_setreleasehook(vm, -nparam, DefSQDestructorCallback<Tcls>);
369 }
catch (SQInteger &e) {
static bool GetInstance(HSQUIRRELVM vm, HSQOBJECT *ptr, int pos=1)
Get the Squirrel-instance pointer.
The Squirrel convert routines.
SQInteger DefSQAdvancedConstructorCallback(HSQUIRRELVM vm)
A general template to handle creating of an instance with a complex constructor.
static SQInteger DefSQDestructorCallback(SQUserPointer p, SQInteger)
A general template for the destructor of SQ instances.
SQInteger DefSQAdvancedStaticCallback(HSQUIRRELVM vm)
A general template for all static advanced method callbacks from Squirrel.
SQInteger DefSQConstructorCallback(HSQUIRRELVM vm)
A general template to handle creating of instance with any amount of params.
SQInteger DefSQAdvancedNonStaticCallback(HSQUIRRELVM vm)
A general template for all non-static advanced method callbacks from Squirrel.
SQInteger DefSQNonStaticCallback(HSQUIRRELVM vm)
A general template for all non-static method callbacks from Squirrel.
SQInteger DefSQStaticCallback(HSQUIRRELVM vm)
A general template for all function/static method callbacks from Squirrel.
defines the Squirrel class
Helper structs for converting Squirrel data structures to C++.
std::vector< Titem > Array
Definition of a simple array.
static void StrMakeValid(T &dst, const char *str, const char *last, StringValidationSettings settings)
Copies the valid (UTF-8) characters from str up to last to the dst.
Helper class to recognize the function type (retval type, args) and use the proper specialization for...
To get a param from squirrel, we use this helper class.
To return a value to squirrel, we use this helper class.
StrongType::Typedef< uint32_t, struct TileIndexTag, StrongType::Compare, StrongType::Integer, StrongType::Compatible< int32_t >, StrongType::Compatible< int64_t > > TileIndex
The index/ID of a Tile.