amulet-core 1.9.19__py3-none-any.whl → 1.9.20__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of amulet-core might be problematic. Click here for more details.

Files changed (198) hide show
  1. amulet/__init__.py +27 -27
  2. amulet/__pyinstaller/__init__.py +2 -2
  3. amulet/__pyinstaller/hook-amulet.py +4 -4
  4. amulet/_version.py +21 -21
  5. amulet/api/__init__.py +2 -2
  6. amulet/api/abstract_base_entity.py +128 -128
  7. amulet/api/block.py +630 -630
  8. amulet/api/block_entity.py +71 -71
  9. amulet/api/cache.py +107 -107
  10. amulet/api/chunk/__init__.py +6 -6
  11. amulet/api/chunk/biomes.py +207 -207
  12. amulet/api/chunk/block_entity_dict.py +175 -175
  13. amulet/api/chunk/blocks.py +46 -46
  14. amulet/api/chunk/chunk.py +389 -389
  15. amulet/api/chunk/entity_list.py +75 -75
  16. amulet/api/chunk/status.py +167 -167
  17. amulet/api/data_types/__init__.py +4 -4
  18. amulet/api/data_types/generic_types.py +4 -4
  19. amulet/api/data_types/operation_types.py +16 -16
  20. amulet/api/data_types/world_types.py +49 -49
  21. amulet/api/data_types/wrapper_types.py +71 -71
  22. amulet/api/entity.py +74 -74
  23. amulet/api/errors.py +119 -119
  24. amulet/api/history/__init__.py +36 -36
  25. amulet/api/history/base/__init__.py +3 -3
  26. amulet/api/history/base/base_history.py +26 -26
  27. amulet/api/history/base/history_manager.py +63 -63
  28. amulet/api/history/base/revision_manager.py +73 -73
  29. amulet/api/history/changeable.py +15 -15
  30. amulet/api/history/data_types.py +7 -7
  31. amulet/api/history/history_manager/__init__.py +3 -3
  32. amulet/api/history/history_manager/container.py +102 -102
  33. amulet/api/history/history_manager/database.py +279 -279
  34. amulet/api/history/history_manager/meta.py +93 -93
  35. amulet/api/history/history_manager/object.py +116 -116
  36. amulet/api/history/revision_manager/__init__.py +2 -2
  37. amulet/api/history/revision_manager/disk.py +33 -33
  38. amulet/api/history/revision_manager/ram.py +12 -12
  39. amulet/api/item.py +75 -75
  40. amulet/api/level/__init__.py +4 -4
  41. amulet/api/level/base_level/__init__.py +1 -1
  42. amulet/api/level/base_level/base_level.py +1035 -1026
  43. amulet/api/level/base_level/chunk_manager.py +227 -227
  44. amulet/api/level/base_level/clone.py +389 -389
  45. amulet/api/level/base_level/player_manager.py +101 -101
  46. amulet/api/level/immutable_structure/__init__.py +1 -1
  47. amulet/api/level/immutable_structure/immutable_structure.py +94 -94
  48. amulet/api/level/immutable_structure/void_format_wrapper.py +117 -117
  49. amulet/api/level/structure.py +22 -22
  50. amulet/api/level/world.py +19 -19
  51. amulet/api/partial_3d_array/__init__.py +2 -2
  52. amulet/api/partial_3d_array/base_partial_3d_array.py +263 -263
  53. amulet/api/partial_3d_array/bounded_partial_3d_array.py +528 -528
  54. amulet/api/partial_3d_array/data_types.py +15 -15
  55. amulet/api/partial_3d_array/unbounded_partial_3d_array.py +229 -229
  56. amulet/api/partial_3d_array/util.py +152 -152
  57. amulet/api/player.py +65 -65
  58. amulet/api/registry/__init__.py +2 -2
  59. amulet/api/registry/base_registry.py +34 -34
  60. amulet/api/registry/biome_manager.py +153 -153
  61. amulet/api/registry/block_manager.py +156 -156
  62. amulet/api/selection/__init__.py +2 -2
  63. amulet/api/selection/abstract_selection.py +315 -315
  64. amulet/api/selection/box.py +805 -805
  65. amulet/api/selection/group.py +488 -488
  66. amulet/api/structure.py +37 -37
  67. amulet/api/wrapper/__init__.py +8 -8
  68. amulet/api/wrapper/chunk/interface.py +441 -441
  69. amulet/api/wrapper/chunk/translator.py +567 -567
  70. amulet/api/wrapper/format_wrapper.py +772 -772
  71. amulet/api/wrapper/structure_format_wrapper.py +116 -116
  72. amulet/api/wrapper/world_format_wrapper.py +63 -63
  73. amulet/level/__init__.py +1 -1
  74. amulet/level/formats/anvil_forge_world.py +40 -40
  75. amulet/level/formats/anvil_world/__init__.py +3 -3
  76. amulet/level/formats/anvil_world/_sector_manager.py +291 -384
  77. amulet/level/formats/anvil_world/data_pack/__init__.py +2 -2
  78. amulet/level/formats/anvil_world/data_pack/data_pack.py +224 -224
  79. amulet/level/formats/anvil_world/data_pack/data_pack_manager.py +77 -77
  80. amulet/level/formats/anvil_world/dimension.py +177 -177
  81. amulet/level/formats/anvil_world/format.py +769 -769
  82. amulet/level/formats/anvil_world/region.py +384 -384
  83. amulet/level/formats/construction/__init__.py +3 -3
  84. amulet/level/formats/construction/format_wrapper.py +515 -515
  85. amulet/level/formats/construction/interface.py +134 -134
  86. amulet/level/formats/construction/section.py +60 -60
  87. amulet/level/formats/construction/util.py +165 -165
  88. amulet/level/formats/leveldb_world/__init__.py +3 -3
  89. amulet/level/formats/leveldb_world/chunk.py +33 -33
  90. amulet/level/formats/leveldb_world/dimension.py +385 -419
  91. amulet/level/formats/leveldb_world/format.py +659 -641
  92. amulet/level/formats/leveldb_world/interface/chunk/__init__.py +36 -36
  93. amulet/level/formats/leveldb_world/interface/chunk/base_leveldb_interface.py +836 -836
  94. amulet/level/formats/leveldb_world/interface/chunk/generate_interface.py +31 -31
  95. amulet/level/formats/leveldb_world/interface/chunk/leveldb_0.py +30 -30
  96. amulet/level/formats/leveldb_world/interface/chunk/leveldb_1.py +12 -12
  97. amulet/level/formats/leveldb_world/interface/chunk/leveldb_10.py +12 -12
  98. amulet/level/formats/leveldb_world/interface/chunk/leveldb_11.py +12 -12
  99. amulet/level/formats/leveldb_world/interface/chunk/leveldb_12.py +12 -12
  100. amulet/level/formats/leveldb_world/interface/chunk/leveldb_13.py +12 -12
  101. amulet/level/formats/leveldb_world/interface/chunk/leveldb_14.py +12 -12
  102. amulet/level/formats/leveldb_world/interface/chunk/leveldb_15.py +12 -12
  103. amulet/level/formats/leveldb_world/interface/chunk/leveldb_16.py +12 -12
  104. amulet/level/formats/leveldb_world/interface/chunk/leveldb_17.py +12 -12
  105. amulet/level/formats/leveldb_world/interface/chunk/leveldb_18.py +12 -12
  106. amulet/level/formats/leveldb_world/interface/chunk/leveldb_19.py +12 -12
  107. amulet/level/formats/leveldb_world/interface/chunk/leveldb_2.py +12 -12
  108. amulet/level/formats/leveldb_world/interface/chunk/leveldb_20.py +12 -12
  109. amulet/level/formats/leveldb_world/interface/chunk/leveldb_21.py +12 -12
  110. amulet/level/formats/leveldb_world/interface/chunk/leveldb_22.py +12 -12
  111. amulet/level/formats/leveldb_world/interface/chunk/leveldb_23.py +10 -10
  112. amulet/level/formats/leveldb_world/interface/chunk/leveldb_24.py +10 -10
  113. amulet/level/formats/leveldb_world/interface/chunk/leveldb_25.py +24 -24
  114. amulet/level/formats/leveldb_world/interface/chunk/leveldb_26.py +10 -10
  115. amulet/level/formats/leveldb_world/interface/chunk/leveldb_27.py +10 -10
  116. amulet/level/formats/leveldb_world/interface/chunk/leveldb_28.py +10 -10
  117. amulet/level/formats/leveldb_world/interface/chunk/leveldb_29.py +33 -33
  118. amulet/level/formats/leveldb_world/interface/chunk/leveldb_3.py +57 -57
  119. amulet/level/formats/leveldb_world/interface/chunk/leveldb_30.py +10 -10
  120. amulet/level/formats/leveldb_world/interface/chunk/leveldb_31.py +10 -10
  121. amulet/level/formats/leveldb_world/interface/chunk/leveldb_32.py +10 -10
  122. amulet/level/formats/leveldb_world/interface/chunk/leveldb_33.py +10 -10
  123. amulet/level/formats/leveldb_world/interface/chunk/leveldb_34.py +10 -10
  124. amulet/level/formats/leveldb_world/interface/chunk/leveldb_35.py +10 -10
  125. amulet/level/formats/leveldb_world/interface/chunk/leveldb_36.py +10 -10
  126. amulet/level/formats/leveldb_world/interface/chunk/leveldb_37.py +10 -10
  127. amulet/level/formats/leveldb_world/interface/chunk/leveldb_38.py +10 -10
  128. amulet/level/formats/leveldb_world/interface/chunk/leveldb_39.py +12 -12
  129. amulet/level/formats/leveldb_world/interface/chunk/leveldb_4.py +12 -12
  130. amulet/level/formats/leveldb_world/interface/chunk/leveldb_40.py +16 -16
  131. amulet/level/formats/leveldb_world/interface/chunk/leveldb_5.py +12 -12
  132. amulet/level/formats/leveldb_world/interface/chunk/leveldb_6.py +12 -12
  133. amulet/level/formats/leveldb_world/interface/chunk/leveldb_7.py +12 -12
  134. amulet/level/formats/leveldb_world/interface/chunk/leveldb_8.py +180 -180
  135. amulet/level/formats/leveldb_world/interface/chunk/leveldb_9.py +18 -18
  136. amulet/level/formats/leveldb_world/interface/chunk/leveldb_chunk_versions.py +79 -79
  137. amulet/level/formats/mcstructure/__init__.py +3 -3
  138. amulet/level/formats/mcstructure/chunk.py +50 -50
  139. amulet/level/formats/mcstructure/format_wrapper.py +408 -408
  140. amulet/level/formats/mcstructure/interface.py +175 -175
  141. amulet/level/formats/schematic/__init__.py +3 -3
  142. amulet/level/formats/schematic/chunk.py +55 -55
  143. amulet/level/formats/schematic/data_types.py +4 -4
  144. amulet/level/formats/schematic/format_wrapper.py +373 -373
  145. amulet/level/formats/schematic/interface.py +142 -142
  146. amulet/level/formats/sponge_schem/__init__.py +4 -4
  147. amulet/level/formats/sponge_schem/chunk.py +62 -62
  148. amulet/level/formats/sponge_schem/format_wrapper.py +463 -463
  149. amulet/level/formats/sponge_schem/interface.py +118 -118
  150. amulet/level/formats/sponge_schem/varint/__init__.py +1 -1
  151. amulet/level/formats/sponge_schem/varint/varint.py +87 -87
  152. amulet/level/interfaces/chunk/anvil/anvil_0.py +72 -72
  153. amulet/level/interfaces/chunk/anvil/anvil_1444.py +336 -336
  154. amulet/level/interfaces/chunk/anvil/anvil_1466.py +94 -94
  155. amulet/level/interfaces/chunk/anvil/anvil_1467.py +37 -37
  156. amulet/level/interfaces/chunk/anvil/anvil_1484.py +20 -20
  157. amulet/level/interfaces/chunk/anvil/anvil_1503.py +20 -20
  158. amulet/level/interfaces/chunk/anvil/anvil_1519.py +34 -34
  159. amulet/level/interfaces/chunk/anvil/anvil_1901.py +20 -20
  160. amulet/level/interfaces/chunk/anvil/anvil_1908.py +20 -20
  161. amulet/level/interfaces/chunk/anvil/anvil_1912.py +21 -21
  162. amulet/level/interfaces/chunk/anvil/anvil_1934.py +20 -20
  163. amulet/level/interfaces/chunk/anvil/anvil_2203.py +69 -69
  164. amulet/level/interfaces/chunk/anvil/anvil_2529.py +19 -19
  165. amulet/level/interfaces/chunk/anvil/anvil_2681.py +76 -76
  166. amulet/level/interfaces/chunk/anvil/anvil_2709.py +19 -19
  167. amulet/level/interfaces/chunk/anvil/anvil_2844.py +267 -267
  168. amulet/level/interfaces/chunk/anvil/anvil_3463.py +19 -19
  169. amulet/level/interfaces/chunk/anvil/anvil_na.py +607 -607
  170. amulet/level/interfaces/chunk/anvil/base_anvil_interface.py +326 -326
  171. amulet/level/load.py +59 -59
  172. amulet/level/loader.py +95 -95
  173. amulet/level/translators/chunk/bedrock/__init__.py +267 -267
  174. amulet/level/translators/chunk/bedrock/bedrock_nbt_blockstate_translator.py +46 -46
  175. amulet/level/translators/chunk/bedrock/bedrock_numerical_translator.py +39 -39
  176. amulet/level/translators/chunk/bedrock/bedrock_psudo_numerical_translator.py +37 -37
  177. amulet/level/translators/chunk/java/java_1_18_translator.py +40 -40
  178. amulet/level/translators/chunk/java/java_blockstate_translator.py +94 -94
  179. amulet/level/translators/chunk/java/java_numerical_translator.py +62 -62
  180. amulet/libs/leveldb/__init__.py +7 -7
  181. amulet/operations/__init__.py +5 -5
  182. amulet/operations/clone.py +18 -18
  183. amulet/operations/delete_chunk.py +32 -32
  184. amulet/operations/fill.py +30 -30
  185. amulet/operations/paste.py +65 -65
  186. amulet/operations/replace.py +58 -58
  187. amulet/utils/__init__.py +14 -14
  188. amulet/utils/format_utils.py +41 -41
  189. amulet/utils/generator.py +15 -15
  190. amulet/utils/matrix.py +243 -243
  191. amulet/utils/numpy_helpers.py +46 -46
  192. amulet/utils/world_utils.py +349 -349
  193. {amulet_core-1.9.19.dist-info → amulet_core-1.9.20.dist-info}/METADATA +97 -97
  194. amulet_core-1.9.20.dist-info/RECORD +208 -0
  195. amulet_core-1.9.19.dist-info/RECORD +0 -208
  196. {amulet_core-1.9.19.dist-info → amulet_core-1.9.20.dist-info}/WHEEL +0 -0
  197. {amulet_core-1.9.19.dist-info → amulet_core-1.9.20.dist-info}/entry_points.txt +0 -0
  198. {amulet_core-1.9.19.dist-info → amulet_core-1.9.20.dist-info}/top_level.txt +0 -0
