use std::enable_if for create checking

This commit is contained in:
altalk23 2023-01-30 11:02:32 +03:00
parent 68e75eafb5
commit 4aa09c085b
2 changed files with 27 additions and 19 deletions

View file

@ -112,6 +112,7 @@ class GeodeNodeMetadata;
#include <stdint.h> #include <stdint.h>
#include <string> #include <string>
#include <type_traits>
#include <variant> #include <variant>
namespace tulip::hook { namespace tulip::hook {
@ -136,7 +137,8 @@ namespace geode {
namespace addresser { namespace addresser {
template <class Class> template <class Class>
Class* friendCreate(); Class* friendCreate(typename std::enable_if_t<
std::is_same_v<decltype(&Class::create), Class* (*)()>>*);
} }
} }
@ -149,7 +151,9 @@ namespace geode {
friend geode::Result<tulip::hook::HandlerMetadata, std::string> \ friend geode::Result<tulip::hook::HandlerMetadata, std::string> \
geode::modifier::handlerMetadataForAddress(uintptr_t address); \ geode::modifier::handlerMetadataForAddress(uintptr_t address); \
template <class Class> \ template <class Class> \
friend Class* geode::addresser::friendCreate(); friend Class* \
geode::addresser::friendCreate(typename std::enable_if_t< \
std::is_same_v<decltype(&Class::create), Class* (*)()>>*);
#define GEODE_ADD(...) __VA_ARGS__ #define GEODE_ADD(...) __VA_ARGS__
@ -168,9 +172,9 @@ namespace geode {
@param varType : the type of variable. @param varType : the type of variable.
@param varName : variable name. @param varName : variable name.
@param funName : "get + funName" is the name of the getter. @param funName : "get + funName" is the name of the getter.
@warning : The getter is a public virtual function, you should rewrite it first. @warning : The getter is a public virtual function, you should rewrite
The variables and methods declared after CC_PROPERTY_READONLY are all public. it first. The variables and methods declared after CC_PROPERTY_READONLY
If you need protected or private, please declare. are all public. If you need protected or private, please declare.
*/ */
#define CC_PROPERTY_READONLY(varType, varName, funName) \ #define CC_PROPERTY_READONLY(varType, varName, funName) \
\ \
@ -189,14 +193,16 @@ public: \
virtual const varType& get##funName(void); virtual const varType& get##funName(void);
/** CC_PROPERTY is used to declare a protected variable. /** CC_PROPERTY is used to declare a protected variable.
We can use getter to read the variable, and use the setter to change the variable. We can use getter to read the variable, and use the setter to change
the variable.
@param varType : the type of variable. @param varType : the type of variable.
@param varName : variable name. @param varName : variable name.
@param funName : "get + funName" is the name of the getter. @param funName : "get + funName" is the name of the getter.
"set + funName" is the name of the setter. "set + funName" is the name of the setter.
@warning : The getter and setter are public virtual functions, you should rewrite them first. @warning : The getter and setter are public virtual functions, you
The variables and methods declared after CC_PROPERTY are all public. should rewrite them first. The variables and methods declared after
If you need protected or private, please declare. CC_PROPERTY are all public. If you need protected or private, please
declare.
*/ */
#define CC_PROPERTY(varType, varName, funName) \ #define CC_PROPERTY(varType, varName, funName) \
\ \
@ -226,8 +232,8 @@ public: \
@param varName : variable name. @param varName : variable name.
@param funName : "get + funName" is the name of the getter. @param funName : "get + funName" is the name of the getter.
@warning : The getter is a public inline function. @warning : The getter is a public inline function.
The variables and methods declared after CC_SYNTHESIZE_READONLY are all public. The variables and methods declared after CC_SYNTHESIZE_READONLY are all
If you need protected or private, please declare. public. If you need protected or private, please declare.
*/ */
#define CC_SYNTHESIZE_READONLY(varType, varName, funName) \ #define CC_SYNTHESIZE_READONLY(varType, varName, funName) \
\ \

View file

@ -28,12 +28,14 @@ namespace geode::addresser {
inline F rthunkAdjust(T func, F self); inline F rthunkAdjust(T func, F self);
template <class Class> template <class Class>
Class* friendCreate() { Class* friendCreate(typename std::enable_if_t<std::is_same_v<decltype(&Class::create), Class* (*)()>>*) {
return Class::create(); return Class::create();
} }
template <class Class> template <class Class>
concept HasCreate = requires() { friendCreate<Class>(); }; concept HasCreate = requires() {
{ friendCreate<Class>(nullptr) } -> std::same_as<Class*>;
};
class GEODE_DLL Addresser final { class GEODE_DLL Addresser final {
template <char C> template <char C>
@ -74,7 +76,7 @@ namespace geode::addresser {
// I gave up // I gave up
template <HasCreate Class> template <HasCreate Class>
static Class* generateInstance() { static Class* generateInstance() {
return friendCreate<Class>(); return friendCreate<Class>(nullptr);
} }
template <class Class> template <class Class>