BsManagedSerializableObjectInfo.cpp 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597
  1. //********************************** Banshee Engine (www.banshee3d.com) **************************************************//
  2. //**************** Copyright (c) 2016 Marko Pintera ([email protected]). All rights reserved. **********************//
  3. #include "Serialization/BsManagedSerializableObjectInfo.h"
  4. #include "RTTI/BsManagedSerializableObjectInfoRTTI.h"
  5. #include "Wrappers/GUI/BsScriptRange.h"
  6. #include "Wrappers/GUI/BsScriptStep.h"
  7. #include "BsMonoUtil.h"
  8. #include "BsMonoClass.h"
  9. #include "BsMonoManager.h"
  10. #include "BsMonoField.h"
  11. #include "BsMonoProperty.h"
  12. #include "Serialization/BsScriptAssemblyManager.h"
  13. #include "Wrappers/BsScriptManagedResource.h"
  14. #include "Wrappers/BsScriptRRefBase.h"
  15. namespace bs
  16. {
  17. RTTITypeBase* ManagedSerializableAssemblyInfo::getRTTIStatic()
  18. {
  19. return ManagedSerializableAssemblyInfoRTTI::instance();
  20. }
  21. RTTITypeBase* ManagedSerializableAssemblyInfo::getRTTI() const
  22. {
  23. return ManagedSerializableAssemblyInfo::getRTTIStatic();
  24. }
  25. ManagedSerializableObjectInfo::ManagedSerializableObjectInfo()
  26. :mMonoClass(nullptr)
  27. {
  28. }
  29. SPtr<ManagedSerializableMemberInfo> ManagedSerializableObjectInfo::findMatchingField(const SPtr<ManagedSerializableMemberInfo>& fieldInfo,
  30. const SPtr<ManagedSerializableTypeInfo>& fieldTypeInfo) const
  31. {
  32. const ManagedSerializableObjectInfo* objInfo = this;
  33. while (objInfo != nullptr)
  34. {
  35. if (objInfo->mTypeInfo->matches(fieldTypeInfo))
  36. {
  37. auto iterFind = objInfo->mFieldNameToId.find(fieldInfo->mName);
  38. if (iterFind != objInfo->mFieldNameToId.end())
  39. {
  40. auto iterFind2 = objInfo->mFields.find(iterFind->second);
  41. if (iterFind2 != objInfo->mFields.end())
  42. {
  43. SPtr<ManagedSerializableMemberInfo> foundField = iterFind2->second;
  44. if (foundField->isSerializable())
  45. {
  46. if (fieldInfo->mTypeInfo->matches(foundField->mTypeInfo))
  47. return foundField;
  48. }
  49. }
  50. }
  51. return nullptr;
  52. }
  53. if (objInfo->mBaseClass != nullptr)
  54. objInfo = objInfo->mBaseClass.get();
  55. else
  56. objInfo = nullptr;
  57. }
  58. return nullptr;
  59. }
  60. RTTITypeBase* ManagedSerializableObjectInfo::getRTTIStatic()
  61. {
  62. return ManagedSerializableObjectInfoRTTI::instance();
  63. }
  64. RTTITypeBase* ManagedSerializableObjectInfo::getRTTI() const
  65. {
  66. return ManagedSerializableObjectInfo::getRTTIStatic();
  67. }
  68. ManagedSerializableMemberInfo::ManagedSerializableMemberInfo()
  69. :mFieldId(0), mFlags(0)
  70. {
  71. }
  72. RTTITypeBase* ManagedSerializableMemberInfo::getRTTIStatic()
  73. {
  74. return ManagedSerializableMemberInfoRTTI::instance();
  75. }
  76. RTTITypeBase* ManagedSerializableMemberInfo::getRTTI() const
  77. {
  78. return ManagedSerializableMemberInfo::getRTTIStatic();
  79. }
  80. ManagedSerializableFieldInfo::ManagedSerializableFieldInfo()
  81. :mMonoField(nullptr)
  82. {
  83. }
  84. float ManagedSerializableFieldInfo::getRangeMinimum() const
  85. {
  86. if (mFlags.isSet(ScriptFieldFlag::Range))
  87. {
  88. MonoClass* range = ScriptAssemblyManager::instance().getBuiltinClasses().rangeAttribute;
  89. if (range != nullptr)
  90. {
  91. float min = 0;
  92. ScriptRange::getMinRangeField()->get(mMonoField->getAttribute(range), &min);
  93. return min;
  94. }
  95. }
  96. return 0;
  97. }
  98. float ManagedSerializableFieldInfo::getRangeMaximum() const
  99. {
  100. if (mFlags.isSet(ScriptFieldFlag::Range))
  101. {
  102. MonoClass* range = ScriptAssemblyManager::instance().getBuiltinClasses().rangeAttribute;
  103. if (range != nullptr)
  104. {
  105. float max = 0;
  106. ScriptRange::getMaxRangeField()->get(mMonoField->getAttribute(range), &max);
  107. return max;
  108. }
  109. }
  110. return 0;
  111. }
  112. bool ManagedSerializableFieldInfo::renderAsSlider() const
  113. {
  114. if (mFlags.isSet(ScriptFieldFlag::Range))
  115. {
  116. MonoClass* range = ScriptAssemblyManager::instance().getBuiltinClasses().rangeAttribute;
  117. if (range != nullptr)
  118. {
  119. bool slider = false;
  120. ScriptRange::getSliderField()->get(mMonoField->getAttribute(range), &slider);
  121. return slider;
  122. }
  123. }
  124. return false;
  125. }
  126. float ManagedSerializableFieldInfo::getStep() const
  127. {
  128. if (mFlags.isSet(ScriptFieldFlag::Step))
  129. {
  130. MonoClass* step = ScriptAssemblyManager::instance().getBuiltinClasses().stepAttribute;
  131. if (step != nullptr)
  132. {
  133. float value = 0;
  134. ScriptStep::getStepField()->get(mMonoField->getAttribute(step), &value);
  135. return value;
  136. }
  137. }
  138. return 0;
  139. }
  140. MonoObject* ManagedSerializableFieldInfo::getValue(MonoObject* instance) const
  141. {
  142. return mMonoField->getBoxed(instance);
  143. }
  144. void ManagedSerializableFieldInfo::setValue(MonoObject* instance, void* value) const
  145. {
  146. mMonoField->set(instance, value);
  147. }
  148. RTTITypeBase* ManagedSerializableFieldInfo::getRTTIStatic()
  149. {
  150. return ManagedSerializableFieldInfoRTTI::instance();
  151. }
  152. RTTITypeBase* ManagedSerializableFieldInfo::getRTTI() const
  153. {
  154. return ManagedSerializableFieldInfo::getRTTIStatic();
  155. }
  156. ManagedSerializablePropertyInfo::ManagedSerializablePropertyInfo()
  157. :mMonoProperty(nullptr)
  158. {
  159. }
  160. float ManagedSerializablePropertyInfo::getRangeMinimum() const
  161. {
  162. if (mFlags.isSet(ScriptFieldFlag::Range))
  163. {
  164. MonoClass* range = ScriptAssemblyManager::instance().getBuiltinClasses().rangeAttribute;
  165. if (range != nullptr)
  166. {
  167. float min = 0;
  168. ScriptRange::getMinRangeField()->get(mMonoProperty->getAttribute(range), &min);
  169. return min;
  170. }
  171. }
  172. return 0;
  173. }
  174. float ManagedSerializablePropertyInfo::getRangeMaximum() const
  175. {
  176. if (mFlags.isSet(ScriptFieldFlag::Range))
  177. {
  178. MonoClass* range = ScriptAssemblyManager::instance().getBuiltinClasses().rangeAttribute;
  179. if (range != nullptr)
  180. {
  181. float max = 0;
  182. ScriptRange::getMaxRangeField()->get(mMonoProperty->getAttribute(range), &max);
  183. return max;
  184. }
  185. }
  186. return 0;
  187. }
  188. bool ManagedSerializablePropertyInfo::renderAsSlider() const
  189. {
  190. if (mFlags.isSet(ScriptFieldFlag::Range))
  191. {
  192. MonoClass* range = ScriptAssemblyManager::instance().getBuiltinClasses().rangeAttribute;
  193. if (range != nullptr)
  194. {
  195. bool slider = false;
  196. ScriptRange::getSliderField()->get(mMonoProperty->getAttribute(range), &slider);
  197. return slider;
  198. }
  199. }
  200. return false;
  201. }
  202. float ManagedSerializablePropertyInfo::getStep() const
  203. {
  204. if (mFlags.isSet(ScriptFieldFlag::Step))
  205. {
  206. MonoClass* step = ScriptAssemblyManager::instance().getBuiltinClasses().stepAttribute;
  207. if (step != nullptr)
  208. {
  209. float value = 0;
  210. ScriptStep::getStepField()->get(mMonoProperty->getAttribute(step), &value);
  211. return value;
  212. }
  213. }
  214. return 0;
  215. }
  216. MonoObject* ManagedSerializablePropertyInfo::getValue(MonoObject* instance) const
  217. {
  218. return mMonoProperty->get(instance);
  219. }
  220. void ManagedSerializablePropertyInfo::setValue(MonoObject* instance, void* value) const
  221. {
  222. mMonoProperty->set(instance, value);
  223. }
  224. RTTITypeBase* ManagedSerializablePropertyInfo::getRTTIStatic()
  225. {
  226. return ManagedSerializablePropertyInfoRTTI::instance();
  227. }
  228. RTTITypeBase* ManagedSerializablePropertyInfo::getRTTI() const
  229. {
  230. return ManagedSerializablePropertyInfo::getRTTIStatic();
  231. }
  232. RTTITypeBase* ManagedSerializableTypeInfo::getRTTIStatic()
  233. {
  234. return ManagedSerializableTypeInfoRTTI::instance();
  235. }
  236. RTTITypeBase* ManagedSerializableTypeInfo::getRTTI() const
  237. {
  238. return ManagedSerializableTypeInfo::getRTTIStatic();
  239. }
  240. bool ManagedSerializableTypeInfoPrimitive::matches(const SPtr<ManagedSerializableTypeInfo>& typeInfo) const
  241. {
  242. if(!rtti_is_of_type<ManagedSerializableTypeInfoPrimitive>(typeInfo))
  243. return false;
  244. auto primTypeInfo = std::static_pointer_cast<ManagedSerializableTypeInfoPrimitive>(typeInfo);
  245. return primTypeInfo->mType == mType;
  246. }
  247. bool ManagedSerializableTypeInfoPrimitive::isTypeLoaded() const
  248. {
  249. return mType < ScriptPrimitiveType::Count; // Ignoring some removed types
  250. }
  251. ::MonoClass* ManagedSerializableTypeInfoPrimitive::getMonoClass() const
  252. {
  253. switch(mType)
  254. {
  255. case ScriptPrimitiveType::Bool:
  256. return MonoUtil::getBoolClass();
  257. case ScriptPrimitiveType::Char:
  258. return MonoUtil::getCharClass();
  259. case ScriptPrimitiveType::I8:
  260. return MonoUtil::getSByteClass();
  261. case ScriptPrimitiveType::U8:
  262. return MonoUtil::getByteClass();
  263. case ScriptPrimitiveType::I16:
  264. return MonoUtil::getINT16Class();
  265. case ScriptPrimitiveType::U16:
  266. return MonoUtil::getUINT16Class();
  267. case ScriptPrimitiveType::I32:
  268. return MonoUtil::getINT32Class();
  269. case ScriptPrimitiveType::U32:
  270. return MonoUtil::getUINT32Class();
  271. case ScriptPrimitiveType::I64:
  272. return MonoUtil::getINT64Class();
  273. case ScriptPrimitiveType::U64:
  274. return MonoUtil::getUINT64Class();
  275. case ScriptPrimitiveType::Float:
  276. return MonoUtil::getFloatClass();
  277. case ScriptPrimitiveType::Double:
  278. return MonoUtil::getDoubleClass();
  279. case ScriptPrimitiveType::String:
  280. return MonoUtil::getStringClass();
  281. default:
  282. break;
  283. }
  284. return nullptr;
  285. }
  286. RTTITypeBase* ManagedSerializableTypeInfoPrimitive::getRTTIStatic()
  287. {
  288. return ManagedSerializableTypeInfoPrimitiveRTTI::instance();
  289. }
  290. RTTITypeBase* ManagedSerializableTypeInfoPrimitive::getRTTI() const
  291. {
  292. return ManagedSerializableTypeInfoPrimitive::getRTTIStatic();
  293. }
  294. bool ManagedSerializableTypeInfoRef::matches(const SPtr<ManagedSerializableTypeInfo>& typeInfo) const
  295. {
  296. if (!rtti_is_of_type<ManagedSerializableTypeInfoRef>(typeInfo))
  297. return false;
  298. auto objTypeInfo = std::static_pointer_cast<ManagedSerializableTypeInfoRef>(typeInfo);
  299. return objTypeInfo->mTypeNamespace == mTypeNamespace && objTypeInfo->mTypeName == mTypeName;
  300. }
  301. bool ManagedSerializableTypeInfoRef::isTypeLoaded() const
  302. {
  303. switch (mType)
  304. {
  305. case ScriptReferenceType::BuiltinResourceBase:
  306. case ScriptReferenceType::ManagedResourceBase:
  307. case ScriptReferenceType::BuiltinResource:
  308. case ScriptReferenceType::BuiltinComponentBase:
  309. case ScriptReferenceType::ManagedComponentBase:
  310. case ScriptReferenceType::BuiltinComponent:
  311. case ScriptReferenceType::SceneObject:
  312. return true;
  313. default:
  314. break;
  315. }
  316. return ScriptAssemblyManager::instance().hasSerializableObjectInfo(mTypeNamespace, mTypeName);
  317. }
  318. ::MonoClass* ManagedSerializableTypeInfoRef::getMonoClass() const
  319. {
  320. switch (mType)
  321. {
  322. case ScriptReferenceType::BuiltinResourceBase:
  323. return ScriptResource::getMetaData()->scriptClass->_getInternalClass();
  324. case ScriptReferenceType::ManagedResourceBase:
  325. return ScriptManagedResource::getMetaData()->scriptClass->_getInternalClass();
  326. case ScriptReferenceType::SceneObject:
  327. return ScriptAssemblyManager::instance().getBuiltinClasses().sceneObjectClass->_getInternalClass();
  328. case ScriptReferenceType::BuiltinComponentBase:
  329. return ScriptAssemblyManager::instance().getBuiltinClasses().componentClass->_getInternalClass();
  330. case ScriptReferenceType::ManagedComponentBase:
  331. return ScriptAssemblyManager::instance().getBuiltinClasses().managedComponentClass->_getInternalClass();
  332. default:
  333. break;
  334. }
  335. // Specific component or resource (either builtin or custom)
  336. SPtr<ManagedSerializableObjectInfo> objInfo;
  337. if (!ScriptAssemblyManager::instance().getSerializableObjectInfo(mTypeNamespace, mTypeName, objInfo))
  338. return nullptr;
  339. return objInfo->mMonoClass->_getInternalClass();
  340. }
  341. RTTITypeBase* ManagedSerializableTypeInfoRef::getRTTIStatic()
  342. {
  343. return ManagedSerializableTypeInfoRefRTTI::instance();
  344. }
  345. RTTITypeBase* ManagedSerializableTypeInfoRef::getRTTI() const
  346. {
  347. return ManagedSerializableTypeInfoRef::getRTTIStatic();
  348. }
  349. bool ManagedSerializableTypeInfoRRef::matches(const SPtr<ManagedSerializableTypeInfo>& typeInfo) const
  350. {
  351. if(!rtti_is_of_type<ManagedSerializableTypeInfoRRef>(typeInfo))
  352. return false;
  353. auto resourceTypeInfo = std::static_pointer_cast<ManagedSerializableTypeInfoRRef>(typeInfo);
  354. if(mResourceType == nullptr)
  355. return resourceTypeInfo->mResourceType == nullptr;
  356. return mResourceType->matches(resourceTypeInfo->mResourceType);
  357. }
  358. bool ManagedSerializableTypeInfoRRef::isTypeLoaded() const
  359. {
  360. return mResourceType == nullptr || mResourceType->isTypeLoaded();
  361. }
  362. ::MonoClass* ManagedSerializableTypeInfoRRef::getMonoClass() const
  363. {
  364. // If non-null, this is a templated (i.e. C# generic) RRef type
  365. if(mResourceType)
  366. {
  367. ::MonoClass* resourceTypeClass = mResourceType->getMonoClass();
  368. if (resourceTypeClass == nullptr)
  369. return nullptr;
  370. return ScriptRRefBase::bindGenericParam(resourceTypeClass);
  371. }
  372. // RRefBase
  373. else
  374. return ScriptAssemblyManager::instance().getBuiltinClasses().rrefBaseClass->_getInternalClass();
  375. }
  376. RTTITypeBase* ManagedSerializableTypeInfoRRef::getRTTIStatic()
  377. {
  378. return ManagedSerializableTypeInfoRRefRTTI::instance();
  379. }
  380. RTTITypeBase* ManagedSerializableTypeInfoRRef::getRTTI() const
  381. {
  382. return ManagedSerializableTypeInfoRRef::getRTTIStatic();
  383. }
  384. bool ManagedSerializableTypeInfoObject::matches(const SPtr<ManagedSerializableTypeInfo>& typeInfo) const
  385. {
  386. if(!rtti_is_of_type<ManagedSerializableTypeInfoObject>(typeInfo))
  387. return false;
  388. auto objTypeInfo = std::static_pointer_cast<ManagedSerializableTypeInfoObject>(typeInfo);
  389. return objTypeInfo->mTypeNamespace == mTypeNamespace && objTypeInfo->mTypeName == mTypeName && objTypeInfo->mValueType == mValueType;
  390. }
  391. bool ManagedSerializableTypeInfoObject::isTypeLoaded() const
  392. {
  393. return ScriptAssemblyManager::instance().hasSerializableObjectInfo(mTypeNamespace, mTypeName);
  394. }
  395. ::MonoClass* ManagedSerializableTypeInfoObject::getMonoClass() const
  396. {
  397. SPtr<ManagedSerializableObjectInfo> objInfo;
  398. if(!ScriptAssemblyManager::instance().getSerializableObjectInfo(mTypeNamespace, mTypeName, objInfo))
  399. return nullptr;
  400. return objInfo->mMonoClass->_getInternalClass();
  401. }
  402. RTTITypeBase* ManagedSerializableTypeInfoObject::getRTTIStatic()
  403. {
  404. return ManagedSerializableTypeInfoObjectRTTI::instance();
  405. }
  406. RTTITypeBase* ManagedSerializableTypeInfoObject::getRTTI() const
  407. {
  408. return ManagedSerializableTypeInfoObject::getRTTIStatic();
  409. }
  410. bool ManagedSerializableTypeInfoArray::matches(const SPtr<ManagedSerializableTypeInfo>& typeInfo) const
  411. {
  412. if(!rtti_is_of_type<ManagedSerializableTypeInfoArray>(typeInfo))
  413. return false;
  414. auto arrayTypeInfo = std::static_pointer_cast<ManagedSerializableTypeInfoArray>(typeInfo);
  415. return arrayTypeInfo->mRank == mRank && arrayTypeInfo->mElementType->matches(mElementType);
  416. }
  417. bool ManagedSerializableTypeInfoArray::isTypeLoaded() const
  418. {
  419. return mElementType->isTypeLoaded();
  420. }
  421. ::MonoClass* ManagedSerializableTypeInfoArray::getMonoClass() const
  422. {
  423. ::MonoClass* elementClass = mElementType->getMonoClass();
  424. if(elementClass == nullptr)
  425. return nullptr;
  426. return ScriptArray::buildArrayClass(mElementType->getMonoClass(), mRank);
  427. }
  428. RTTITypeBase* ManagedSerializableTypeInfoArray::getRTTIStatic()
  429. {
  430. return ManagedSerializableTypeInfoArrayRTTI::instance();
  431. }
  432. RTTITypeBase* ManagedSerializableTypeInfoArray::getRTTI() const
  433. {
  434. return ManagedSerializableTypeInfoArray::getRTTIStatic();
  435. }
  436. bool ManagedSerializableTypeInfoList::matches(const SPtr<ManagedSerializableTypeInfo>& typeInfo) const
  437. {
  438. if(!rtti_is_of_type<ManagedSerializableTypeInfoList>(typeInfo))
  439. return false;
  440. auto listTypeInfo = std::static_pointer_cast<ManagedSerializableTypeInfoList>(typeInfo);
  441. return listTypeInfo->mElementType->matches(mElementType);
  442. }
  443. bool ManagedSerializableTypeInfoList::isTypeLoaded() const
  444. {
  445. return mElementType->isTypeLoaded();
  446. }
  447. ::MonoClass* ManagedSerializableTypeInfoList::getMonoClass() const
  448. {
  449. ::MonoClass* elementClass = mElementType->getMonoClass();
  450. if(elementClass == nullptr)
  451. return nullptr;
  452. MonoClass* genericListClass = ScriptAssemblyManager::instance().getBuiltinClasses().systemGenericListClass;
  453. ::MonoClass* genParams[1] = { elementClass };
  454. return MonoUtil::bindGenericParameters(genericListClass->_getInternalClass(), genParams, 1);
  455. }
  456. RTTITypeBase* ManagedSerializableTypeInfoList::getRTTIStatic()
  457. {
  458. return ManagedSerializableTypeInfoListRTTI::instance();
  459. }
  460. RTTITypeBase* ManagedSerializableTypeInfoList::getRTTI() const
  461. {
  462. return ManagedSerializableTypeInfoList::getRTTIStatic();
  463. }
  464. bool ManagedSerializableTypeInfoDictionary::matches(const SPtr<ManagedSerializableTypeInfo>& typeInfo) const
  465. {
  466. if(!rtti_is_of_type<ManagedSerializableTypeInfoDictionary>(typeInfo))
  467. return false;
  468. auto dictTypeInfo = std::static_pointer_cast<ManagedSerializableTypeInfoDictionary>(typeInfo);
  469. return dictTypeInfo->mKeyType->matches(mKeyType) && dictTypeInfo->mValueType->matches(mValueType);
  470. }
  471. bool ManagedSerializableTypeInfoDictionary::isTypeLoaded() const
  472. {
  473. return mKeyType->isTypeLoaded() && mValueType->isTypeLoaded();
  474. }
  475. ::MonoClass* ManagedSerializableTypeInfoDictionary::getMonoClass() const
  476. {
  477. ::MonoClass* keyClass = mKeyType->getMonoClass();
  478. ::MonoClass* valueClass = mValueType->getMonoClass();
  479. if(keyClass == nullptr || valueClass == nullptr)
  480. return nullptr;
  481. MonoClass* genericDictionaryClass =
  482. ScriptAssemblyManager::instance().getBuiltinClasses().systemGenericDictionaryClass;
  483. ::MonoClass* params[2] = { keyClass, valueClass };
  484. return MonoUtil::bindGenericParameters(genericDictionaryClass->_getInternalClass(), params, 2);
  485. }
  486. RTTITypeBase* ManagedSerializableTypeInfoDictionary::getRTTIStatic()
  487. {
  488. return ManagedSerializableTypeInfoDictionaryRTTI::instance();
  489. }
  490. RTTITypeBase* ManagedSerializableTypeInfoDictionary::getRTTI() const
  491. {
  492. return ManagedSerializableTypeInfoDictionary::getRTTIStatic();
  493. }
  494. }