@@ -1,315 +1,315 @@
1
- from __future__ import annotations
2
-
3
- from abc import ABC, abstractmethod
4
- from typing import Iterable, Tuple
5
- import numpy
6
- from .. import selection
7
-
8
- from amulet.api.data_types import (
9
- CoordinatesAny,
10
- ChunkCoordinates,
11
- SubChunkCoordinates,
12
- FloatTriplet,
13
- BlockCoordinates,
14
- )
15
-
16
-
17
- class AbstractBaseSelection(ABC):
18
- """
19
- A parent selection class to force a consistent API for selection group and box.
20
- """
21
-
22
- __slots__ = ()
23
-
24
- @abstractmethod
25
- def __contains__(self, item: CoordinatesAny) -> bool:
26
- """
27
- Is the given block/point contained within the selection.
28
-
29
- >>> (1, 2, 3) in selection1
30
- True
31
- >>> (1.5, 2.5, 3.5) in selection1
32
- True
33
-
34
- Will return False if the coordinate is on the most positive edge.
35
- See :meth:`contains_point` to include the top edge.
36
-
37
- :param item: The block/point to check.
38
- :return: True if the block/point is in the selection, False otherwise.
39
- """
40
- raise NotImplementedError
41
-
42
- @abstractmethod
43
- def __eq__(self, other) -> bool:
44
- """
45
- Is the selection equal to the other selection.
46
-
47
- >>> selection1 == selection2
48
- True
49
-
50
- :param other: The other selection to test.
51
- :return: True if the selections are the same, False otherwise.
52
- """
53
- raise NotImplementedError
54
-
55
- @abstractmethod
56
- def __iter__(self):
57
- raise NotImplementedError
58
-
59
- @abstractmethod
60
- def __repr__(self) -> str:
61
- raise NotImplementedError
62
-
63
- @abstractmethod
64
- def __str__(self) -> str:
65
- raise NotImplementedError
66
-
67
- @property
68
- @abstractmethod
69
- def blocks(self) -> Iterable[BlockCoordinates]:
70
- """
71
- The location of every block in the selection.
72
-
73
- :return: An iterable of block locations.
74
- """
75
- raise NotImplementedError
76
-
77
- @property
78
- @abstractmethod
79
- def bounds(self) -> Tuple[BlockCoordinates, BlockCoordinates]:
80
- """
81
- The minimum and maximum points in the selection.
82
- """
83
- raise NotImplementedError
84
-
85
- @property
86
- @abstractmethod
87
- def bounds_array(self) -> numpy.ndarray:
88
- """
89
- The minimum and maximum points in the selection as a numpy array.
90
- """
91
- raise NotImplementedError
92
-
93
- @abstractmethod
94
- def chunk_boxes(
95
- self, sub_chunk_size: int = 16
96
- ) -> Iterable[Tuple[ChunkCoordinates, selection.box.SelectionBox]]:
97
- """
98
- An iterable of chunk coordinates and boxes that intersect the selection and the chunk.
99
-
100
- >>> for (cx, cz), box in selection1.chunk_boxes():
101
- >>> ...
102
-
103
- :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
104
- """
105
- raise NotImplementedError
106
-
107
- @abstractmethod
108
- def chunk_count(self, sub_chunk_size: int = 16) -> int:
109
- """
110
- The number of chunks that intersect the selection.
111
-
112
- :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
113
- """
114
- raise NotImplementedError
115
-
116
- @abstractmethod
117
- def chunk_locations(self, sub_chunk_size: int = 16) -> Iterable[ChunkCoordinates]:
118
- """
119
- An iterable of chunk coordinates that intersect the selection.
120
-
121
- >>> for cx, cz in selection1.chunk_locations():
122
- >>> ...
123
-
124
- :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
125
- """
126
- raise NotImplementedError
127
-
128
- @abstractmethod
129
- def contains_block(self, coords: CoordinatesAny) -> bool:
130
- """
131
- Is the block contained within the selection.
132
-
133
- >>> (1, 2, 3) in selection1
134
- True
135
-
136
- :param coords: The coordinate of the block defined by the most negative corner.
137
- :return: True if the block is in the selection.
138
- """
139
- raise NotImplementedError
140
-
141
- # @abstractmethod
142
- # def contains_box(self, other: box.SelectionBox) -> bool:
143
- # raise NotImplementedError
144
-
145
- @abstractmethod
146
- def contains_point(self, coords: CoordinatesAny) -> bool:
147
- """
148
- Is the point contained within the selection.
149
-
150
- >>> (1.5, 2.5, 3.5) in selection1
151
- True
152
-
153
- :param coords: The coordinate of the point.
154
- :return: True if the point is in the selection.
155
- """
156
- raise NotImplementedError
157
-
158
- @abstractmethod
159
- def intersection(self, other):
160
- """
161
- Create and return a new a selection containing the volume that this selection and other both contain.
162
-
163
- If the selections do not intersect the returned selection will have no volume.
164
-
165
- Use :meth:`intersects` to test if the two selections intersect.
166
-
167
- :param other: The other selection.
168
- :return: A new selection containing the intersection.
169
- """
170
- raise NotImplementedError
171
-
172
- @abstractmethod
173
- def intersects(self, other) -> bool:
174
- """
175
- Does this selection intersect ``other``.
176
-
177
- :param other: The other selection.
178
- :return: True if the selections intersect, False otherwise.
179
- """
180
- raise NotImplementedError
181
-
182
- @property
183
- @abstractmethod
184
- def max(self) -> BlockCoordinates:
185
- """
186
- The maximum point in the selection.
187
- """
188
- raise NotImplementedError
189
-
190
- @property
191
- @abstractmethod
192
- def max_array(self) -> numpy.ndarray:
193
- """
194
- The maximum point in the selection as a numpy array.
195
- """
196
- raise NotImplementedError
197
-
198
- @property
199
- @abstractmethod
200
- def max_x(self) -> int:
201
- """
202
- The maximum x coordinate of the selection.
203
- """
204
- raise NotImplementedError
205
-
206
- @property
207
- @abstractmethod
208
- def max_y(self) -> int:
209
- """
210
- The maximum y coordinate of the selection.
211
- """
212
- raise NotImplementedError
213
-
214
- @property
215
- @abstractmethod
216
- def max_z(self) -> int:
217
- """
218
- The maximum z coordinate of the selection.
219
- """
220
- raise NotImplementedError
221
-
222
- @property
223
- @abstractmethod
224
- def min(self) -> BlockCoordinates:
225
- """
226
- The minimum point in the selection.
227
- """
228
- raise NotImplementedError
229
-
230
- @property
231
- @abstractmethod
232
- def min_array(self) -> numpy.ndarray:
233
- """
234
- The minimum point in the selection as a numpy array.
235
- """
236
- raise NotImplementedError
237
-
238
- @property
239
- @abstractmethod
240
- def min_x(self) -> int:
241
- """
242
- The minimum x coordinate of the selection.
243
- """
244
- raise NotImplementedError
245
-
246
- @property
247
- @abstractmethod
248
- def min_y(self) -> int:
249
- """
250
- The minimum y coordinate of the selection.
251
- """
252
- raise NotImplementedError
253
-
254
- @property
255
- @abstractmethod
256
- def min_z(self) -> int:
257
- """
258
- The minimum z coordinate of the selection.
259
- """
260
- raise NotImplementedError
261
-
262
- @abstractmethod
263
- def sub_chunk_boxes(
264
- self, sub_chunk_size: int = 16
265
- ) -> Iterable[Tuple[SubChunkCoordinates, selection.box.SelectionBox]]:
266
- """
267
- An iterable of sub-chunk coordinates and boxes that intersect the selection and the sub-chunk.
268
-
269
- >>> for (cx, cy, cz), box in selection1.sub_chunk_boxes():
270
- >>> ...
271
-
272
- :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
273
- """
274
- raise NotImplementedError
275
-
276
- @abstractmethod
277
- def sub_chunk_count(self, sub_chunk_size: int = 16) -> int:
278
- """
279
- The number of sub-chunks that intersect the selection.
280
-
281
- :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
282
- """
283
- raise NotImplementedError
284
-
285
- @abstractmethod
286
- def sub_chunk_locations(
287
- self, sub_chunk_size: int = 16
288
- ) -> Iterable[SubChunkCoordinates]:
289
- """
290
- An iterable of sub-chunk coordinates that intersect the selection.
291
-
292
- >>> for cx, cy, cz in selection1.sub_chunk_locations():
293
- >>> ...
294
-
295
- :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
296
- """
297
- raise NotImplementedError
298
-
299
- @abstractmethod
300
- def subtract(self, other):
301
- raise NotImplementedError
302
-
303
- @abstractmethod
304
- def transform(
305
- self, scale: FloatTriplet, rotation: FloatTriplet, translation: FloatTriplet
306
- ):
307
- raise NotImplementedError
308
-
309
- @property
310
- @abstractmethod
311
- def volume(self) -> int:
312
- """
313
- The number of blocks in the selection.
314
- """
315
- raise NotImplementedError
1
+ from __future__ import annotations
2
+
3
+ from abc import ABC, abstractmethod
4
+ from typing import Iterable, Tuple
5
+ import numpy
6
+ from .. import selection
7
+
8
+ from amulet.api.data_types import (
9
+ CoordinatesAny,
10
+ ChunkCoordinates,
11
+ SubChunkCoordinates,
12
+ FloatTriplet,
13
+ BlockCoordinates,
14
+ )
15
+
16
+
17
+ class AbstractBaseSelection(ABC):
18
+ """
19
+ A parent selection class to force a consistent API for selection group and box.
20
+ """
21
+
22
+ __slots__ = ()
23
+
24
+ @abstractmethod
25
+ def __contains__(self, item: CoordinatesAny) -> bool:
26
+ """
27
+ Is the given block/point contained within the selection.
28
+
29
+ >>> (1, 2, 3) in selection1
30
+ True
31
+ >>> (1.5, 2.5, 3.5) in selection1
32
+ True
33
+
34
+ Will return False if the coordinate is on the most positive edge.
35
+ See :meth:`contains_point` to include the top edge.
36
+
37
+ :param item: The block/point to check.
38
+ :return: True if the block/point is in the selection, False otherwise.
39
+ """
40
+ raise NotImplementedError
41
+
42
+ @abstractmethod
43
+ def __eq__(self, other) -> bool:
44
+ """
45
+ Is the selection equal to the other selection.
46
+
47
+ >>> selection1 == selection2
48
+ True
49
+
50
+ :param other: The other selection to test.
51
+ :return: True if the selections are the same, False otherwise.
52
+ """
53
+ raise NotImplementedError
54
+
55
+ @abstractmethod
56
+ def __iter__(self):
57
+ raise NotImplementedError
58
+
59
+ @abstractmethod
60
+ def __repr__(self) -> str:
61
+ raise NotImplementedError
62
+
63
+ @abstractmethod
64
+ def __str__(self) -> str:
65
+ raise NotImplementedError
66
+
67
+ @property
68
+ @abstractmethod
69
+ def blocks(self) -> Iterable[BlockCoordinates]:
70
+ """
71
+ The location of every block in the selection.
72
+
73
+ :return: An iterable of block locations.
74
+ """
75
+ raise NotImplementedError
76
+
77
+ @property
78
+ @abstractmethod
79
+ def bounds(self) -> Tuple[BlockCoordinates, BlockCoordinates]:
80
+ """
81
+ The minimum and maximum points in the selection.
82
+ """
83
+ raise NotImplementedError
84
+
85
+ @property
86
+ @abstractmethod
87
+ def bounds_array(self) -> numpy.ndarray:
88
+ """
89
+ The minimum and maximum points in the selection as a numpy array.
90
+ """
91
+ raise NotImplementedError
92
+
93
+ @abstractmethod
94
+ def chunk_boxes(
95
+ self, sub_chunk_size: int = 16
96
+ ) -> Iterable[Tuple[ChunkCoordinates, selection.box.SelectionBox]]:
97
+ """
98
+ An iterable of chunk coordinates and boxes that intersect the selection and the chunk.
99
+
100
+ >>> for (cx, cz), box in selection1.chunk_boxes():
101
+ >>> ...
102
+
103
+ :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
104
+ """
105
+ raise NotImplementedError
106
+
107
+ @abstractmethod
108
+ def chunk_count(self, sub_chunk_size: int = 16) -> int:
109
+ """
110
+ The number of chunks that intersect the selection.
111
+
112
+ :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
113
+ """
114
+ raise NotImplementedError
115
+
116
+ @abstractmethod
117
+ def chunk_locations(self, sub_chunk_size: int = 16) -> Iterable[ChunkCoordinates]:
118
+ """
119
+ An iterable of chunk coordinates that intersect the selection.
120
+
121
+ >>> for cx, cz in selection1.chunk_locations():
122
+ >>> ...
123
+
124
+ :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
125
+ """
126
+ raise NotImplementedError
127
+
128
+ @abstractmethod
129
+ def contains_block(self, coords: CoordinatesAny) -> bool:
130
+ """
131
+ Is the block contained within the selection.
132
+
133
+ >>> (1, 2, 3) in selection1
134
+ True
135
+
136
+ :param coords: The coordinate of the block defined by the most negative corner.
137
+ :return: True if the block is in the selection.
138
+ """
139
+ raise NotImplementedError
140
+
141
+ # @abstractmethod
142
+ # def contains_box(self, other: box.SelectionBox) -> bool:
143
+ # raise NotImplementedError
144
+
145
+ @abstractmethod
146
+ def contains_point(self, coords: CoordinatesAny) -> bool:
147
+ """
148
+ Is the point contained within the selection.
149
+
150
+ >>> (1.5, 2.5, 3.5) in selection1
151
+ True
152
+
153
+ :param coords: The coordinate of the point.
154
+ :return: True if the point is in the selection.
155
+ """
156
+ raise NotImplementedError
157
+
158
+ @abstractmethod
159
+ def intersection(self, other):
160
+ """
161
+ Create and return a new a selection containing the volume that this selection and other both contain.
162
+
163
+ If the selections do not intersect the returned selection will have no volume.
164
+
165
+ Use :meth:`intersects` to test if the two selections intersect.
166
+
167
+ :param other: The other selection.
168
+ :return: A new selection containing the intersection.
169
+ """
170
+ raise NotImplementedError
171
+
172
+ @abstractmethod
173
+ def intersects(self, other) -> bool:
174
+ """
175
+ Does this selection intersect ``other``.
176
+
177
+ :param other: The other selection.
178
+ :return: True if the selections intersect, False otherwise.
179
+ """
180
+ raise NotImplementedError
181
+
182
+ @property
183
+ @abstractmethod
184
+ def max(self) -> BlockCoordinates:
185
+ """
186
+ The maximum point in the selection.
187
+ """
188
+ raise NotImplementedError
189
+
190
+ @property
191
+ @abstractmethod
192
+ def max_array(self) -> numpy.ndarray:
193
+ """
194
+ The maximum point in the selection as a numpy array.
195
+ """
196
+ raise NotImplementedError
197
+
198
+ @property
199
+ @abstractmethod
200
+ def max_x(self) -> int:
201
+ """
202
+ The maximum x coordinate of the selection.
203
+ """
204
+ raise NotImplementedError
205
+
206
+ @property
207
+ @abstractmethod
208
+ def max_y(self) -> int:
209
+ """
210
+ The maximum y coordinate of the selection.
211
+ """
212
+ raise NotImplementedError
213
+
214
+ @property
215
+ @abstractmethod
216
+ def max_z(self) -> int:
217
+ """
218
+ The maximum z coordinate of the selection.
219
+ """
220
+ raise NotImplementedError
221
+
222
+ @property
223
+ @abstractmethod
224
+ def min(self) -> BlockCoordinates:
225
+ """
226
+ The minimum point in the selection.
227
+ """
228
+ raise NotImplementedError
229
+
230
+ @property
231
+ @abstractmethod
232
+ def min_array(self) -> numpy.ndarray:
233
+ """
234
+ The minimum point in the selection as a numpy array.
235
+ """
236
+ raise NotImplementedError
237
+
238
+ @property
239
+ @abstractmethod
240
+ def min_x(self) -> int:
241
+ """
242
+ The minimum x coordinate of the selection.
243
+ """
244
+ raise NotImplementedError
245
+
246
+ @property
247
+ @abstractmethod
248
+ def min_y(self) -> int:
249
+ """
250
+ The minimum y coordinate of the selection.
251
+ """
252
+ raise NotImplementedError
253
+
254
+ @property
255
+ @abstractmethod
256
+ def min_z(self) -> int:
257
+ """
258
+ The minimum z coordinate of the selection.
259
+ """
260
+ raise NotImplementedError
261
+
262
+ @abstractmethod
263
+ def sub_chunk_boxes(
264
+ self, sub_chunk_size: int = 16
265
+ ) -> Iterable[Tuple[SubChunkCoordinates, selection.box.SelectionBox]]:
266
+ """
267
+ An iterable of sub-chunk coordinates and boxes that intersect the selection and the sub-chunk.
268
+
269
+ >>> for (cx, cy, cz), box in selection1.sub_chunk_boxes():
270
+ >>> ...
271
+
272
+ :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
273
+ """
274
+ raise NotImplementedError
275
+
276
+ @abstractmethod
277
+ def sub_chunk_count(self, sub_chunk_size: int = 16) -> int:
278
+ """
279
+ The number of sub-chunks that intersect the selection.
280
+
281
+ :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
282
+ """
283
+ raise NotImplementedError
284
+
285
+ @abstractmethod
286
+ def sub_chunk_locations(
287
+ self, sub_chunk_size: int = 16
288
+ ) -> Iterable[SubChunkCoordinates]:
289
+ """
290
+ An iterable of sub-chunk coordinates that intersect the selection.
291
+
292
+ >>> for cx, cy, cz in selection1.sub_chunk_locations():
293
+ >>> ...
294
+
295
+ :param sub_chunk_size: The dimension of a sub-chunk. Default 16.
296
+ """
297
+ raise NotImplementedError
298
+
299
+ @abstractmethod
300
+ def subtract(self, other):
301
+ raise NotImplementedError
302
+
303
+ @abstractmethod
304
+ def transform(
305
+ self, scale: FloatTriplet, rotation: FloatTriplet, translation: FloatTriplet
306
+ ):
307
+ raise NotImplementedError
308
+
309
+ @property
310
+ @abstractmethod
311
+ def volume(self) -> int:
312
+ """
313
+ The number of blocks in the selection.
314
+ """
315
+ raise NotImplementedError