11#pragma once
22
33#include " Export.h"
4+ #include " SObject.h"
45
56#include < cstddef>
67#include < typeinfo>
78#include < type_traits>
89#include < utility>
10+ #include < vector>
11+ #include < map>
12+ #include < string>
913
1014#define SCLASS (class_name )\
1115public: \
12- using Super = sh::core::Reflection ::MakeSuper<class_name>::type;\
16+ using Super = sh::core::reflection ::MakeSuper<class_name>::type;\
1317 using This = class_name;\
1418public: \
15- static auto GetStaticTypeInfo () -> const sh::core::Reflection ::TypeInfo&\
19+ static auto GetStaticType () -> sh::core::reflection ::TypeInfo&\
1620 {\
17- static sh::core::Reflection ::TypeInfo info{ sh::core::Reflection ::TypeInfoData<class_name>(#class_name) };\
21+ static sh::core::reflection ::TypeInfo info{ sh::core::reflection ::TypeInfoData<class_name>(#class_name) };\
1822 return info;\
1923 }\
20- virtual auto GetTypeInfo () const -> const sh::core::Reflection ::TypeInfo&\
24+ virtual auto GetType () const -> sh::core::reflection ::TypeInfo&\
2125 {\
2226 return typeInfo;\
2327 }\
24- private: \
25- inline static const sh::core::Reflection ::TypeInfo& typeInfo = GetStaticTypeInfo ();
28+ private: \
29+ inline static sh::core::reflection ::TypeInfo& typeInfo = GetStaticType ();
2630
27- namespace sh ::core
31+ #define PROPERTY (variable_name )\
32+ struct _PropertyFactory_ ##variable_name\
33+ {\
34+ _PropertyFactory_##variable_name()\
35+ {\
36+ static sh::core::reflection::PropertyInfo\
37+ <This, \
38+ decltype (variable_name), \
39+ decltype (&This::##variable_name), \
40+ &This::##variable_name> property_##variable_name{ #variable_name };\
41+ }\
42+ } _propertyFactory_##variable_name;\
43+
44+ namespace sh ::core::reflection
2845{
29- class SH_CORE_API Reflection
46+ class TypeInfo ;
47+ class Property ;
48+
49+ template <typename T>
50+ struct TypeInfoData
3051 {
31- public:
32- class TypeInfo ;
52+ const char * name;
53+ const TypeInfo* super ;
3354
34- template < typename T>
35- struct TypeInfoData
55+ TypeInfoData ( const char * name) :
56+ name (name), super( nullptr )
3657 {
37- const char * name;
38- const TypeInfo* super;
39-
40- TypeInfoData (const char * name) :
41- name (name), super(nullptr )
58+ if constexpr (HasSuper<T>())
4259 {
43- if constexpr (HasSuper<T>())
44- {
45- super = &(T::Super::GetStaticTypeInfo ());
46- }
60+ super = &(T::Super::GetStaticType ());
4761 }
48- };
49-
50- class SH_CORE_API TypeInfo {
51- private:
52- const char * name;
53- const TypeInfo* super;
54- const size_t hash;
55- public:
56- template <typename T>
57- explicit TypeInfo (TypeInfoData<T> data) :
58- name(data.name), super(data.super), hash(typeid (T).hash_code()) {}
59-
60- auto GetName () const -> const char*;
61- auto GetSuper () const -> const TypeInfo*;
62- // other와 자신이 같은 타입인지
63- bool IsA (const TypeInfo& other) const ;
64- // 현재 타입이 other의 자식인지
65- bool IsChild (const TypeInfo& other) const ;
66- };
62+ }
63+ };
64+
65+ class TypeInfo {
66+ private:
67+ const char * name;
68+ const TypeInfo* super;
69+ const size_t hash;
70+
71+ std::map<std::string, Property> properties;
6772 public:
68- template <typename T, typename U = void >
69- struct MakeSuper {
70- using type = U;
71- };
72- template <typename T>
73- struct MakeSuper <T, std::void_t <typename T::This>> {
74- using type = typename T::This;
75- };
76-
77- // 기본 HasSuper 구조체
78- template <typename T, typename U = void >
79- struct HasSuper :
80- std::bool_constant<false > {};
81- // T가 Super을 가지고 있다면 오버로딩 된다(SFINAE). 없으면 기본HasSuper
8273 template <typename T>
83- struct HasSuper <T, std:: void_t < typename T::Super>> :
84- std::bool_constant<!std::is_same_v< typename T::Super, void >> {};
74+ explicit TypeInfo (TypeInfoData<T> data) :
75+ name(data.name), super(data.super), hash( typeid (T).hash_code()) {}
8576
86- template <typename T, typename U = void >
87- struct HasThis :
88- std::bool_constant<false > {};
77+ SH_CORE_API auto GetName () const -> const char*;
78+ SH_CORE_API auto GetSuper () const -> const TypeInfo*;
79+ // other와 자신이 같은 타입인지
80+ SH_CORE_API bool IsA (const TypeInfo& other) const ;
81+ // 현재 타입이 other의 자식인지
82+ SH_CORE_API bool IsChild (const TypeInfo& other) const ;
8983
90- template <typename T>
91- struct HasThis <T, std::void_t <typename T::This>> :
92- std::bool_constant<!std::is_same_v<typename T::This, void >> {};
84+ SH_CORE_API void AddProperty (const std::string& name, const Property& prop);
85+ SH_CORE_API auto GetProperty (const std::string& name) const -> const Property*;
86+ SH_CORE_API auto GetProperties (const std::string& name) const -> const std::map<std::string, Property>&;
87+ };// TypeInfo
9388
94- template <typename T>
95- struct IsSClass : std::bool_constant<HasThis<T>::value> {};
89+ class PropertyDataBase
90+ {
91+ };
92+
93+ template <typename T>
94+ class IPropertyData : public PropertyDataBase
95+ {
96+ public:
97+ virtual auto Get (void * sobject) const -> T& = 0;
9698 };
99+
100+ template <typename ThisType, typename T>
101+ class PropertyData : public IPropertyData <T>
102+ {
103+ private:
104+ T ThisType::* ptr; // 맴버변수 포인터
105+ public:
106+ PropertyData (T ThisType::* ptr):
107+ ptr (ptr)
108+ {
109+ }
110+
111+ auto Get (void * sobject) const -> T& override
112+ {
113+ return static_cast <ThisType*>(sobject)->*ptr;
114+ }
115+ };
116+
117+ template <typename ThisType, typename T, typename VariablePointer, VariablePointer ptr>
118+ class PropertyInfo
119+ {
120+ private:
121+ const char * name;
122+ TypeInfo& owner;
123+ VariablePointer test;
124+ public:
125+ PropertyInfo (const char * name) :
126+ name (name), owner(ThisType::GetStaticType())
127+ {
128+
129+ static PropertyData<ThisType, T> data{ ptr };
130+ Property property{ &data };
131+ owner.AddProperty (name, property);
132+ }
133+ };
134+
135+ class Property
136+ {
137+ private:
138+ PropertyDataBase* data;
139+ public:
140+ Property (PropertyDataBase* data) :
141+ data (data)
142+ {
143+
144+ }
145+
146+ template <typename T, typename ThisType>
147+ auto Get (ThisType* sobject) const -> T&
148+ {
149+ return static_cast <IPropertyData<T>*>(data)->Get (sobject);
150+ }
151+ };
152+
153+ template <typename T, typename U = void >
154+ struct MakeSuper {
155+ using type = U;
156+ };
157+ template <typename T>
158+ struct MakeSuper <T, std::void_t <typename T::This>> {
159+ using type = typename T::This;
160+ };
161+
162+ // 기본 HasSuper 구조체
163+ template <typename T, typename U = void >
164+ struct HasSuper :
165+ std::bool_constant<false > {};
166+ // T가 Super을 가지고 있다면 오버로딩 된다(SFINAE). 없으면 기본HasSuper
167+ template <typename T>
168+ struct HasSuper <T, std::void_t <typename T::Super>> :
169+ std::bool_constant<!std::is_same_v<typename T::Super, void >> {};
170+
171+ template <typename T, typename U = void >
172+ struct HasThis :
173+ std::bool_constant<false > {};
174+
175+ template <typename T>
176+ struct HasThis <T, std::void_t <typename T::This>> :
177+ std::bool_constant<!std::is_same_v<typename T::This, void >> {};
178+
179+ template <typename T>
180+ struct IsSClass : std::bool_constant<HasThis<T>::value> {};
97181}
0 commit comments