meta.cpp 62 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075
  1. #include <utility>
  2. #include <functional>
  3. #include <type_traits>
  4. #include <gtest/gtest.h>
  5. #include <entt/core/hashed_string.hpp>
  6. #include <entt/core/utility.hpp>
  7. #include <entt/meta/factory.hpp>
  8. #include <entt/meta/meta.hpp>
  9. template<typename Type>
  10. void set(Type &prop, Type value) {
  11. prop = value;
  12. }
  13. template<typename Type>
  14. Type get(Type &prop) {
  15. return prop;
  16. }
  17. enum class properties {
  18. prop_int,
  19. prop_bool
  20. };
  21. struct empty_type {
  22. virtual ~empty_type() = default;
  23. static void destroy(empty_type &) {
  24. ++counter;
  25. }
  26. inline static int counter = 0;
  27. };
  28. struct fat_type: empty_type {
  29. fat_type() = default;
  30. fat_type(int *value)
  31. : foo{value}, bar{value}
  32. {}
  33. int *foo{nullptr};
  34. int *bar{nullptr};
  35. bool operator==(const fat_type &other) const {
  36. return foo == other.foo && bar == other.bar;
  37. }
  38. };
  39. union union_type {
  40. int i;
  41. double d;
  42. };
  43. struct base_type {
  44. virtual ~base_type() = default;
  45. };
  46. struct derived_type: base_type {
  47. derived_type() = default;
  48. derived_type(const base_type &, int value, char character)
  49. : i{value}, c{character}
  50. {}
  51. int f() const { return i; }
  52. static char g(const derived_type &type) { return type.c; }
  53. const int i{};
  54. const char c{};
  55. };
  56. derived_type derived_factory(const base_type &, int value) {
  57. return {derived_type{}, value, 'c'};
  58. }
  59. struct data_type {
  60. int i{0};
  61. const int j{1};
  62. inline static int h{2};
  63. inline static const int k{3};
  64. empty_type empty{};
  65. int v{0};
  66. };
  67. struct array_type {
  68. static inline int global[3];
  69. int local[3];
  70. };
  71. struct func_type {
  72. int f(const base_type &, int a, int b) { return f(a, b); }
  73. int f(int a, int b) { value = a; return b*b; }
  74. int f(int v) const { return v*v; }
  75. void g(int v) { value = v*v; }
  76. static int h(int &v) { return (v *= value); }
  77. static void k(int v) { value = v; }
  78. int v(int v) const { return (value = v); }
  79. int & a() const { return value; }
  80. inline static int value = 0;
  81. };
  82. struct setter_getter_type {
  83. int value{};
  84. int setter(int val) { return value = val; }
  85. int getter() { return value; }
  86. int setter_with_ref(const int &val) { return value = val; }
  87. const int & getter_with_ref() { return value; }
  88. static int static_setter(setter_getter_type &type, int value) { return type.value = value; }
  89. static int static_getter(const setter_getter_type &type) { return type.value; }
  90. };
  91. struct not_comparable_type {
  92. bool operator==(const not_comparable_type &) const = delete;
  93. };
  94. bool operator!=(const not_comparable_type &, const not_comparable_type &) = delete;
  95. struct an_abstract_type {
  96. virtual ~an_abstract_type() = default;
  97. void f(int v) { i = v; }
  98. virtual void g(int) = 0;
  99. int i{};
  100. };
  101. struct another_abstract_type {
  102. virtual ~another_abstract_type() = default;
  103. virtual void h(char) = 0;
  104. char j{};
  105. };
  106. struct concrete_type: an_abstract_type, another_abstract_type {
  107. void f(int v) { i = v*v; } // hide, it's ok :-)
  108. void g(int v) override { i = -v; }
  109. void h(char c) override { j = c; }
  110. };
  111. struct Meta: ::testing::Test {
  112. static void SetUpTestCase() {
  113. entt::meta<double>().conv<int>();
  114. entt::meta<char>()
  115. .type("char"_hs)
  116. .prop<entt::property<properties::prop_int, 42>>()
  117. .data<&set<char>, &get<char>>("value"_hs);
  118. entt::meta<properties>()
  119. .data<properties::prop_bool>("prop_bool"_hs)
  120. .prop<entt::property<properties::prop_int, 0>>()
  121. .data<properties::prop_int>("prop_int"_hs)
  122. .prop<entt::property<properties::prop_bool, true>>()
  123. .prop<entt::property<properties::prop_int, 0>>()
  124. .data<&set<properties>, &get<properties>>("value"_hs);
  125. entt::meta<unsigned int>().data<0u>("min"_hs).data<100u>("max"_hs);
  126. entt::meta<base_type>()
  127. .type("base"_hs);
  128. entt::meta<derived_type>()
  129. .type("derived"_hs)
  130. .prop<entt::property<properties::prop_int, 99>>()
  131. .base<base_type>()
  132. .ctor<const base_type &, int, char>()
  133. .prop<entt::property<properties::prop_bool, false>>()
  134. .ctor<&derived_factory>()
  135. .prop<entt::property<properties::prop_int, 42>>()
  136. .conv<&derived_type::f>()
  137. .conv<&derived_type::g>();
  138. entt::meta<empty_type>()
  139. .type("empty"_hs)
  140. .dtor<&empty_type::destroy>();
  141. entt::meta<fat_type>()
  142. .type("fat"_hs)
  143. .base<empty_type>()
  144. .dtor<&fat_type::destroy>();
  145. entt::meta<data_type>()
  146. .type("data"_hs)
  147. .data<&data_type::i, entt::as_alias_t>("i"_hs)
  148. .prop<entt::property<properties::prop_int, 0>>()
  149. .data<&data_type::j>("j"_hs)
  150. .prop<entt::property<properties::prop_int, 1>>()
  151. .data<&data_type::h>("h"_hs)
  152. .prop<entt::property<properties::prop_int, 2>>()
  153. .data<&data_type::k>("k"_hs)
  154. .prop<entt::property<properties::prop_int, 3>>()
  155. .data<&data_type::empty>("empty"_hs)
  156. .data<&data_type::v, entt::as_void_t>("v"_hs);
  157. entt::meta<array_type>()
  158. .type("array"_hs)
  159. .data<&array_type::global>("global"_hs)
  160. .data<&array_type::local>("local"_hs);
  161. entt::meta<func_type>()
  162. .type("func"_hs)
  163. .func<entt::overload<int(const base_type &, int, int)>(&func_type::f)>("f3"_hs)
  164. .func<entt::overload<int(int, int)>(&func_type::f)>("f2"_hs)
  165. .prop<entt::property<properties::prop_bool, false>>()
  166. .func<entt::overload<int(int) const>(&func_type::f)>("f1"_hs)
  167. .prop<entt::property<properties::prop_bool, false>>()
  168. .func<&func_type::g>("g"_hs)
  169. .prop<entt::property<properties::prop_bool, false>>()
  170. .func<&func_type::h>("h"_hs)
  171. .prop<entt::property<properties::prop_bool, false>>()
  172. .func<&func_type::k>("k"_hs)
  173. .prop<entt::property<properties::prop_bool, false>>()
  174. .func<&func_type::v, entt::as_void_t>("v"_hs)
  175. .func<&func_type::a, entt::as_alias_t>("a"_hs);
  176. entt::meta<setter_getter_type>()
  177. .type("setter_getter"_hs)
  178. .data<&setter_getter_type::static_setter, &setter_getter_type::static_getter>("x"_hs)
  179. .data<&setter_getter_type::setter, &setter_getter_type::getter>("y"_hs)
  180. .data<&setter_getter_type::static_setter, &setter_getter_type::getter>("z"_hs)
  181. .data<&setter_getter_type::setter_with_ref, &setter_getter_type::getter_with_ref>("w"_hs);
  182. entt::meta<an_abstract_type>()
  183. .type("an_abstract_type"_hs)
  184. .prop<entt::property<properties::prop_bool, false>>()
  185. .data<&an_abstract_type::i>("i"_hs)
  186. .func<&an_abstract_type::f>("f"_hs)
  187. .func<&an_abstract_type::g>("g"_hs);
  188. entt::meta<another_abstract_type>()
  189. .type("another_abstract_type"_hs)
  190. .prop<entt::property<properties::prop_int, 42>>()
  191. .data<&another_abstract_type::j>("j"_hs)
  192. .func<&another_abstract_type::h>("h"_hs);
  193. entt::meta<concrete_type>()
  194. .type("concrete"_hs)
  195. .base<an_abstract_type>()
  196. .base<another_abstract_type>()
  197. .func<&concrete_type::f>("f"_hs);
  198. }
  199. static void SetUpAfterUnregistration() {
  200. entt::meta<double>().conv<float>();
  201. entt::meta<derived_type>()
  202. .type("my_type"_hs)
  203. .prop<entt::property<properties::prop_bool, false>>()
  204. .ctor<>();
  205. entt::meta<another_abstract_type>()
  206. .type("your_type"_hs)
  207. .data<&another_abstract_type::j>("a_data_member"_hs)
  208. .func<&another_abstract_type::h>("a_member_function"_hs);
  209. }
  210. void SetUp() override {
  211. empty_type::counter = 0;
  212. func_type::value = 0;
  213. }
  214. };
  215. TEST_F(Meta, Resolve) {
  216. ASSERT_EQ(entt::resolve<derived_type>(), entt::resolve("derived"_hs));
  217. bool found = false;
  218. entt::resolve([&found](auto type) {
  219. found = found || type == entt::resolve<derived_type>();
  220. });
  221. ASSERT_TRUE(found);
  222. }
  223. TEST_F(Meta, MetaAnyFromMetaHandle) {
  224. int value = 42;
  225. entt::meta_handle handle{value};
  226. entt::meta_any any{handle};
  227. any.cast<int>() = 3;
  228. ASSERT_TRUE(any);
  229. ASSERT_EQ(any.type(), entt::resolve<int>());
  230. ASSERT_EQ(any.try_cast<std::size_t>(), nullptr);
  231. ASSERT_EQ(any.try_cast<int>(), handle.data());
  232. ASSERT_EQ(std::as_const(any).try_cast<int>(), handle.data());
  233. ASSERT_EQ(any.data(), handle.data());
  234. ASSERT_EQ(std::as_const(any).data(), handle.data());
  235. ASSERT_EQ(value, 3);
  236. }
  237. TEST_F(Meta, MetaAnySBO) {
  238. entt::meta_any any{'c'};
  239. ASSERT_TRUE(any);
  240. ASSERT_FALSE(any.try_cast<std::size_t>());
  241. ASSERT_TRUE(any.try_cast<char>());
  242. ASSERT_EQ(any.cast<char>(), 'c');
  243. ASSERT_EQ(std::as_const(any).cast<char>(), 'c');
  244. ASSERT_NE(any.data(), nullptr);
  245. ASSERT_NE(std::as_const(any).data(), nullptr);
  246. ASSERT_EQ(any, entt::meta_any{'c'});
  247. ASSERT_NE(entt::meta_any{'h'}, any);
  248. }
  249. TEST_F(Meta, MetaAnyNoSBO) {
  250. int value = 42;
  251. fat_type instance{&value};
  252. entt::meta_any any{instance};
  253. ASSERT_TRUE(any);
  254. ASSERT_FALSE(any.try_cast<std::size_t>());
  255. ASSERT_TRUE(any.try_cast<fat_type>());
  256. ASSERT_EQ(any.cast<fat_type>(), instance);
  257. ASSERT_EQ(std::as_const(any).cast<fat_type>(), instance);
  258. ASSERT_NE(any.data(), nullptr);
  259. ASSERT_NE(std::as_const(any).data(), nullptr);
  260. ASSERT_EQ(any, entt::meta_any{instance});
  261. ASSERT_NE(fat_type{}, any);
  262. }
  263. TEST_F(Meta, MetaAnyEmpty) {
  264. entt::meta_any any{};
  265. ASSERT_FALSE(any);
  266. ASSERT_FALSE(any.type());
  267. ASSERT_FALSE(any.try_cast<std::size_t>());
  268. ASSERT_FALSE(any.try_cast<empty_type>());
  269. ASSERT_EQ(any.data(), nullptr);
  270. ASSERT_EQ(std::as_const(any).data(), nullptr);
  271. ASSERT_EQ(any, entt::meta_any{});
  272. ASSERT_NE(entt::meta_any{'c'}, any);
  273. }
  274. TEST_F(Meta, MetaAnySBOInPlaceTypeConstruction) {
  275. entt::meta_any any{std::in_place_type<int>, 42};
  276. ASSERT_TRUE(any);
  277. ASSERT_FALSE(any.try_cast<std::size_t>());
  278. ASSERT_TRUE(any.try_cast<int>());
  279. ASSERT_EQ(any.cast<int>(), 42);
  280. ASSERT_EQ(std::as_const(any).cast<int>(), 42);
  281. ASSERT_NE(any.data(), nullptr);
  282. ASSERT_NE(std::as_const(any).data(), nullptr);
  283. ASSERT_EQ(any, (entt::meta_any{std::in_place_type<int>, 42}));
  284. ASSERT_EQ(any, entt::meta_any{42});
  285. ASSERT_NE(entt::meta_any{3}, any);
  286. }
  287. TEST_F(Meta, MetaAnySBOAsAliasConstruction) {
  288. int value = 3;
  289. int other = 42;
  290. entt::meta_any any{std::ref(value)};
  291. ASSERT_TRUE(any);
  292. ASSERT_FALSE(any.try_cast<std::size_t>());
  293. ASSERT_TRUE(any.try_cast<int>());
  294. ASSERT_EQ(any.cast<int>(), 3);
  295. ASSERT_EQ(std::as_const(any).cast<int>(), 3);
  296. ASSERT_NE(any.data(), nullptr);
  297. ASSERT_NE(std::as_const(any).data(), nullptr);
  298. ASSERT_EQ(any, (entt::meta_any{std::ref(value)}));
  299. ASSERT_NE(any, (entt::meta_any{std::ref(other)}));
  300. ASSERT_NE(any, entt::meta_any{42});
  301. ASSERT_EQ(entt::meta_any{3}, any);
  302. }
  303. TEST_F(Meta, MetaAnySBOCopyConstruction) {
  304. entt::meta_any any{42};
  305. entt::meta_any other{any};
  306. ASSERT_TRUE(any);
  307. ASSERT_TRUE(other);
  308. ASSERT_FALSE(other.try_cast<std::size_t>());
  309. ASSERT_TRUE(other.try_cast<int>());
  310. ASSERT_EQ(other.cast<int>(), 42);
  311. ASSERT_EQ(std::as_const(other).cast<int>(), 42);
  312. ASSERT_EQ(other, entt::meta_any{42});
  313. ASSERT_NE(other, entt::meta_any{0});
  314. }
  315. TEST_F(Meta, MetaAnySBOCopyAssignment) {
  316. entt::meta_any any{42};
  317. entt::meta_any other{3};
  318. other = any;
  319. ASSERT_TRUE(any);
  320. ASSERT_TRUE(other);
  321. ASSERT_FALSE(other.try_cast<std::size_t>());
  322. ASSERT_TRUE(other.try_cast<int>());
  323. ASSERT_EQ(other.cast<int>(), 42);
  324. ASSERT_EQ(std::as_const(other).cast<int>(), 42);
  325. ASSERT_EQ(other, entt::meta_any{42});
  326. ASSERT_NE(other, entt::meta_any{0});
  327. }
  328. TEST_F(Meta, MetaAnySBOMoveConstruction) {
  329. entt::meta_any any{42};
  330. entt::meta_any other{std::move(any)};
  331. ASSERT_FALSE(any);
  332. ASSERT_TRUE(other);
  333. ASSERT_FALSE(other.try_cast<std::size_t>());
  334. ASSERT_TRUE(other.try_cast<int>());
  335. ASSERT_EQ(other.cast<int>(), 42);
  336. ASSERT_EQ(std::as_const(other).cast<int>(), 42);
  337. ASSERT_EQ(other, entt::meta_any{42});
  338. ASSERT_NE(other, entt::meta_any{0});
  339. }
  340. TEST_F(Meta, MetaAnySBOMoveAssignment) {
  341. entt::meta_any any{42};
  342. entt::meta_any other{3};
  343. other = std::move(any);
  344. ASSERT_FALSE(any);
  345. ASSERT_TRUE(other);
  346. ASSERT_FALSE(other.try_cast<std::size_t>());
  347. ASSERT_TRUE(other.try_cast<int>());
  348. ASSERT_EQ(other.cast<int>(), 42);
  349. ASSERT_EQ(std::as_const(other).cast<int>(), 42);
  350. ASSERT_EQ(other, entt::meta_any{42});
  351. ASSERT_NE(other, entt::meta_any{0});
  352. }
  353. TEST_F(Meta, MetaAnySBODirectAssignment) {
  354. entt::meta_any any{};
  355. any = 42;
  356. ASSERT_FALSE(any.try_cast<std::size_t>());
  357. ASSERT_TRUE(any.try_cast<int>());
  358. ASSERT_EQ(any.cast<int>(), 42);
  359. ASSERT_EQ(std::as_const(any).cast<int>(), 42);
  360. ASSERT_EQ(any, entt::meta_any{42});
  361. ASSERT_NE(entt::meta_any{0}, any);
  362. }
  363. TEST_F(Meta, MetaAnyNoSBOInPlaceTypeConstruction) {
  364. int value = 42;
  365. fat_type instance{&value};
  366. entt::meta_any any{std::in_place_type<fat_type>, instance};
  367. ASSERT_TRUE(any);
  368. ASSERT_FALSE(any.try_cast<std::size_t>());
  369. ASSERT_TRUE(any.try_cast<fat_type>());
  370. ASSERT_EQ(any.cast<fat_type>(), instance);
  371. ASSERT_EQ(std::as_const(any).cast<fat_type>(), instance);
  372. ASSERT_NE(any.data(), nullptr);
  373. ASSERT_NE(std::as_const(any).data(), nullptr);
  374. ASSERT_EQ(any, (entt::meta_any{std::in_place_type<fat_type>, instance}));
  375. ASSERT_EQ(any, entt::meta_any{instance});
  376. ASSERT_NE(entt::meta_any{fat_type{}}, any);
  377. }
  378. TEST_F(Meta, MetaAnyNoSBOAsAliasConstruction) {
  379. int value = 3;
  380. fat_type instance{&value};
  381. entt::meta_any any{std::ref(instance)};
  382. ASSERT_TRUE(any);
  383. ASSERT_FALSE(any.try_cast<std::size_t>());
  384. ASSERT_TRUE(any.try_cast<fat_type>());
  385. ASSERT_EQ(any.cast<fat_type>(), instance);
  386. ASSERT_EQ(std::as_const(any).cast<fat_type>(), instance);
  387. ASSERT_NE(any.data(), nullptr);
  388. ASSERT_NE(std::as_const(any).data(), nullptr);
  389. ASSERT_EQ(any, (entt::meta_any{std::ref(instance)}));
  390. ASSERT_EQ(any, entt::meta_any{instance});
  391. ASSERT_NE(entt::meta_any{fat_type{}}, any);
  392. }
  393. TEST_F(Meta, MetaAnyNoSBOCopyConstruction) {
  394. int value = 42;
  395. fat_type instance{&value};
  396. entt::meta_any any{instance};
  397. entt::meta_any other{any};
  398. ASSERT_TRUE(any);
  399. ASSERT_TRUE(other);
  400. ASSERT_FALSE(other.try_cast<std::size_t>());
  401. ASSERT_TRUE(other.try_cast<fat_type>());
  402. ASSERT_EQ(other.cast<fat_type>(), instance);
  403. ASSERT_EQ(std::as_const(other).cast<fat_type>(), instance);
  404. ASSERT_EQ(other, entt::meta_any{instance});
  405. ASSERT_NE(other, fat_type{});
  406. }
  407. TEST_F(Meta, MetaAnyNoSBOCopyAssignment) {
  408. int value = 42;
  409. fat_type instance{&value};
  410. entt::meta_any any{instance};
  411. entt::meta_any other{3};
  412. other = any;
  413. ASSERT_TRUE(any);
  414. ASSERT_TRUE(other);
  415. ASSERT_FALSE(other.try_cast<std::size_t>());
  416. ASSERT_TRUE(other.try_cast<fat_type>());
  417. ASSERT_EQ(other.cast<fat_type>(), instance);
  418. ASSERT_EQ(std::as_const(other).cast<fat_type>(), instance);
  419. ASSERT_EQ(other, entt::meta_any{instance});
  420. ASSERT_NE(other, fat_type{});
  421. }
  422. TEST_F(Meta, MetaAnyNoSBOMoveConstruction) {
  423. int value = 42;
  424. fat_type instance{&value};
  425. entt::meta_any any{instance};
  426. entt::meta_any other{std::move(any)};
  427. ASSERT_FALSE(any);
  428. ASSERT_TRUE(other);
  429. ASSERT_FALSE(other.try_cast<std::size_t>());
  430. ASSERT_TRUE(other.try_cast<fat_type>());
  431. ASSERT_EQ(other.cast<fat_type>(), instance);
  432. ASSERT_EQ(std::as_const(other).cast<fat_type>(), instance);
  433. ASSERT_EQ(other, entt::meta_any{instance});
  434. ASSERT_NE(other, fat_type{});
  435. }
  436. TEST_F(Meta, MetaAnyNoSBOMoveAssignment) {
  437. int value = 42;
  438. fat_type instance{&value};
  439. entt::meta_any any{instance};
  440. entt::meta_any other{3};
  441. other = std::move(any);
  442. ASSERT_FALSE(any);
  443. ASSERT_TRUE(other);
  444. ASSERT_FALSE(other.try_cast<std::size_t>());
  445. ASSERT_TRUE(other.try_cast<fat_type>());
  446. ASSERT_EQ(other.cast<fat_type>(), instance);
  447. ASSERT_EQ(std::as_const(other).cast<fat_type>(), instance);
  448. ASSERT_EQ(other, entt::meta_any{instance});
  449. ASSERT_NE(other, fat_type{});
  450. }
  451. TEST_F(Meta, MetaAnyNoSBODirectAssignment) {
  452. int value = 42;
  453. entt::meta_any any{};
  454. any = fat_type{&value};
  455. ASSERT_FALSE(any.try_cast<std::size_t>());
  456. ASSERT_TRUE(any.try_cast<fat_type>());
  457. ASSERT_EQ(any.cast<fat_type>(), fat_type{&value});
  458. ASSERT_EQ(std::as_const(any).cast<fat_type>(), fat_type{&value});
  459. ASSERT_EQ(any, entt::meta_any{fat_type{&value}});
  460. ASSERT_NE(fat_type{}, any);
  461. }
  462. TEST_F(Meta, MetaAnyVoidInPlaceTypeConstruction) {
  463. entt::meta_any any{std::in_place_type<void>};
  464. ASSERT_TRUE(any);
  465. ASSERT_FALSE(any.try_cast<char>());
  466. ASSERT_EQ(any.data(), nullptr);
  467. ASSERT_EQ(std::as_const(any).data(), nullptr);
  468. ASSERT_EQ(any.type(), entt::resolve<void>());
  469. ASSERT_EQ(any, entt::meta_any{std::in_place_type<void>});
  470. ASSERT_NE(entt::meta_any{3}, any);
  471. }
  472. TEST_F(Meta, MetaAnyVoidCopyConstruction) {
  473. entt::meta_any any{std::in_place_type<void>};
  474. entt::meta_any other{any};
  475. ASSERT_TRUE(any);
  476. ASSERT_TRUE(other);
  477. ASSERT_EQ(any.type(), entt::resolve<void>());
  478. ASSERT_EQ(other, entt::meta_any{std::in_place_type<void>});
  479. }
  480. TEST_F(Meta, MetaAnyVoidCopyAssignment) {
  481. entt::meta_any any{std::in_place_type<void>};
  482. entt::meta_any other{std::in_place_type<void>};
  483. other = any;
  484. ASSERT_TRUE(any);
  485. ASSERT_TRUE(other);
  486. ASSERT_EQ(any.type(), entt::resolve<void>());
  487. ASSERT_EQ(other, entt::meta_any{std::in_place_type<void>});
  488. }
  489. TEST_F(Meta, MetaAnyVoidMoveConstruction) {
  490. entt::meta_any any{std::in_place_type<void>};
  491. entt::meta_any other{std::move(any)};
  492. ASSERT_FALSE(any);
  493. ASSERT_TRUE(other);
  494. ASSERT_EQ(other.type(), entt::resolve<void>());
  495. ASSERT_EQ(other, entt::meta_any{std::in_place_type<void>});
  496. }
  497. TEST_F(Meta, MetaAnyVoidMoveAssignment) {
  498. entt::meta_any any{std::in_place_type<void>};
  499. entt::meta_any other{std::in_place_type<void>};
  500. other = std::move(any);
  501. ASSERT_FALSE(any);
  502. ASSERT_TRUE(other);
  503. ASSERT_EQ(other.type(), entt::resolve<void>());
  504. ASSERT_EQ(other, entt::meta_any{std::in_place_type<void>});
  505. }
  506. TEST_F(Meta, MetaAnySBOMoveInvalidate) {
  507. entt::meta_any any{42};
  508. entt::meta_any other{std::move(any)};
  509. entt::meta_any valid = std::move(other);
  510. ASSERT_FALSE(any);
  511. ASSERT_FALSE(other);
  512. ASSERT_TRUE(valid);
  513. }
  514. TEST_F(Meta, MetaAnyNoSBOMoveInvalidate) {
  515. int value = 42;
  516. fat_type instance{&value};
  517. entt::meta_any any{instance};
  518. entt::meta_any other{std::move(any)};
  519. entt::meta_any valid = std::move(other);
  520. ASSERT_FALSE(any);
  521. ASSERT_FALSE(other);
  522. ASSERT_TRUE(valid);
  523. }
  524. TEST_F(Meta, MetaAnyVoidMoveInvalidate) {
  525. entt::meta_any any{std::in_place_type<void>};
  526. entt::meta_any other{std::move(any)};
  527. entt::meta_any valid = std::move(other);
  528. ASSERT_FALSE(any);
  529. ASSERT_FALSE(other);
  530. ASSERT_TRUE(valid);
  531. }
  532. TEST_F(Meta, MetaAnySBODestruction) {
  533. ASSERT_EQ(empty_type::counter, 0);
  534. { entt::meta_any any{empty_type{}}; }
  535. ASSERT_EQ(empty_type::counter, 1);
  536. }
  537. TEST_F(Meta, MetaAnyNoSBODestruction) {
  538. ASSERT_EQ(fat_type::counter, 0);
  539. { entt::meta_any any{fat_type{}}; }
  540. ASSERT_EQ(fat_type::counter, 1);
  541. }
  542. TEST_F(Meta, MetaAnyVoidDestruction) {
  543. // just let asan tell us if everything is ok here
  544. [[maybe_unused]] entt::meta_any any{std::in_place_type<void>};
  545. }
  546. TEST_F(Meta, MetaAnyEmplace) {
  547. entt::meta_any any{};
  548. any.emplace<int>(42);
  549. ASSERT_TRUE(any);
  550. ASSERT_FALSE(any.try_cast<std::size_t>());
  551. ASSERT_TRUE(any.try_cast<int>());
  552. ASSERT_EQ(any.cast<int>(), 42);
  553. ASSERT_EQ(std::as_const(any).cast<int>(), 42);
  554. ASSERT_NE(any.data(), nullptr);
  555. ASSERT_NE(std::as_const(any).data(), nullptr);
  556. ASSERT_EQ(any, (entt::meta_any{std::in_place_type<int>, 42}));
  557. ASSERT_EQ(any, entt::meta_any{42});
  558. ASSERT_NE(entt::meta_any{3}, any);
  559. }
  560. TEST_F(Meta, MetaAnyEmplaceVoid) {
  561. entt::meta_any any{};
  562. any.emplace<void>();
  563. ASSERT_TRUE(any);
  564. ASSERT_EQ(any.data(), nullptr);
  565. ASSERT_EQ(std::as_const(any).data(), nullptr);
  566. ASSERT_EQ(any.type(), entt::resolve<void>());
  567. ASSERT_EQ(any, (entt::meta_any{std::in_place_type<void>}));
  568. }
  569. TEST_F(Meta, MetaAnySBOSwap) {
  570. entt::meta_any lhs{'c'};
  571. entt::meta_any rhs{42};
  572. std::swap(lhs, rhs);
  573. ASSERT_TRUE(lhs.try_cast<int>());
  574. ASSERT_EQ(lhs.cast<int>(), 42);
  575. ASSERT_TRUE(rhs.try_cast<char>());
  576. ASSERT_EQ(rhs.cast<char>(), 'c');
  577. }
  578. TEST_F(Meta, MetaAnyNoSBOSwap) {
  579. int i, j;
  580. entt::meta_any lhs{fat_type{&i}};
  581. entt::meta_any rhs{fat_type{&j}};
  582. std::swap(lhs, rhs);
  583. ASSERT_EQ(lhs.cast<fat_type>().foo, &j);
  584. ASSERT_EQ(rhs.cast<fat_type>().bar, &i);
  585. }
  586. TEST_F(Meta, MetaAnyVoidSwap) {
  587. entt::meta_any lhs{std::in_place_type<void>};
  588. entt::meta_any rhs{std::in_place_type<void>};
  589. const auto *pre = lhs.data();
  590. std::swap(lhs, rhs);
  591. ASSERT_EQ(pre, lhs.data());
  592. }
  593. TEST_F(Meta, MetaAnySBOWithNoSBOSwap) {
  594. int value = 42;
  595. entt::meta_any lhs{fat_type{&value}};
  596. entt::meta_any rhs{'c'};
  597. std::swap(lhs, rhs);
  598. ASSERT_TRUE(lhs.try_cast<char>());
  599. ASSERT_EQ(lhs.cast<char>(), 'c');
  600. ASSERT_TRUE(rhs.try_cast<fat_type>());
  601. ASSERT_EQ(rhs.cast<fat_type>().foo, &value);
  602. ASSERT_EQ(rhs.cast<fat_type>().bar, &value);
  603. }
  604. TEST_F(Meta, MetaAnySBOWithEmptySwap) {
  605. entt::meta_any lhs{'c'};
  606. entt::meta_any rhs{};
  607. std::swap(lhs, rhs);
  608. ASSERT_FALSE(lhs);
  609. ASSERT_TRUE(rhs.try_cast<char>());
  610. ASSERT_EQ(rhs.cast<char>(), 'c');
  611. std::swap(lhs, rhs);
  612. ASSERT_FALSE(rhs);
  613. ASSERT_TRUE(lhs.try_cast<char>());
  614. ASSERT_EQ(lhs.cast<char>(), 'c');
  615. }
  616. TEST_F(Meta, MetaAnySBOWithVoidSwap) {
  617. entt::meta_any lhs{'c'};
  618. entt::meta_any rhs{std::in_place_type<void>};
  619. std::swap(lhs, rhs);
  620. ASSERT_EQ(lhs.type(), entt::resolve<void>());
  621. ASSERT_TRUE(rhs.try_cast<char>());
  622. ASSERT_EQ(rhs.cast<char>(), 'c');
  623. }
  624. TEST_F(Meta, MetaAnyNoSBOWithEmptySwap) {
  625. int i;
  626. entt::meta_any lhs{fat_type{&i}};
  627. entt::meta_any rhs{};
  628. std::swap(lhs, rhs);
  629. ASSERT_EQ(rhs.cast<fat_type>().bar, &i);
  630. std::swap(lhs, rhs);
  631. ASSERT_EQ(lhs.cast<fat_type>().bar, &i);
  632. }
  633. TEST_F(Meta, MetaAnyNoSBOWithVoidSwap) {
  634. int i;
  635. entt::meta_any lhs{fat_type{&i}};
  636. entt::meta_any rhs{std::in_place_type<void>};
  637. std::swap(lhs, rhs);
  638. ASSERT_EQ(rhs.cast<fat_type>().bar, &i);
  639. std::swap(lhs, rhs);
  640. ASSERT_EQ(lhs.cast<fat_type>().bar, &i);
  641. }
  642. TEST_F(Meta, MetaAnyComparable) {
  643. entt::meta_any any{'c'};
  644. ASSERT_EQ(any, any);
  645. ASSERT_EQ(any, entt::meta_any{'c'});
  646. ASSERT_NE(entt::meta_any{'a'}, any);
  647. ASSERT_NE(any, entt::meta_any{});
  648. ASSERT_TRUE(any == any);
  649. ASSERT_TRUE(any == entt::meta_any{'c'});
  650. ASSERT_FALSE(any == entt::meta_any{'a'});
  651. ASSERT_TRUE(any != entt::meta_any{'a'});
  652. ASSERT_TRUE(any != entt::meta_any{});
  653. }
  654. TEST_F(Meta, MetaAnyNotComparable) {
  655. entt::meta_any any{not_comparable_type{}};
  656. ASSERT_EQ(any, any);
  657. ASSERT_NE(any, entt::meta_any{not_comparable_type{}});
  658. ASSERT_NE(entt::meta_any{}, any);
  659. ASSERT_TRUE(any == any);
  660. ASSERT_FALSE(any == entt::meta_any{not_comparable_type{}});
  661. ASSERT_TRUE(any != entt::meta_any{});
  662. }
  663. TEST_F(Meta, MetaAnyCompareVoid) {
  664. entt::meta_any any{std::in_place_type<void>};
  665. ASSERT_EQ(any, any);
  666. ASSERT_EQ(any, entt::meta_any{std::in_place_type<void>});
  667. ASSERT_NE(entt::meta_any{'a'}, any);
  668. ASSERT_NE(any, entt::meta_any{});
  669. ASSERT_TRUE(any == any);
  670. ASSERT_TRUE(any == entt::meta_any{std::in_place_type<void>});
  671. ASSERT_FALSE(any == entt::meta_any{'a'});
  672. ASSERT_TRUE(any != entt::meta_any{'a'});
  673. ASSERT_TRUE(any != entt::meta_any{});
  674. }
  675. TEST_F(Meta, MetaAnyTryCast) {
  676. entt::meta_any any{derived_type{}};
  677. ASSERT_TRUE(any);
  678. ASSERT_EQ(any.type(), entt::resolve<derived_type>());
  679. ASSERT_EQ(any.try_cast<void>(), nullptr);
  680. ASSERT_NE(any.try_cast<base_type>(), nullptr);
  681. ASSERT_EQ(any.try_cast<derived_type>(), any.data());
  682. ASSERT_EQ(std::as_const(any).try_cast<base_type>(), any.try_cast<base_type>());
  683. ASSERT_EQ(std::as_const(any).try_cast<derived_type>(), any.data());
  684. }
  685. TEST_F(Meta, MetaAnyCast) {
  686. entt::meta_any any{derived_type{}};
  687. ASSERT_TRUE(any);
  688. ASSERT_EQ(any.type(), entt::resolve<derived_type>());
  689. ASSERT_EQ(any.try_cast<std::size_t>(), nullptr);
  690. ASSERT_NE(any.try_cast<base_type>(), nullptr);
  691. ASSERT_EQ(any.try_cast<derived_type>(), any.data());
  692. ASSERT_EQ(std::as_const(any).try_cast<base_type>(), any.try_cast<base_type>());
  693. ASSERT_EQ(std::as_const(any).try_cast<derived_type>(), any.data());
  694. }
  695. TEST_F(Meta, MetaAnyConvert) {
  696. entt::meta_any any{42.};
  697. ASSERT_TRUE(any);
  698. ASSERT_EQ(any.type(), entt::resolve<double>());
  699. ASSERT_TRUE(any.convert<double>());
  700. ASSERT_FALSE(any.convert<char>());
  701. ASSERT_EQ(any.type(), entt::resolve<double>());
  702. ASSERT_EQ(any.cast<double>(), 42.);
  703. ASSERT_TRUE(any.convert<int>());
  704. ASSERT_EQ(any.type(), entt::resolve<int>());
  705. ASSERT_EQ(any.cast<int>(), 42);
  706. }
  707. TEST_F(Meta, MetaAnyConstConvert) {
  708. const entt::meta_any any{42.};
  709. ASSERT_TRUE(any);
  710. ASSERT_EQ(any.type(), entt::resolve<double>());
  711. ASSERT_TRUE(any.convert<double>());
  712. ASSERT_FALSE(any.convert<char>());
  713. ASSERT_EQ(any.type(), entt::resolve<double>());
  714. ASSERT_EQ(any.cast<double>(), 42.);
  715. auto other = any.convert<int>();
  716. ASSERT_EQ(any.type(), entt::resolve<double>());
  717. ASSERT_EQ(any.cast<double>(), 42.);
  718. ASSERT_EQ(other.type(), entt::resolve<int>());
  719. ASSERT_EQ(other.cast<int>(), 42);
  720. }
  721. TEST_F(Meta, MetaHandleFromObject) {
  722. empty_type empty{};
  723. entt::meta_handle handle{empty};
  724. ASSERT_TRUE(handle);
  725. ASSERT_EQ(handle.type(), entt::resolve<empty_type>());
  726. ASSERT_EQ(std::as_const(handle).data(), &empty);
  727. ASSERT_EQ(handle.data(), &empty);
  728. }
  729. TEST_F(Meta, MetaHandleFromMetaAny) {
  730. entt::meta_any any{42};
  731. entt::meta_handle handle{any};
  732. ASSERT_TRUE(handle);
  733. ASSERT_EQ(handle.type(), entt::resolve<int>());
  734. ASSERT_EQ(std::as_const(handle).data(), any.data());
  735. ASSERT_EQ(handle.data(), any.data());
  736. }
  737. TEST_F(Meta, MetaHandleEmpty) {
  738. entt::meta_handle handle{};
  739. ASSERT_FALSE(handle);
  740. ASSERT_FALSE(handle.type());
  741. ASSERT_EQ(std::as_const(handle).data(), nullptr);
  742. ASSERT_EQ(handle.data(), nullptr);
  743. }
  744. TEST_F(Meta, MetaProp) {
  745. auto prop = entt::resolve<char>().prop(properties::prop_int);
  746. ASSERT_TRUE(prop);
  747. ASSERT_NE(prop, entt::meta_prop{});
  748. ASSERT_EQ(prop.key(), properties::prop_int);
  749. ASSERT_EQ(prop.value(), 42);
  750. }
  751. TEST_F(Meta, MetaBase) {
  752. auto base = entt::resolve<derived_type>().base("base"_hs);
  753. derived_type derived{};
  754. ASSERT_TRUE(base);
  755. ASSERT_NE(base, entt::meta_base{});
  756. ASSERT_EQ(base.parent(), entt::resolve("derived"_hs));
  757. ASSERT_EQ(base.type(), entt::resolve<base_type>());
  758. ASSERT_EQ(base.cast(&derived), static_cast<base_type *>(&derived));
  759. }
  760. TEST_F(Meta, MetaConv) {
  761. auto conv = entt::resolve<double>().conv<int>();
  762. double value = 3.;
  763. ASSERT_TRUE(conv);
  764. ASSERT_NE(conv, entt::meta_conv{});
  765. ASSERT_EQ(conv.parent(), entt::resolve<double>());
  766. ASSERT_EQ(conv.type(), entt::resolve<int>());
  767. auto any = conv.convert(&value);
  768. ASSERT_TRUE(any);
  769. ASSERT_EQ(any.type(), entt::resolve<int>());
  770. ASSERT_EQ(any.cast<int>(), 3);
  771. }
  772. TEST_F(Meta, MetaConvAsFreeFunctions) {
  773. auto conv = entt::resolve<derived_type>().conv<int>();
  774. derived_type derived{derived_type{}, 42, 'c'};
  775. ASSERT_TRUE(conv);
  776. ASSERT_NE(conv, entt::meta_conv{});
  777. ASSERT_EQ(conv.parent(), entt::resolve<derived_type>());
  778. ASSERT_EQ(conv.type(), entt::resolve<int>());
  779. auto any = conv.convert(&derived);
  780. ASSERT_TRUE(any);
  781. ASSERT_EQ(any.type(), entt::resolve<int>());
  782. ASSERT_EQ(any.cast<int>(), 42);
  783. }
  784. TEST_F(Meta, MetaConvAsMemberFunctions) {
  785. auto conv = entt::resolve<derived_type>().conv<char>();
  786. derived_type derived{derived_type{}, 42, 'c'};
  787. ASSERT_TRUE(conv);
  788. ASSERT_NE(conv, entt::meta_conv{});
  789. ASSERT_EQ(conv.parent(), entt::resolve<derived_type>());
  790. ASSERT_EQ(conv.type(), entt::resolve<char>());
  791. auto any = conv.convert(&derived);
  792. ASSERT_TRUE(any);
  793. ASSERT_EQ(any.type(), entt::resolve<char>());
  794. ASSERT_EQ(any.cast<char>(), 'c');
  795. }
  796. TEST_F(Meta, MetaCtor) {
  797. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int, char>();
  798. ASSERT_TRUE(ctor);
  799. ASSERT_NE(ctor, entt::meta_ctor{});
  800. ASSERT_EQ(ctor.parent(), entt::resolve("derived"_hs));
  801. ASSERT_EQ(ctor.size(), entt::meta_ctor::size_type{3});
  802. ASSERT_EQ(ctor.arg(entt::meta_ctor::size_type{0}), entt::resolve<base_type>());
  803. ASSERT_EQ(ctor.arg(entt::meta_ctor::size_type{1}), entt::resolve<int>());
  804. ASSERT_EQ(ctor.arg(entt::meta_ctor::size_type{2}), entt::resolve<char>());
  805. ASSERT_FALSE(ctor.arg(entt::meta_ctor::size_type{3}));
  806. auto any = ctor.invoke(base_type{}, 42, 'c');
  807. auto empty = ctor.invoke();
  808. ASSERT_FALSE(empty);
  809. ASSERT_TRUE(any);
  810. ASSERT_TRUE(any.try_cast<derived_type>());
  811. ASSERT_EQ(any.cast<derived_type>().i, 42);
  812. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  813. ctor.prop([](auto prop) {
  814. ASSERT_TRUE(prop);
  815. ASSERT_EQ(prop.key(), properties::prop_bool);
  816. ASSERT_FALSE(prop.value().template cast<bool>());
  817. });
  818. ASSERT_FALSE(ctor.prop(properties::prop_int));
  819. auto prop = ctor.prop(properties::prop_bool);
  820. ASSERT_TRUE(prop);
  821. ASSERT_EQ(prop.key(), properties::prop_bool);
  822. ASSERT_FALSE(prop.value().template cast<bool>());
  823. }
  824. TEST_F(Meta, MetaCtorFunc) {
  825. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int>();
  826. ASSERT_TRUE(ctor);
  827. ASSERT_EQ(ctor.parent(), entt::resolve("derived"_hs));
  828. ASSERT_EQ(ctor.size(), entt::meta_ctor::size_type{2});
  829. ASSERT_EQ(ctor.arg(entt::meta_ctor::size_type{0}), entt::resolve<base_type>());
  830. ASSERT_EQ(ctor.arg(entt::meta_ctor::size_type{1}), entt::resolve<int>());
  831. ASSERT_FALSE(ctor.arg(entt::meta_ctor::size_type{2}));
  832. auto any = ctor.invoke(derived_type{}, 42);
  833. auto empty = ctor.invoke(3, 'c');
  834. ASSERT_FALSE(empty);
  835. ASSERT_TRUE(any);
  836. ASSERT_TRUE(any.try_cast<derived_type>());
  837. ASSERT_EQ(any.cast<derived_type>().i, 42);
  838. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  839. ctor.prop([](auto prop) {
  840. ASSERT_TRUE(prop);
  841. ASSERT_EQ(prop.key(), properties::prop_int);
  842. ASSERT_EQ(prop.value(), 42);
  843. });
  844. ASSERT_FALSE(ctor.prop(properties::prop_bool));
  845. auto prop = ctor.prop(properties::prop_int);
  846. ASSERT_TRUE(prop);
  847. ASSERT_EQ(prop.key(), properties::prop_int);
  848. ASSERT_EQ(prop.value(), 42);
  849. }
  850. TEST_F(Meta, MetaCtorMetaAnyArgs) {
  851. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int, char>();
  852. auto any = ctor.invoke(base_type{}, entt::meta_any{42}, entt::meta_any{'c'});
  853. ASSERT_TRUE(any);
  854. ASSERT_TRUE(any.try_cast<derived_type>());
  855. ASSERT_EQ(any.cast<derived_type>().i, 42);
  856. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  857. }
  858. TEST_F(Meta, MetaCtorInvalidArgs) {
  859. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int, char>();
  860. ASSERT_FALSE(ctor.invoke(base_type{}, entt::meta_any{'c'}, entt::meta_any{42}));
  861. }
  862. TEST_F(Meta, MetaCtorCastAndConvert) {
  863. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int, char>();
  864. auto any = ctor.invoke(entt::meta_any{derived_type{}}, entt::meta_any{42.}, entt::meta_any{'c'});
  865. ASSERT_TRUE(any);
  866. ASSERT_TRUE(any.try_cast<derived_type>());
  867. ASSERT_EQ(any.cast<derived_type>().i, 42);
  868. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  869. }
  870. TEST_F(Meta, MetaCtorFuncMetaAnyArgs) {
  871. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int>();
  872. auto any = ctor.invoke(base_type{}, entt::meta_any{42});
  873. ASSERT_TRUE(any);
  874. ASSERT_TRUE(any.try_cast<derived_type>());
  875. ASSERT_EQ(any.cast<derived_type>().i, 42);
  876. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  877. }
  878. TEST_F(Meta, MetaCtorFuncInvalidArgs) {
  879. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int>();
  880. ASSERT_FALSE(ctor.invoke(base_type{}, entt::meta_any{'c'}));
  881. }
  882. TEST_F(Meta, MetaCtorFuncCastAndConvert) {
  883. auto ctor = entt::resolve<derived_type>().ctor<const base_type &, int>();
  884. auto any = ctor.invoke(entt::meta_any{derived_type{}}, entt::meta_any{42.});
  885. ASSERT_TRUE(any);
  886. ASSERT_TRUE(any.try_cast<derived_type>());
  887. ASSERT_EQ(any.cast<derived_type>().i, 42);
  888. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  889. }
  890. TEST_F(Meta, MetaDtor) {
  891. auto dtor = entt::resolve<empty_type>().dtor();
  892. empty_type empty{};
  893. ASSERT_TRUE(dtor);
  894. ASSERT_NE(dtor, entt::meta_dtor{});
  895. ASSERT_EQ(dtor.parent(), entt::resolve("empty"_hs));
  896. ASSERT_EQ(empty_type::counter, 0);
  897. ASSERT_TRUE(dtor.invoke(empty));
  898. ASSERT_EQ(empty_type::counter, 1);
  899. }
  900. TEST_F(Meta, MetaDtorMetaAnyArg) {
  901. auto dtor = entt::resolve<empty_type>().dtor();
  902. entt::meta_any any{empty_type{}};
  903. ASSERT_EQ(empty_type::counter, 0);
  904. ASSERT_TRUE(dtor.invoke(any));
  905. ASSERT_EQ(empty_type::counter, 1);
  906. }
  907. TEST_F(Meta, MetaDtorMetaAnyInvalidArg) {
  908. auto instance = 0;
  909. ASSERT_FALSE(entt::resolve<empty_type>().dtor().invoke(instance));
  910. }
  911. TEST_F(Meta, MetaData) {
  912. auto data = entt::resolve<data_type>().data("i"_hs);
  913. data_type instance{};
  914. ASSERT_TRUE(data);
  915. ASSERT_NE(data, entt::meta_data{});
  916. ASSERT_EQ(data.parent(), entt::resolve("data"_hs));
  917. ASSERT_EQ(data.type(), entt::resolve<int>());
  918. ASSERT_EQ(data.identifier(), "i"_hs);
  919. ASSERT_FALSE(data.is_const());
  920. ASSERT_FALSE(data.is_static());
  921. ASSERT_EQ(data.get(instance).cast<int>(), 0);
  922. ASSERT_TRUE(data.set(instance, 42));
  923. ASSERT_EQ(data.get(instance).cast<int>(), 42);
  924. data.prop([](auto prop) {
  925. ASSERT_TRUE(prop);
  926. ASSERT_EQ(prop.key(), properties::prop_int);
  927. ASSERT_EQ(prop.value(), 0);
  928. });
  929. ASSERT_FALSE(data.prop(properties::prop_bool));
  930. auto prop = data.prop(properties::prop_int);
  931. ASSERT_TRUE(prop);
  932. ASSERT_EQ(prop.key(), properties::prop_int);
  933. ASSERT_EQ(prop.value(), 0);
  934. }
  935. TEST_F(Meta, MetaDataConst) {
  936. auto data = entt::resolve<data_type>().data("j"_hs);
  937. data_type instance{};
  938. ASSERT_TRUE(data);
  939. ASSERT_EQ(data.parent(), entt::resolve("data"_hs));
  940. ASSERT_EQ(data.type(), entt::resolve<int>());
  941. ASSERT_EQ(data.identifier(), "j"_hs);
  942. ASSERT_TRUE(data.is_const());
  943. ASSERT_FALSE(data.is_static());
  944. ASSERT_EQ(data.get(instance).cast<int>(), 1);
  945. ASSERT_FALSE(data.set(instance, 42));
  946. ASSERT_EQ(data.get(instance).cast<int>(), 1);
  947. data.prop([](auto prop) {
  948. ASSERT_TRUE(prop);
  949. ASSERT_EQ(prop.key(), properties::prop_int);
  950. ASSERT_EQ(prop.value(), 1);
  951. });
  952. ASSERT_FALSE(data.prop(properties::prop_bool));
  953. auto prop = data.prop(properties::prop_int);
  954. ASSERT_TRUE(prop);
  955. ASSERT_EQ(prop.key(), properties::prop_int);
  956. ASSERT_EQ(prop.value(), 1);
  957. }
  958. TEST_F(Meta, MetaDataStatic) {
  959. auto data = entt::resolve<data_type>().data("h"_hs);
  960. ASSERT_TRUE(data);
  961. ASSERT_EQ(data.parent(), entt::resolve("data"_hs));
  962. ASSERT_EQ(data.type(), entt::resolve<int>());
  963. ASSERT_EQ(data.identifier(), "h"_hs);
  964. ASSERT_FALSE(data.is_const());
  965. ASSERT_TRUE(data.is_static());
  966. ASSERT_EQ(data.get({}).cast<int>(), 2);
  967. ASSERT_TRUE(data.set({}, 42));
  968. ASSERT_EQ(data.get({}).cast<int>(), 42);
  969. data.prop([](auto prop) {
  970. ASSERT_TRUE(prop);
  971. ASSERT_EQ(prop.key(), properties::prop_int);
  972. ASSERT_EQ(prop.value(), 2);
  973. });
  974. ASSERT_FALSE(data.prop(properties::prop_bool));
  975. auto prop = data.prop(properties::prop_int);
  976. ASSERT_TRUE(prop);
  977. ASSERT_EQ(prop.key(), properties::prop_int);
  978. ASSERT_EQ(prop.value(), 2);
  979. }
  980. TEST_F(Meta, MetaDataConstStatic) {
  981. auto data = entt::resolve<data_type>().data("k"_hs);
  982. ASSERT_TRUE(data);
  983. ASSERT_EQ(data.parent(), entt::resolve("data"_hs));
  984. ASSERT_EQ(data.type(), entt::resolve<int>());
  985. ASSERT_EQ(data.identifier(), "k"_hs);
  986. ASSERT_TRUE(data.is_const());
  987. ASSERT_TRUE(data.is_static());
  988. ASSERT_EQ(data.get({}).cast<int>(), 3);
  989. ASSERT_FALSE(data.set({}, 42));
  990. ASSERT_EQ(data.get({}).cast<int>(), 3);
  991. data.prop([](auto prop) {
  992. ASSERT_TRUE(prop);
  993. ASSERT_EQ(prop.key(), properties::prop_int);
  994. ASSERT_EQ(prop.value(), 3);
  995. });
  996. ASSERT_FALSE(data.prop(properties::prop_bool));
  997. auto prop = data.prop(properties::prop_int);
  998. ASSERT_TRUE(prop);
  999. ASSERT_EQ(prop.key(), properties::prop_int);
  1000. ASSERT_EQ(prop.value(), 3);
  1001. }
  1002. TEST_F(Meta, MetaDataGetMetaAnyArg) {
  1003. auto data = entt::resolve<data_type>().data("i"_hs);
  1004. entt::meta_any any{data_type{}};
  1005. any.cast<data_type>().i = 99;
  1006. const auto value = data.get(any);
  1007. ASSERT_TRUE(value);
  1008. ASSERT_TRUE(value.cast<int>());
  1009. ASSERT_EQ(value.cast<int>(), 99);
  1010. }
  1011. TEST_F(Meta, MetaDataGetInvalidArg) {
  1012. auto instance = 0;
  1013. ASSERT_FALSE(entt::resolve<data_type>().data("i"_hs).get(instance));
  1014. }
  1015. TEST_F(Meta, MetaDataSetMetaAnyArg) {
  1016. auto data = entt::resolve<data_type>().data("i"_hs);
  1017. entt::meta_any any{data_type{}};
  1018. entt::meta_any value{42};
  1019. ASSERT_EQ(any.cast<data_type>().i, 0);
  1020. ASSERT_TRUE(data.set(any, value));
  1021. ASSERT_EQ(any.cast<data_type>().i, 42);
  1022. }
  1023. TEST_F(Meta, MetaDataSetInvalidArg) {
  1024. ASSERT_FALSE(entt::resolve<data_type>().data("i"_hs).set({}, 'c'));
  1025. }
  1026. TEST_F(Meta, MetaDataSetCast) {
  1027. auto data = entt::resolve<data_type>().data("empty"_hs);
  1028. data_type instance{};
  1029. ASSERT_EQ(empty_type::counter, 0);
  1030. ASSERT_TRUE(data.set(instance, fat_type{}));
  1031. ASSERT_EQ(empty_type::counter, 1);
  1032. }
  1033. TEST_F(Meta, MetaDataSetConvert) {
  1034. auto data = entt::resolve<data_type>().data("i"_hs);
  1035. data_type instance{};
  1036. ASSERT_EQ(instance.i, 0);
  1037. ASSERT_TRUE(data.set(instance, 3.));
  1038. ASSERT_EQ(instance.i, 3);
  1039. }
  1040. TEST_F(Meta, MetaDataSetterGetterAsFreeFunctions) {
  1041. auto data = entt::resolve<setter_getter_type>().data("x"_hs);
  1042. setter_getter_type instance{};
  1043. ASSERT_TRUE(data);
  1044. ASSERT_NE(data, entt::meta_data{});
  1045. ASSERT_EQ(data.parent(), entt::resolve("setter_getter"_hs));
  1046. ASSERT_EQ(data.type(), entt::resolve<int>());
  1047. ASSERT_EQ(data.identifier(), "x"_hs);
  1048. ASSERT_FALSE(data.is_const());
  1049. ASSERT_FALSE(data.is_static());
  1050. ASSERT_EQ(data.get(instance).cast<int>(), 0);
  1051. ASSERT_TRUE(data.set(instance, 42));
  1052. ASSERT_EQ(data.get(instance).cast<int>(), 42);
  1053. }
  1054. TEST_F(Meta, MetaDataSetterGetterAsMemberFunctions) {
  1055. auto data = entt::resolve<setter_getter_type>().data("y"_hs);
  1056. setter_getter_type instance{};
  1057. ASSERT_TRUE(data);
  1058. ASSERT_NE(data, entt::meta_data{});
  1059. ASSERT_EQ(data.parent(), entt::resolve("setter_getter"_hs));
  1060. ASSERT_EQ(data.type(), entt::resolve<int>());
  1061. ASSERT_EQ(data.identifier(), "y"_hs);
  1062. ASSERT_FALSE(data.is_const());
  1063. ASSERT_FALSE(data.is_static());
  1064. ASSERT_EQ(data.get(instance).cast<int>(), 0);
  1065. ASSERT_TRUE(data.set(instance, 42));
  1066. ASSERT_EQ(data.get(instance).cast<int>(), 42);
  1067. }
  1068. TEST_F(Meta, MetaDataSetterGetterWithRefAsMemberFunctions) {
  1069. auto data = entt::resolve<setter_getter_type>().data("w"_hs);
  1070. setter_getter_type instance{};
  1071. ASSERT_TRUE(data);
  1072. ASSERT_NE(data, entt::meta_data{});
  1073. ASSERT_EQ(data.parent(), entt::resolve("setter_getter"_hs));
  1074. ASSERT_EQ(data.type(), entt::resolve<int>());
  1075. ASSERT_EQ(data.identifier(), "w"_hs);
  1076. ASSERT_FALSE(data.is_const());
  1077. ASSERT_FALSE(data.is_static());
  1078. ASSERT_EQ(data.get(instance).cast<int>(), 0);
  1079. ASSERT_TRUE(data.set(instance, 42));
  1080. ASSERT_EQ(data.get(instance).cast<int>(), 42);
  1081. }
  1082. TEST_F(Meta, MetaDataSetterGetterMixed) {
  1083. auto data = entt::resolve<setter_getter_type>().data("z"_hs);
  1084. setter_getter_type instance{};
  1085. ASSERT_TRUE(data);
  1086. ASSERT_NE(data, entt::meta_data{});
  1087. ASSERT_EQ(data.parent(), entt::resolve("setter_getter"_hs));
  1088. ASSERT_EQ(data.type(), entt::resolve<int>());
  1089. ASSERT_EQ(data.identifier(), "z"_hs);
  1090. ASSERT_FALSE(data.is_const());
  1091. ASSERT_FALSE(data.is_static());
  1092. ASSERT_EQ(data.get(instance).cast<int>(), 0);
  1093. ASSERT_TRUE(data.set(instance, 42));
  1094. ASSERT_EQ(data.get(instance).cast<int>(), 42);
  1095. }
  1096. TEST_F(Meta, MetaDataArrayStatic) {
  1097. auto data = entt::resolve<array_type>().data("global"_hs);
  1098. array_type::global[0] = 3;
  1099. array_type::global[1] = 5;
  1100. array_type::global[2] = 7;
  1101. ASSERT_TRUE(data);
  1102. ASSERT_NE(data, entt::meta_data{});
  1103. ASSERT_EQ(data.parent(), entt::resolve("array"_hs));
  1104. ASSERT_EQ(data.type(), entt::resolve<int[3]>());
  1105. ASSERT_EQ(data.identifier(), "global"_hs);
  1106. ASSERT_FALSE(data.is_const());
  1107. ASSERT_TRUE(data.is_static());
  1108. ASSERT_TRUE(data.type().is_array());
  1109. ASSERT_EQ(data.type().extent(), 3);
  1110. ASSERT_EQ(data.get({}, 0).cast<int>(), 3);
  1111. ASSERT_EQ(data.get({}, 1).cast<int>(), 5);
  1112. ASSERT_EQ(data.get({}, 2).cast<int>(), 7);
  1113. ASSERT_FALSE(data.set({}, 0, 'c'));
  1114. ASSERT_EQ(data.get({}, 0).cast<int>(), 3);
  1115. ASSERT_TRUE(data.set({}, 0, data.get({}, 0).cast<int>()+2));
  1116. ASSERT_TRUE(data.set({}, 1, data.get({}, 1).cast<int>()+2));
  1117. ASSERT_TRUE(data.set({}, 2, data.get({}, 2).cast<int>()+2));
  1118. ASSERT_EQ(data.get({}, 0).cast<int>(), 5);
  1119. ASSERT_EQ(data.get({}, 1).cast<int>(), 7);
  1120. ASSERT_EQ(data.get({}, 2).cast<int>(), 9);
  1121. }
  1122. TEST_F(Meta, MetaDataArray) {
  1123. auto data = entt::resolve<array_type>().data("local"_hs);
  1124. array_type instance;
  1125. instance.local[0] = 3;
  1126. instance.local[1] = 5;
  1127. instance.local[2] = 7;
  1128. ASSERT_TRUE(data);
  1129. ASSERT_NE(data, entt::meta_data{});
  1130. ASSERT_EQ(data.parent(), entt::resolve("array"_hs));
  1131. ASSERT_EQ(data.type(), entt::resolve<int[3]>());
  1132. ASSERT_EQ(data.identifier(), "local"_hs);
  1133. ASSERT_FALSE(data.is_const());
  1134. ASSERT_FALSE(data.is_static());
  1135. ASSERT_TRUE(data.type().is_array());
  1136. ASSERT_EQ(data.type().extent(), 3);
  1137. ASSERT_EQ(data.get(instance, 0).cast<int>(), 3);
  1138. ASSERT_EQ(data.get(instance, 1).cast<int>(), 5);
  1139. ASSERT_EQ(data.get(instance, 2).cast<int>(), 7);
  1140. ASSERT_FALSE(data.set(instance, 0, 'c'));
  1141. ASSERT_EQ(data.get(instance, 0).cast<int>(), 3);
  1142. ASSERT_TRUE(data.set(instance, 0, data.get(instance, 0).cast<int>()+2));
  1143. ASSERT_TRUE(data.set(instance, 1, data.get(instance, 1).cast<int>()+2));
  1144. ASSERT_TRUE(data.set(instance, 2, data.get(instance, 2).cast<int>()+2));
  1145. ASSERT_EQ(data.get(instance, 0).cast<int>(), 5);
  1146. ASSERT_EQ(data.get(instance, 1).cast<int>(), 7);
  1147. ASSERT_EQ(data.get(instance, 2).cast<int>(), 9);
  1148. }
  1149. TEST_F(Meta, MetaDataAsVoid) {
  1150. auto data = entt::resolve<data_type>().data("v"_hs);
  1151. data_type instance{};
  1152. ASSERT_TRUE(data.set(instance, 42));
  1153. ASSERT_EQ(instance.v, 42);
  1154. ASSERT_EQ(data.get(instance), entt::meta_any{std::in_place_type<void>});
  1155. }
  1156. TEST_F(Meta, MetaDataAsAlias) {
  1157. data_type instance{};
  1158. auto h_data = entt::resolve<data_type>().data("h"_hs);
  1159. auto i_data = entt::resolve<data_type>().data("i"_hs);
  1160. h_data.get(instance).cast<int>() = 3;
  1161. i_data.get(instance).cast<int>() = 3;
  1162. ASSERT_EQ(h_data.type(), entt::resolve<int>());
  1163. ASSERT_EQ(i_data.type(), entt::resolve<int>());
  1164. ASSERT_NE(instance.h, 3);
  1165. ASSERT_EQ(instance.i, 3);
  1166. }
  1167. TEST_F(Meta, MetaFunc) {
  1168. auto func = entt::resolve<func_type>().func("f2"_hs);
  1169. func_type instance{};
  1170. ASSERT_TRUE(func);
  1171. ASSERT_NE(func, entt::meta_func{});
  1172. ASSERT_EQ(func.parent(), entt::resolve("func"_hs));
  1173. ASSERT_EQ(func.identifier(), "f2"_hs);
  1174. ASSERT_EQ(func.size(), entt::meta_func::size_type{2});
  1175. ASSERT_FALSE(func.is_const());
  1176. ASSERT_FALSE(func.is_static());
  1177. ASSERT_EQ(func.ret(), entt::resolve<int>());
  1178. ASSERT_EQ(func.arg(entt::meta_func::size_type{0}), entt::resolve<int>());
  1179. ASSERT_EQ(func.arg(entt::meta_func::size_type{1}), entt::resolve<int>());
  1180. ASSERT_FALSE(func.arg(entt::meta_func::size_type{2}));
  1181. auto any = func.invoke(instance, 3, 2);
  1182. auto empty = func.invoke(instance);
  1183. ASSERT_FALSE(empty);
  1184. ASSERT_TRUE(any);
  1185. ASSERT_EQ(any.type(), entt::resolve<int>());
  1186. ASSERT_EQ(any.cast<int>(), 4);
  1187. ASSERT_EQ(func_type::value, 3);
  1188. func.prop([](auto prop) {
  1189. ASSERT_TRUE(prop);
  1190. ASSERT_EQ(prop.key(), properties::prop_bool);
  1191. ASSERT_FALSE(prop.value().template cast<bool>());
  1192. });
  1193. ASSERT_FALSE(func.prop(properties::prop_int));
  1194. auto prop = func.prop(properties::prop_bool);
  1195. ASSERT_TRUE(prop);
  1196. ASSERT_EQ(prop.key(), properties::prop_bool);
  1197. ASSERT_FALSE(prop.value().cast<bool>());
  1198. }
  1199. TEST_F(Meta, MetaFuncConst) {
  1200. auto func = entt::resolve<func_type>().func("f1"_hs);
  1201. func_type instance{};
  1202. ASSERT_TRUE(func);
  1203. ASSERT_EQ(func.parent(), entt::resolve("func"_hs));
  1204. ASSERT_EQ(func.identifier(), "f1"_hs);
  1205. ASSERT_EQ(func.size(), entt::meta_func::size_type{1});
  1206. ASSERT_TRUE(func.is_const());
  1207. ASSERT_FALSE(func.is_static());
  1208. ASSERT_EQ(func.ret(), entt::resolve<int>());
  1209. ASSERT_EQ(func.arg(entt::meta_func::size_type{0}), entt::resolve<int>());
  1210. ASSERT_FALSE(func.arg(entt::meta_func::size_type{1}));
  1211. auto any = func.invoke(instance, 4);
  1212. auto empty = func.invoke(instance, 'c');
  1213. ASSERT_FALSE(empty);
  1214. ASSERT_TRUE(any);
  1215. ASSERT_EQ(any.type(), entt::resolve<int>());
  1216. ASSERT_EQ(any.cast<int>(), 16);
  1217. func.prop([](auto prop) {
  1218. ASSERT_TRUE(prop);
  1219. ASSERT_EQ(prop.key(), properties::prop_bool);
  1220. ASSERT_FALSE(prop.value().template cast<bool>());
  1221. });
  1222. ASSERT_FALSE(func.prop(properties::prop_int));
  1223. auto prop = func.prop(properties::prop_bool);
  1224. ASSERT_TRUE(prop);
  1225. ASSERT_EQ(prop.key(), properties::prop_bool);
  1226. ASSERT_FALSE(prop.value().cast<bool>());
  1227. }
  1228. TEST_F(Meta, MetaFuncRetVoid) {
  1229. auto func = entt::resolve<func_type>().func("g"_hs);
  1230. func_type instance{};
  1231. ASSERT_TRUE(func);
  1232. ASSERT_EQ(func.parent(), entt::resolve("func"_hs));
  1233. ASSERT_EQ(func.identifier(), "g"_hs);
  1234. ASSERT_EQ(func.size(), entt::meta_func::size_type{1});
  1235. ASSERT_FALSE(func.is_const());
  1236. ASSERT_FALSE(func.is_static());
  1237. ASSERT_EQ(func.ret(), entt::resolve<void>());
  1238. ASSERT_EQ(func.arg(entt::meta_func::size_type{0}), entt::resolve<int>());
  1239. ASSERT_FALSE(func.arg(entt::meta_func::size_type{1}));
  1240. auto any = func.invoke(instance, 5);
  1241. ASSERT_TRUE(any);
  1242. ASSERT_EQ(any.type(), entt::resolve<void>());
  1243. ASSERT_EQ(func_type::value, 25);
  1244. func.prop([](auto prop) {
  1245. ASSERT_TRUE(prop);
  1246. ASSERT_EQ(prop.key(), properties::prop_bool);
  1247. ASSERT_FALSE(prop.value().template cast<bool>());
  1248. });
  1249. ASSERT_FALSE(func.prop(properties::prop_int));
  1250. auto prop = func.prop(properties::prop_bool);
  1251. ASSERT_TRUE(prop);
  1252. ASSERT_EQ(prop.key(), properties::prop_bool);
  1253. ASSERT_FALSE(prop.value().cast<bool>());
  1254. }
  1255. TEST_F(Meta, MetaFuncStatic) {
  1256. auto func = entt::resolve<func_type>().func("h"_hs);
  1257. func_type::value = 2;
  1258. ASSERT_TRUE(func);
  1259. ASSERT_EQ(func.parent(), entt::resolve("func"_hs));
  1260. ASSERT_EQ(func.identifier(), "h"_hs);
  1261. ASSERT_EQ(func.size(), entt::meta_func::size_type{1});
  1262. ASSERT_FALSE(func.is_const());
  1263. ASSERT_TRUE(func.is_static());
  1264. ASSERT_EQ(func.ret(), entt::resolve<int>());
  1265. ASSERT_EQ(func.arg(entt::meta_func::size_type{0}), entt::resolve<int>());
  1266. ASSERT_FALSE(func.arg(entt::meta_func::size_type{1}));
  1267. auto any = func.invoke({}, 3);
  1268. auto empty = func.invoke({}, 'c');
  1269. ASSERT_FALSE(empty);
  1270. ASSERT_TRUE(any);
  1271. ASSERT_EQ(any.type(), entt::resolve<int>());
  1272. ASSERT_EQ(any.cast<int>(), 6);
  1273. func.prop([](auto prop) {
  1274. ASSERT_TRUE(prop);
  1275. ASSERT_EQ(prop.key(), properties::prop_bool);
  1276. ASSERT_FALSE(prop.value().template cast<bool>());
  1277. });
  1278. ASSERT_FALSE(func.prop(properties::prop_int));
  1279. auto prop = func.prop(properties::prop_bool);
  1280. ASSERT_TRUE(prop);
  1281. ASSERT_EQ(prop.key(), properties::prop_bool);
  1282. ASSERT_FALSE(prop.value().cast<bool>());
  1283. }
  1284. TEST_F(Meta, MetaFuncStaticRetVoid) {
  1285. auto func = entt::resolve<func_type>().func("k"_hs);
  1286. ASSERT_TRUE(func);
  1287. ASSERT_EQ(func.parent(), entt::resolve("func"_hs));
  1288. ASSERT_EQ(func.identifier(), "k"_hs);
  1289. ASSERT_EQ(func.size(), entt::meta_func::size_type{1});
  1290. ASSERT_FALSE(func.is_const());
  1291. ASSERT_TRUE(func.is_static());
  1292. ASSERT_EQ(func.ret(), entt::resolve<void>());
  1293. ASSERT_EQ(func.arg(entt::meta_func::size_type{0}), entt::resolve<int>());
  1294. ASSERT_FALSE(func.arg(entt::meta_func::size_type{1}));
  1295. auto any = func.invoke({}, 42);
  1296. ASSERT_TRUE(any);
  1297. ASSERT_EQ(any.type(), entt::resolve<void>());
  1298. ASSERT_EQ(func_type::value, 42);
  1299. func.prop([](auto *prop) {
  1300. ASSERT_TRUE(prop);
  1301. ASSERT_EQ(prop->key(), properties::prop_bool);
  1302. ASSERT_FALSE(prop->value().template cast<bool>());
  1303. });
  1304. ASSERT_FALSE(func.prop(properties::prop_int));
  1305. auto prop = func.prop(properties::prop_bool);
  1306. ASSERT_TRUE(prop);
  1307. ASSERT_EQ(prop.key(), properties::prop_bool);
  1308. ASSERT_FALSE(prop.value().cast<bool>());
  1309. }
  1310. TEST_F(Meta, MetaFuncMetaAnyArgs) {
  1311. auto func = entt::resolve<func_type>().func("f1"_hs);
  1312. func_type instance;
  1313. auto any = func.invoke(instance, entt::meta_any{3});
  1314. ASSERT_TRUE(any);
  1315. ASSERT_EQ(any.type(), entt::resolve<int>());
  1316. ASSERT_EQ(any.cast<int>(), 9);
  1317. }
  1318. TEST_F(Meta, MetaFuncInvalidArgs) {
  1319. auto func = entt::resolve<func_type>().func("f1"_hs);
  1320. empty_type instance;
  1321. ASSERT_FALSE(func.invoke(instance, entt::meta_any{'c'}));
  1322. }
  1323. TEST_F(Meta, MetaFuncCastAndConvert) {
  1324. auto func = entt::resolve<func_type>().func("f3"_hs);
  1325. func_type instance;
  1326. auto any = func.invoke(instance, derived_type{}, 0, 3.);
  1327. ASSERT_TRUE(any);
  1328. ASSERT_EQ(any.type(), entt::resolve<int>());
  1329. ASSERT_EQ(any.cast<int>(), 9);
  1330. }
  1331. TEST_F(Meta, MetaFuncAsVoid) {
  1332. auto func = entt::resolve<func_type>().func("v"_hs);
  1333. func_type instance{};
  1334. ASSERT_EQ(func.invoke(instance, 42), entt::meta_any{std::in_place_type<void>});
  1335. ASSERT_EQ(func.ret(), entt::resolve<void>());
  1336. ASSERT_EQ(instance.value, 42);
  1337. }
  1338. TEST_F(Meta, MetaFuncAsAlias) {
  1339. func_type instance{};
  1340. auto func = entt::resolve<func_type>().func("a"_hs);
  1341. func.invoke(instance).cast<int>() = 3;
  1342. ASSERT_EQ(func.ret(), entt::resolve<int>());
  1343. ASSERT_EQ(instance.value, 3);
  1344. }
  1345. TEST_F(Meta, MetaFuncByReference) {
  1346. auto func = entt::resolve<func_type>().func("h"_hs);
  1347. func_type::value = 2;
  1348. entt::meta_any any{3};
  1349. int value = 4;
  1350. ASSERT_EQ(func.invoke({}, value).cast<int>(), 8);
  1351. ASSERT_EQ(func.invoke({}, any).cast<int>(), 6);
  1352. ASSERT_EQ(any.cast<int>(), 6);
  1353. ASSERT_EQ(value, 8);
  1354. }
  1355. TEST_F(Meta, MetaType) {
  1356. auto type = entt::resolve<derived_type>();
  1357. ASSERT_TRUE(type);
  1358. ASSERT_NE(type, entt::meta_type{});
  1359. ASSERT_EQ(type.identifier(), "derived"_hs);
  1360. type.prop([](auto prop) {
  1361. ASSERT_TRUE(prop);
  1362. ASSERT_EQ(prop.key(), properties::prop_int);
  1363. ASSERT_EQ(prop.value(), 99);
  1364. });
  1365. ASSERT_FALSE(type.prop(properties::prop_bool));
  1366. auto prop = type.prop(properties::prop_int);
  1367. ASSERT_TRUE(prop);
  1368. ASSERT_EQ(prop.key(), properties::prop_int);
  1369. ASSERT_EQ(prop.value(), 99);
  1370. }
  1371. TEST_F(Meta, MetaTypeTraits) {
  1372. ASSERT_TRUE(entt::resolve<void>().is_void());
  1373. ASSERT_TRUE(entt::resolve<bool>().is_integral());
  1374. ASSERT_TRUE(entt::resolve<double>().is_floating_point());
  1375. ASSERT_TRUE(entt::resolve<properties>().is_enum());
  1376. ASSERT_TRUE(entt::resolve<union_type>().is_union());
  1377. ASSERT_TRUE(entt::resolve<derived_type>().is_class());
  1378. ASSERT_TRUE(entt::resolve<int *>().is_pointer());
  1379. ASSERT_TRUE(entt::resolve<decltype(&empty_type::destroy)>().is_function_pointer());
  1380. ASSERT_TRUE(entt::resolve<decltype(&data_type::i)>().is_member_object_pointer());
  1381. ASSERT_TRUE(entt::resolve<decltype(&func_type::g)>().is_member_function_pointer());
  1382. }
  1383. TEST_F(Meta, MetaTypeRemovePointer) {
  1384. ASSERT_EQ(entt::resolve<void *>().remove_pointer(), entt::resolve<void>());
  1385. ASSERT_EQ(entt::resolve<int(*)(char, double)>().remove_pointer(), entt::resolve<int(char, double)>());
  1386. ASSERT_EQ(entt::resolve<derived_type>().remove_pointer(), entt::resolve<derived_type>());
  1387. }
  1388. TEST_F(Meta, MetaTypeBase) {
  1389. auto type = entt::resolve<derived_type>();
  1390. bool iterate = false;
  1391. type.base([&iterate](auto base) {
  1392. ASSERT_EQ(base.type(), entt::resolve<base_type>());
  1393. iterate = true;
  1394. });
  1395. ASSERT_TRUE(iterate);
  1396. ASSERT_EQ(type.base("base"_hs).type(), entt::resolve<base_type>());
  1397. }
  1398. TEST_F(Meta, MetaTypeConv) {
  1399. auto type = entt::resolve<double>();
  1400. bool iterate = false;
  1401. type.conv([&iterate](auto conv) {
  1402. ASSERT_EQ(conv.type(), entt::resolve<int>());
  1403. iterate = true;
  1404. });
  1405. ASSERT_TRUE(iterate);
  1406. auto conv = type.conv<int>();
  1407. ASSERT_EQ(conv.type(), entt::resolve<int>());
  1408. ASSERT_FALSE(type.conv<char>());
  1409. }
  1410. TEST_F(Meta, MetaTypeCtor) {
  1411. auto type = entt::resolve<derived_type>();
  1412. int counter{};
  1413. type.ctor([&counter](auto) {
  1414. ++counter;
  1415. });
  1416. ASSERT_EQ(counter, 2);
  1417. ASSERT_TRUE((type.ctor<const base_type &, int>()));
  1418. ASSERT_TRUE((type.ctor<const derived_type &, double>()));
  1419. }
  1420. TEST_F(Meta, MetaTypeDtor) {
  1421. ASSERT_TRUE(entt::resolve<fat_type>().dtor());
  1422. ASSERT_FALSE(entt::resolve<int>().dtor());
  1423. }
  1424. TEST_F(Meta, MetaTypeData) {
  1425. auto type = entt::resolve<data_type>();
  1426. int counter{};
  1427. type.data([&counter](auto) {
  1428. ++counter;
  1429. });
  1430. ASSERT_EQ(counter, 6);
  1431. ASSERT_TRUE(type.data("i"_hs));
  1432. }
  1433. TEST_F(Meta, MetaTypeFunc) {
  1434. auto type = entt::resolve<func_type>();
  1435. int counter{};
  1436. type.func([&counter](auto) {
  1437. ++counter;
  1438. });
  1439. ASSERT_EQ(counter, 8);
  1440. ASSERT_TRUE(type.func("f1"_hs));
  1441. }
  1442. TEST_F(Meta, MetaTypeConstruct) {
  1443. auto type = entt::resolve<derived_type>();
  1444. auto any = type.construct(base_type{}, 42, 'c');
  1445. ASSERT_TRUE(any);
  1446. ASSERT_TRUE(any.try_cast<derived_type>());
  1447. ASSERT_EQ(any.cast<derived_type>().i, 42);
  1448. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  1449. }
  1450. TEST_F(Meta, MetaTypeConstructMetaAnyArgs) {
  1451. auto type = entt::resolve<derived_type>();
  1452. auto any = type.construct(entt::meta_any{base_type{}}, entt::meta_any{42}, entt::meta_any{'c'});
  1453. ASSERT_TRUE(any);
  1454. ASSERT_TRUE(any.try_cast<derived_type>());
  1455. ASSERT_EQ(any.cast<derived_type>().i, 42);
  1456. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  1457. }
  1458. TEST_F(Meta, MetaTypeConstructInvalidArgs) {
  1459. auto type = entt::resolve<derived_type>();
  1460. auto any = type.construct(entt::meta_any{base_type{}}, entt::meta_any{'c'}, entt::meta_any{42});
  1461. ASSERT_FALSE(any);
  1462. }
  1463. TEST_F(Meta, MetaTypeLessArgs) {
  1464. auto type = entt::resolve<derived_type>();
  1465. auto any = type.construct(base_type{});
  1466. ASSERT_FALSE(any);
  1467. }
  1468. TEST_F(Meta, MetaTypeConstructCastAndConvert) {
  1469. auto type = entt::resolve<derived_type>();
  1470. auto any = type.construct(entt::meta_any{derived_type{}}, entt::meta_any{42.}, entt::meta_any{'c'});
  1471. ASSERT_TRUE(any);
  1472. ASSERT_TRUE(any.try_cast<derived_type>());
  1473. ASSERT_EQ(any.cast<derived_type>().i, 42);
  1474. ASSERT_EQ(any.cast<derived_type>().c, 'c');
  1475. }
  1476. TEST_F(Meta, MetaTypeDestroyDtor) {
  1477. auto type = entt::resolve<empty_type>();
  1478. empty_type instance;
  1479. ASSERT_EQ(empty_type::counter, 0);
  1480. ASSERT_TRUE(type.destroy(instance));
  1481. ASSERT_EQ(empty_type::counter, 1);
  1482. }
  1483. TEST_F(Meta, MetaTypeDestroyDtorInvalidArg) {
  1484. auto type = entt::resolve<empty_type>();
  1485. auto instance = 'c';
  1486. ASSERT_EQ(empty_type::counter, 0);
  1487. ASSERT_FALSE(type.destroy(instance));
  1488. ASSERT_EQ(empty_type::counter, 0);
  1489. }
  1490. TEST_F(Meta, MetaTypeDestroyDtorCastAndConvert) {
  1491. auto type = entt::resolve<empty_type>();
  1492. fat_type instance{};
  1493. ASSERT_EQ(empty_type::counter, 0);
  1494. ASSERT_FALSE(type.destroy(instance));
  1495. ASSERT_EQ(empty_type::counter, 0);
  1496. }
  1497. TEST_F(Meta, MetaTypeDestroyNoDtor) {
  1498. auto instance = 'c';
  1499. ASSERT_TRUE(entt::resolve<char>().destroy(instance));
  1500. }
  1501. TEST_F(Meta, MetaTypeDestroyNoDtorInvalidArg) {
  1502. auto instance = 42;
  1503. ASSERT_FALSE(entt::resolve<char>().destroy(instance));
  1504. }
  1505. TEST_F(Meta, MetaTypeDestroyNoDtorVoid) {
  1506. ASSERT_FALSE(entt::resolve<void>().destroy({}));
  1507. }
  1508. TEST_F(Meta, MetaTypeDestroyNoDtorCastAndConvert) {
  1509. auto instance = 42.;
  1510. ASSERT_FALSE(entt::resolve<int>().destroy(instance));
  1511. }
  1512. TEST_F(Meta, MetaDataFromBase) {
  1513. auto type = entt::resolve<concrete_type>();
  1514. concrete_type instance;
  1515. ASSERT_TRUE(type.data("i"_hs));
  1516. ASSERT_TRUE(type.data("j"_hs));
  1517. ASSERT_EQ(instance.i, 0);
  1518. ASSERT_EQ(instance.j, char{});
  1519. ASSERT_TRUE(type.data("i"_hs).set(instance, 3));
  1520. ASSERT_TRUE(type.data("j"_hs).set(instance, 'c'));
  1521. ASSERT_EQ(instance.i, 3);
  1522. ASSERT_EQ(instance.j, 'c');
  1523. }
  1524. TEST_F(Meta, MetaFuncFromBase) {
  1525. auto type = entt::resolve<concrete_type>();
  1526. auto base = entt::resolve<an_abstract_type>();
  1527. concrete_type instance;
  1528. ASSERT_TRUE(type.func("f"_hs));
  1529. ASSERT_TRUE(type.func("g"_hs));
  1530. ASSERT_TRUE(type.func("h"_hs));
  1531. ASSERT_EQ(type.func("f"_hs).parent(), entt::resolve<concrete_type>());
  1532. ASSERT_EQ(type.func("g"_hs).parent(), entt::resolve<an_abstract_type>());
  1533. ASSERT_EQ(type.func("h"_hs).parent(), entt::resolve<another_abstract_type>());
  1534. ASSERT_EQ(instance.i, 0);
  1535. ASSERT_EQ(instance.j, char{});
  1536. type.func("f"_hs).invoke(instance, 3);
  1537. type.func("h"_hs).invoke(instance, 'c');
  1538. ASSERT_EQ(instance.i, 9);
  1539. ASSERT_EQ(instance.j, 'c');
  1540. base.func("g"_hs).invoke(instance, 3);
  1541. ASSERT_EQ(instance.i, -3);
  1542. }
  1543. TEST_F(Meta, MetaPropFromBase) {
  1544. auto type = entt::resolve<concrete_type>();
  1545. auto prop_bool = type.prop(properties::prop_bool);
  1546. auto prop_int = type.prop(properties::prop_int);
  1547. ASSERT_TRUE(prop_bool);
  1548. ASSERT_TRUE(prop_int);
  1549. ASSERT_FALSE(prop_bool.value().cast<bool>());
  1550. ASSERT_EQ(prop_int.value().cast<int>(), 42);
  1551. }
  1552. TEST_F(Meta, AbstractClass) {
  1553. auto type = entt::resolve<an_abstract_type>();
  1554. concrete_type instance;
  1555. ASSERT_EQ(instance.i, 0);
  1556. type.func("f"_hs).invoke(instance, 3);
  1557. ASSERT_EQ(instance.i, 3);
  1558. type.func("g"_hs).invoke(instance, 3);
  1559. ASSERT_EQ(instance.i, -3);
  1560. }
  1561. TEST_F(Meta, EnumAndNamedConstants) {
  1562. auto type = entt::resolve<properties>();
  1563. ASSERT_TRUE(type.data("prop_bool"_hs));
  1564. ASSERT_TRUE(type.data("prop_int"_hs));
  1565. ASSERT_EQ(type.data("prop_bool"_hs).type(), type);
  1566. ASSERT_EQ(type.data("prop_int"_hs).type(), type);
  1567. ASSERT_FALSE(type.data("prop_bool"_hs).set({}, properties::prop_int));
  1568. ASSERT_FALSE(type.data("prop_int"_hs).set({}, properties::prop_bool));
  1569. ASSERT_EQ(type.data("prop_bool"_hs).get({}).cast<properties>(), properties::prop_bool);
  1570. ASSERT_EQ(type.data("prop_int"_hs).get({}).cast<properties>(), properties::prop_int);
  1571. }
  1572. TEST_F(Meta, ArithmeticTypeAndNamedConstants) {
  1573. auto type = entt::resolve<unsigned int>();
  1574. ASSERT_TRUE(type.data("min"_hs));
  1575. ASSERT_TRUE(type.data("max"_hs));
  1576. ASSERT_EQ(type.data("min"_hs).type(), type);
  1577. ASSERT_EQ(type.data("max"_hs).type(), type);
  1578. ASSERT_FALSE(type.data("min"_hs).set({}, 100u));
  1579. ASSERT_FALSE(type.data("max"_hs).set({}, 0u));
  1580. ASSERT_EQ(type.data("min"_hs).get({}).cast<unsigned int>(), 0u);
  1581. ASSERT_EQ(type.data("max"_hs).get({}).cast<unsigned int>(), 100u);
  1582. }
  1583. TEST_F(Meta, Variables) {
  1584. auto p_data = entt::resolve<properties>().data("value"_hs);
  1585. auto c_data = entt::resolve("char"_hs).data("value"_hs);
  1586. properties prop{properties::prop_int};
  1587. char c = 'c';
  1588. p_data.set(prop, properties::prop_bool);
  1589. c_data.set(c, 'x');
  1590. ASSERT_EQ(p_data.get(prop).cast<properties>(), properties::prop_bool);
  1591. ASSERT_EQ(c_data.get(c).cast<char>(), 'x');
  1592. ASSERT_EQ(prop, properties::prop_bool);
  1593. ASSERT_EQ(c, 'x');
  1594. }
  1595. TEST_F(Meta, SharedProperties) {
  1596. const auto type = entt::resolve<properties>();
  1597. const auto prop_bool = type.data("prop_bool"_hs);
  1598. const auto prop_int = type.data("prop_int"_hs);
  1599. ASSERT_TRUE(prop_bool.prop(properties::prop_int));
  1600. ASSERT_FALSE(prop_bool.prop(properties::prop_bool));
  1601. ASSERT_TRUE(prop_int.prop(properties::prop_int));
  1602. ASSERT_TRUE(prop_int.prop(properties::prop_bool));
  1603. }
  1604. TEST_F(Meta, Reset) {
  1605. ASSERT_NE(*entt::internal::meta_info<>::ctx, nullptr);
  1606. ASSERT_NE(entt::internal::meta_info<>::local, nullptr);
  1607. entt::meta<char>().reset();
  1608. entt::meta<concrete_type>().reset();
  1609. entt::meta<setter_getter_type>().reset();
  1610. entt::meta<fat_type>().reset();
  1611. entt::meta<data_type>().reset();
  1612. entt::meta<func_type>().reset();
  1613. entt::meta<array_type>().reset();
  1614. entt::meta<double>().reset();
  1615. entt::meta<properties>().reset();
  1616. entt::meta<base_type>().reset();
  1617. entt::meta<derived_type>().reset();
  1618. entt::meta<empty_type>().reset();
  1619. entt::meta<an_abstract_type>().reset();
  1620. entt::meta<another_abstract_type>().reset();
  1621. entt::meta<unsigned int>().reset();
  1622. ASSERT_EQ(*entt::internal::meta_info<>::ctx, nullptr);
  1623. ASSERT_EQ(entt::internal::meta_info<>::local, nullptr);
  1624. ASSERT_FALSE(entt::resolve("char"_hs));
  1625. ASSERT_FALSE(entt::resolve("base"_hs));
  1626. ASSERT_FALSE(entt::resolve("derived"_hs));
  1627. ASSERT_FALSE(entt::resolve("empty"_hs));
  1628. ASSERT_FALSE(entt::resolve("fat"_hs));
  1629. ASSERT_FALSE(entt::resolve("data"_hs));
  1630. ASSERT_FALSE(entt::resolve("func"_hs));
  1631. ASSERT_FALSE(entt::resolve("setter_getter"_hs));
  1632. ASSERT_FALSE(entt::resolve("an_abstract_type"_hs));
  1633. ASSERT_FALSE(entt::resolve("another_abstract_type"_hs));
  1634. ASSERT_FALSE(entt::resolve("concrete"_hs));
  1635. Meta::SetUpAfterUnregistration();
  1636. entt::meta_any any{42.};
  1637. ASSERT_TRUE(any);
  1638. ASSERT_FALSE(any.convert<int>());
  1639. ASSERT_TRUE(any.convert<float>());
  1640. ASSERT_FALSE(entt::resolve("derived"_hs));
  1641. ASSERT_TRUE(entt::resolve("my_type"_hs));
  1642. entt::resolve<derived_type>().prop([](auto prop) {
  1643. ASSERT_TRUE(prop);
  1644. ASSERT_EQ(prop.key(), properties::prop_bool);
  1645. ASSERT_FALSE(prop.value().template cast<bool>());
  1646. });
  1647. ASSERT_FALSE((entt::resolve<derived_type>().ctor<const base_type &, int, char>()));
  1648. ASSERT_TRUE((entt::resolve<derived_type>().ctor<>()));
  1649. ASSERT_TRUE(entt::resolve("your_type"_hs).data("a_data_member"_hs));
  1650. ASSERT_FALSE(entt::resolve("your_type"_hs).data("another_data_member"_hs));
  1651. ASSERT_TRUE(entt::resolve("your_type"_hs).func("a_member_function"_hs));
  1652. ASSERT_FALSE(entt::resolve("your_type"_hs).func("another_member_function"_hs));
  1653. }