Mirror of Svelto.ECS because we're a fan of it
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

337 lines
12KB

  1. using Svelto.DataStructures;
  2. namespace Svelto.ECS
  3. {
  4. /// <summary>
  5. /// NOTE THESE ENUMERABLES EXIST TO AVOID BOILERPLATE CODE AS THEY SKIP 0 SIZED GROUPS
  6. /// However if the normal pattern with the double foreach is used, this is not necessary
  7. /// Note: atm cannot be ref structs because they are returned in a valuetuple
  8. /// </summary>
  9. /// <typeparam name="T1"></typeparam>
  10. /// <typeparam name="T2"></typeparam>
  11. /// <typeparam name="T3"></typeparam>
  12. /// <typeparam name="T4"></typeparam>
  13. public readonly ref struct GroupsEnumerable<T1, T2, T3, T4> where T1 : struct, IEntityComponent
  14. where T2 : struct, IEntityComponent
  15. where T3 : struct, IEntityComponent
  16. where T4 : struct, IEntityComponent
  17. {
  18. public GroupsEnumerable(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups)
  19. {
  20. _db = db;
  21. _groups = groups;
  22. }
  23. public ref struct GroupsIterator
  24. {
  25. public GroupsIterator(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups) : this()
  26. {
  27. _groups = groups;
  28. _indexGroup = -1;
  29. _entitiesDB = db;
  30. }
  31. public bool MoveNext()
  32. {
  33. //attention, the while is necessary to skip empty groups
  34. while (++_indexGroup < _groups.count)
  35. {
  36. var exclusiveGroupStruct = _groups[_indexGroup];
  37. if (!exclusiveGroupStruct.IsEnabled())
  38. continue;
  39. var entityCollection1 = _entitiesDB.QueryEntities<T1, T2, T3, T4>(exclusiveGroupStruct);
  40. var array = entityCollection1;
  41. _buffers = new EntityCollection<T1, T2, T3, T4>(array.buffer1, array.buffer2, array.buffer3
  42. , array.buffer4);
  43. break;
  44. }
  45. var moveNext = _indexGroup < _groups.count;
  46. if (moveNext == false)
  47. Reset();
  48. return moveNext;
  49. }
  50. public void Reset() { _indexGroup = -1; }
  51. public RefCurrent Current => new RefCurrent(_buffers, _groups[_indexGroup]);
  52. public bool isValid => _indexGroup != -1;
  53. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  54. int _indexGroup;
  55. EntityCollection<T1, T2, T3, T4> _buffers;
  56. readonly EntitiesDB _entitiesDB;
  57. }
  58. public GroupsIterator GetEnumerator() { return new GroupsIterator(_db, _groups); }
  59. readonly EntitiesDB _db;
  60. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  61. public readonly ref struct RefCurrent
  62. {
  63. public RefCurrent(in EntityCollection<T1, T2, T3, T4> buffers, ExclusiveGroupStruct group)
  64. {
  65. _buffers = buffers;
  66. _group = group;
  67. }
  68. public void Deconstruct(out EntityCollection<T1, T2, T3, T4> buffers, out ExclusiveGroupStruct group)
  69. {
  70. buffers = _buffers;
  71. group = _group;
  72. }
  73. public readonly EntityCollection<T1, T2, T3, T4> _buffers;
  74. public readonly ExclusiveGroupStruct _group;
  75. }
  76. }
  77. public readonly ref struct GroupsEnumerable<T1, T2, T3> where T1 : struct, IEntityComponent
  78. where T2 : struct, IEntityComponent
  79. where T3 : struct, IEntityComponent
  80. {
  81. public GroupsEnumerable(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups)
  82. {
  83. _db = db;
  84. _groups = groups;
  85. }
  86. public ref struct GroupsIterator
  87. {
  88. public GroupsIterator(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups) : this()
  89. {
  90. _groups = groups;
  91. _indexGroup = -1;
  92. _entitiesDB = db;
  93. }
  94. public bool MoveNext()
  95. {
  96. //attention, the while is necessary to skip empty groups
  97. while (++_indexGroup < _groups.count)
  98. {
  99. var exclusiveGroupStruct = _groups[_indexGroup];
  100. if (!exclusiveGroupStruct.IsEnabled())
  101. continue;
  102. var entityCollection = _entitiesDB.QueryEntities<T1, T2, T3>(exclusiveGroupStruct);
  103. if (entityCollection.count == 0)
  104. continue;
  105. _buffers = entityCollection;
  106. break;
  107. }
  108. var moveNext = _indexGroup < _groups.count;
  109. if (moveNext == false)
  110. Reset();
  111. return moveNext;
  112. }
  113. public void Reset() { _indexGroup = -1; }
  114. public RefCurrent Current => new RefCurrent(_buffers, _groups[_indexGroup]);
  115. public bool isValid => _indexGroup != -1;
  116. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  117. int _indexGroup;
  118. EntityCollection<T1, T2, T3> _buffers;
  119. readonly EntitiesDB _entitiesDB;
  120. }
  121. public GroupsIterator GetEnumerator() { return new GroupsIterator(_db, _groups); }
  122. readonly EntitiesDB _db;
  123. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  124. public readonly ref struct RefCurrent
  125. {
  126. public RefCurrent(in EntityCollection<T1, T2, T3> buffers, ExclusiveGroupStruct group)
  127. {
  128. _buffers = buffers;
  129. _group = group;
  130. }
  131. public void Deconstruct(out EntityCollection<T1, T2, T3> buffers, out ExclusiveGroupStruct group)
  132. {
  133. buffers = _buffers;
  134. group = _group;
  135. }
  136. public readonly EntityCollection<T1, T2, T3> _buffers;
  137. public readonly ExclusiveGroupStruct _group;
  138. }
  139. }
  140. public readonly ref struct GroupsEnumerable<T1, T2>
  141. where T1 : struct, IEntityComponent where T2 : struct, IEntityComponent
  142. {
  143. public GroupsEnumerable(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups)
  144. {
  145. _db = db;
  146. _groups = groups;
  147. }
  148. public ref struct GroupsIterator
  149. {
  150. public GroupsIterator(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups) : this()
  151. {
  152. _db = db;
  153. _groups = groups;
  154. _indexGroup = -1;
  155. }
  156. public bool MoveNext()
  157. {
  158. //attention, the while is necessary to skip empty groups
  159. while (++_indexGroup < _groups.count)
  160. {
  161. var exclusiveGroupStruct = _groups[_indexGroup];
  162. if (!exclusiveGroupStruct.IsEnabled())
  163. continue;
  164. var entityCollection = _db.QueryEntities<T1, T2>(exclusiveGroupStruct);
  165. if (entityCollection.count == 0)
  166. continue;
  167. _buffers = entityCollection;
  168. break;
  169. }
  170. var moveNext = _indexGroup < _groups.count;
  171. if (moveNext == false)
  172. Reset();
  173. return moveNext;
  174. }
  175. public void Reset() { _indexGroup = -1; }
  176. public RefCurrent Current => new RefCurrent(_buffers, _groups[_indexGroup]);
  177. public bool isValid => _indexGroup != -1;
  178. readonly EntitiesDB _db;
  179. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  180. int _indexGroup;
  181. EntityCollection<T1, T2> _buffers;
  182. }
  183. public GroupsIterator GetEnumerator() { return new GroupsIterator(_db, _groups); }
  184. readonly EntitiesDB _db;
  185. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  186. public readonly ref struct RefCurrent
  187. {
  188. public RefCurrent(in EntityCollection<T1, T2> buffers, ExclusiveGroupStruct group)
  189. {
  190. _buffers = buffers;
  191. _group = group;
  192. }
  193. public void Deconstruct(out EntityCollection<T1, T2> buffers, out ExclusiveGroupStruct group)
  194. {
  195. buffers = _buffers;
  196. group = _group;
  197. }
  198. public readonly EntityCollection<T1, T2> _buffers;
  199. public readonly ExclusiveGroupStruct _group;
  200. }
  201. }
  202. public readonly ref struct GroupsEnumerable<T1> where T1 : struct, IEntityComponent
  203. {
  204. public GroupsEnumerable(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups)
  205. {
  206. _db = db;
  207. _groups = groups;
  208. }
  209. public ref struct GroupsIterator
  210. {
  211. public GroupsIterator(EntitiesDB db, in LocalFasterReadOnlyList<ExclusiveGroupStruct> groups) : this()
  212. {
  213. _db = db;
  214. _groups = groups;
  215. _indexGroup = -1;
  216. }
  217. public bool MoveNext()
  218. {
  219. //attention, the while is necessary to skip empty groups
  220. while (++_indexGroup < _groups.count)
  221. {
  222. var exclusiveGroupStruct = _groups[_indexGroup];
  223. if (!exclusiveGroupStruct.IsEnabled())
  224. continue;
  225. var entityCollection = _db.QueryEntities<T1>(exclusiveGroupStruct);
  226. if (entityCollection.count == 0)
  227. continue;
  228. _buffer = entityCollection;
  229. break;
  230. }
  231. var moveNext = _indexGroup < _groups.count;
  232. if (moveNext == false)
  233. Reset();
  234. return moveNext;
  235. }
  236. public void Reset() { _indexGroup = -1; }
  237. public RefCurrent Current => new RefCurrent(_buffer, _groups[_indexGroup]);
  238. public bool isValid => _indexGroup != -1;
  239. readonly EntitiesDB _db;
  240. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  241. int _indexGroup;
  242. EntityCollection<T1> _buffer;
  243. }
  244. public GroupsIterator GetEnumerator() { return new GroupsIterator(_db, _groups); }
  245. readonly EntitiesDB _db;
  246. readonly LocalFasterReadOnlyList<ExclusiveGroupStruct> _groups;
  247. public readonly ref struct RefCurrent
  248. {
  249. public RefCurrent(in EntityCollection<T1> buffers, in ExclusiveGroupStruct group)
  250. {
  251. _buffers = buffers;
  252. _group = group;
  253. }
  254. public void Deconstruct(out EntityCollection<T1> buffers, out ExclusiveGroupStruct group)
  255. {
  256. buffers = _buffers;
  257. group = _group;
  258. }
  259. public void Deconstruct(out EntityCollection<T1> buffers)
  260. {
  261. buffers = _buffers;
  262. }
  263. internal readonly EntityCollection<T1> _buffers;
  264. internal readonly ExclusiveGroupStruct _group;
  265. }
  266. }
  267. }