BsManagedSerializableArray.h 7.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185
  1. #pragma once
  2. #include "BsScriptEnginePrerequisites.h"
  3. #include "BsIReflectable.h"
  4. #include <mono/jit/jit.h>
  5. namespace BansheeEngine
  6. {
  7. /**
  8. * @brief Allows access to an underlying managed array, or a cached version of that array that
  9. * can be serialized/deserialized.
  10. *
  11. * @note This class can be in two states:
  12. * - Linked - When the object has a link to a managed object. This is the default
  13. * state when a new instance of ManagedSerializableObject is created.
  14. * Any operations during this state will operate directly on the linked
  15. * managed object.
  16. * - Serialized - When the object has no link to the managed object but instead just
  17. * contains cached object and field data that may be used for initializing
  18. * a managed object. Any operations during this state will operate
  19. * only on the cached internal data.
  20. * You can transfer between these states by calling serialize(linked->serialized) &
  21. * deserialize (serialized->linked).
  22. *
  23. */
  24. class BS_SCR_BE_EXPORT ManagedSerializableArray : public IReflectable
  25. {
  26. private:
  27. struct ConstructPrivately {};
  28. public:
  29. ManagedSerializableArray(const ConstructPrivately& dummy, const ManagedSerializableTypeInfoArrayPtr& typeInfo, MonoObject* managedInstance);
  30. ManagedSerializableArray(const ConstructPrivately& dummy);
  31. /**
  32. * @brief Returns the internal managed instance of the array. This will return null if
  33. * the object is in serialized mode.
  34. */
  35. MonoObject* getManagedInstance() const { return mManagedInstance; }
  36. /**
  37. * @brief Returns the type information for the internal array.
  38. */
  39. ManagedSerializableTypeInfoArrayPtr getTypeInfo() const { return mArrayTypeInfo; }
  40. /**
  41. * @brief Changes the size of the array. Operates on managed object if in linked state,
  42. * or on cached data otherwise.
  43. *
  44. * @param newSizes Array of sizes, one per array dimension. Number of sizes
  45. * must match number of array dimensions as specified by its type.
  46. */
  47. void resize(const Vector<UINT32>& newSizes);
  48. /**
  49. * @brief Returns the size of a specific dimension of the array. Operates on
  50. * managed object if in linked state, or on cached data otherwise.
  51. */
  52. UINT32 getLength(UINT32 dimension) const { return mNumElements[dimension]; }
  53. /**
  54. * @brief Returns the sizes of a all dimensions of the array. Operates on
  55. * managed object if in linked state, or on cached data otherwise.
  56. */
  57. Vector<UINT32> getLengths() const { return mNumElements; }
  58. /**
  59. * @brief Returns the total of all sizes of all dimensions of the array. Operates on
  60. * managed object if in linked state, or on cached data otherwise.
  61. */
  62. UINT32 getTotalLength() const;
  63. /**
  64. * @brief Sets a new element value at the specified array index. Operates on
  65. * managed object if in linked state, or on cached data otherwise.
  66. *
  67. * @param arrayIdx Index at which to set the value.
  68. * @param val Wrapper around the value to store in the array. Must be of the
  69. * array element type.
  70. */
  71. void setFieldData(UINT32 arrayIdx, const ManagedSerializableFieldDataPtr& val);
  72. /**
  73. * @brief Returns the element value at the specified array index. Operates on
  74. * managed object if in linked state, or on cached data otherwise.
  75. *
  76. * @param arrayIdx Index at which to retrieve the value.
  77. *
  78. * @return A wrapper around the element value in the array.
  79. */
  80. ManagedSerializableFieldDataPtr getFieldData(UINT32 arrayIdx);
  81. /**
  82. * @brief Serializes the internal managed object into a set of cached data that can be saved
  83. * in memory/disk and can be deserialized later. Does nothing if object is already is
  84. * serialized mode. When in serialized mode the reference to the managed instance will be lost.
  85. */
  86. void serialize();
  87. /**
  88. * @brief Deserializes a set of cached data into a managed object. This action may fail in case the cached
  89. * data contains a type that no longer exists. You may check if it completely successfully if ::getManagedInstance
  90. * returns non-null after.
  91. *
  92. * This action transfers the object into linked mode. All further operations will operate directly on the managed instance
  93. * and the cached data will be cleared. If you call this method on an already linked object the old object will be
  94. * replaced and initialized with empty data (since cached data does not exist).
  95. */
  96. void deserialize();
  97. /**
  98. * @brief Creates a managed serializable array that references an existing managed array. Created object will be in linked mode.
  99. *
  100. * @param managedInstance Constructed managed instance of the array to link with. Its type must correspond with the provided type info.
  101. * @param typeInfo Type information for the array and its elements.
  102. */
  103. static ManagedSerializableArrayPtr createFromExisting(MonoObject* managedInstance, const ManagedSerializableTypeInfoArrayPtr& typeInfo);
  104. /**
  105. * @brief Creates a managed serializable array that creates and references a brand new managed array instance.
  106. *
  107. * @param typeInfo Type of the array to create.
  108. * @param sizes Array of sizes, one per array dimension. Number of sizes must match number
  109. * of array dimensions as specified by its type.
  110. */
  111. static ManagedSerializableArrayPtr createNew(const ManagedSerializableTypeInfoArrayPtr& typeInfo, const Vector<UINT32>& sizes);
  112. /**
  113. * @brief Creates a managed array instance.
  114. *
  115. * @param typeInfo Type of the array to create.
  116. * @param sizes Array of sizes, one per array dimension. Number of sizes must match number
  117. * of array dimensions as specified by its type.
  118. */
  119. static MonoObject* createManagedInstance(const ManagedSerializableTypeInfoArrayPtr& typeInfo, const Vector<UINT32>& sizes);
  120. protected:
  121. /**
  122. * @brief Retrieves needed Mono types and methods. Should be called
  123. * before performing any operations with the managed object.
  124. */
  125. void initMonoObjects();
  126. /**
  127. * @brief Returns the size of the specified dimension of the array.
  128. * Operates on the internal managed object.
  129. */
  130. UINT32 getLengthInternal(UINT32 dimension) const;
  131. /**
  132. * @brief Sets a value at the specified index in the array.
  133. * Operates on the internal managed object.
  134. */
  135. void setValueInternal(UINT32 arrayIdx, void* val);
  136. /**
  137. * @brief Converts a multi-dimensional array index into
  138. * a sequential one-dimensional index.
  139. */
  140. UINT32 toSequentialIdx(const Vector<UINT32>& idx) const;
  141. MonoObject* mManagedInstance;
  142. ::MonoClass* mElementMonoClass;
  143. MonoMethod* mCopyMethod;
  144. ManagedSerializableTypeInfoArrayPtr mArrayTypeInfo;
  145. Vector<ManagedSerializableFieldDataPtr> mCachedEntries;
  146. Vector<UINT32> mNumElements;
  147. UINT32 mElemSize;
  148. /************************************************************************/
  149. /* RTTI */
  150. /************************************************************************/
  151. /**
  152. * @brief Creates an empty and uninitialized object used for serialization purposes.
  153. */
  154. static ManagedSerializableArrayPtr createNew();
  155. public:
  156. friend class ManagedSerializableArrayRTTI;
  157. static RTTITypeBase* getRTTIStatic();
  158. virtual RTTITypeBase* getRTTI() const override;
  159. };
  160. }