Skip to content

Commit cd97bd5

Browse files
dordsor21octylFractalaurorasmilesme4502TiagoFar78
authored
feat: update [entity/block] transforms (#3278)
Co-authored-by: Octavia Togami <octavia.togami@gmail.com> Co-authored-by: aurora <aurora@cutiepie.at> Co-authored-by: Maddy Miller <git@madelinemiller.dev> Co-authored-by: TiagoFar78 <42421954+TiagoFar78@users.noreply.github.com>
1 parent 01ea271 commit cd97bd5

6 files changed

Lines changed: 328 additions & 147 deletions

File tree

worldedit-bukkit/src/main/java/com/fastasyncworldedit/bukkit/adapter/NativeEntityFunctionSet.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ public boolean contains(Object get) {
3838
if (!(get instanceof com.sk89q.worldedit.entity.Entity e)) {
3939
return false;
4040
}
41-
UUID getUUID = e.getState().getNbtData().getUUID();
41+
UUID getUUID = e.getState().getUUID();
4242
for (NativeEntity entity : nativeEntities) {
4343
UUID uuid = uuidGetter.apply(entity);
4444
if (uuid.equals(getUUID)) {

worldedit-core/src/main/java/com/fastasyncworldedit/core/extent/clipboard/LinearClipboard.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ public void removeEntity(int x, int y, int z, UUID uuid) {
123123
Iterator<ClipboardEntity> iter = this.entities.iterator();
124124
while (iter.hasNext()) {
125125
ClipboardEntity entity = iter.next();
126-
UUID entUUID = entity.getState().getNbtData().getUUID();
126+
UUID entUUID = entity.getState().getUUID();
127127
if (uuid.equals(entUUID)) {
128128
iter.remove();
129129
return;
@@ -140,7 +140,7 @@ public List<? extends Entity> getEntities() {
140140
public void removeEntity(Entity entity) {
141141
if (!(entity instanceof BlockArrayClipboard.ClipboardEntity)) {
142142
Location loc = entity.getLocation();
143-
removeEntity(loc.getBlockX(), loc.getBlockY(), loc.getBlockZ(), entity.getState().getNbtData().getUUID());
143+
removeEntity(loc.getBlockX(), loc.getBlockY(), loc.getBlockZ(), entity.getState().getUUID());
144144
} else {
145145
this.entities.remove(entity);
146146
}

worldedit-core/src/main/java/com/sk89q/worldedit/entity/BaseEntity.java

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,15 @@
2525
import com.sk89q.worldedit.world.entity.EntityType;
2626
import com.sk89q.worldedit.world.entity.EntityTypes;
2727
import org.enginehub.linbus.tree.LinCompoundTag;
28+
import org.enginehub.linbus.tree.LinIntArrayTag;
29+
import org.enginehub.linbus.tree.LinLongTag;
30+
import org.enginehub.linbus.tree.LinTag;
2831

2932
import javax.annotation.Nullable;
3033

34+
import java.util.Map;
35+
import java.util.UUID;
36+
3137
import static com.google.common.base.Preconditions.checkNotNull;
3238

3339
/**
@@ -119,6 +125,33 @@ public EntityType getType() {
119125
public BaseEntity(CompoundTag tag) {
120126
this(EntityTypes.parse(tag.getString("Id")), tag);
121127
}
128+
129+
/**
130+
* Attempt to retrieve the entity's UUID from its NBT tag
131+
*
132+
* @return entity UUID if possible to retrieve
133+
* @since TODO
134+
*/
135+
@Nullable
136+
public UUID getUUID() {
137+
LinCompoundTag tag = getNbt();
138+
if (tag == null) {
139+
return null;
140+
}
141+
Map<String, LinTag<?>> value = tag.value();
142+
if (value.get("UUID") instanceof LinIntArrayTag intArrayTag) {
143+
int[] arr = intArrayTag.value();
144+
return new UUID((long) arr[0] << 32 | (arr[1] & 0xFFFFFFFFL), (long) arr[2] << 32 | (arr[3] & 0xFFFFFFFFL));
145+
} else if (value.get("UUIDMost") instanceof LinLongTag longTag) {
146+
return new UUID(longTag.value(), ((LinLongTag) value.get("UUIDLeast")).value());
147+
} else if (value.get("WorldUUIDMost") instanceof LinLongTag longTag) {
148+
return new UUID(longTag.value(), ((LinLongTag) value.get("WorldUUIDLeast")).value());
149+
} else if (value.get("PersistentIDMSB") instanceof LinLongTag longTag) {
150+
return new UUID(longTag.value(), ((LinLongTag) value.get("PersistentIDLSB")).value());
151+
} else {
152+
return null;
153+
}
154+
}
122155
//FAWE end
123156

124157
}

worldedit-core/src/main/java/com/sk89q/worldedit/extent/transform/BlockTransformExtent.java

Lines changed: 91 additions & 74 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,6 @@
2424
import com.fastasyncworldedit.core.registry.state.PropertyKey;
2525
import com.fastasyncworldedit.core.registry.state.PropertyKeySet;
2626
import com.google.common.collect.ImmutableMap;
27-
import com.sk89q.jnbt.ByteTag;
28-
import com.sk89q.jnbt.CompoundTag;
29-
import com.sk89q.jnbt.Tag;
3027
import com.sk89q.worldedit.WorldEditException;
3128
import com.sk89q.worldedit.extent.Extent;
3229
import com.sk89q.worldedit.internal.helper.MCDirections;
@@ -46,13 +43,15 @@
4643
import com.sk89q.worldedit.world.block.BlockTypes;
4744
import com.sk89q.worldedit.world.block.BlockTypesCache;
4845
import org.apache.logging.log4j.Logger;
46+
import org.enginehub.linbus.tree.LinCompoundTag;
47+
import org.enginehub.linbus.tree.LinNumberTag;
48+
import org.enginehub.linbus.tree.LinTag;
4949

5050
import javax.annotation.Nonnull;
5151
import javax.annotation.Nullable;
5252
import java.util.ArrayList;
5353
import java.util.Arrays;
5454
import java.util.Collection;
55-
import java.util.HashMap;
5655
import java.util.List;
5756
import java.util.Locale;
5857
import java.util.Map;
@@ -63,6 +62,10 @@
6362
import static com.sk89q.worldedit.util.Direction.ASCENDING_NORTH;
6463
import static com.sk89q.worldedit.util.Direction.ASCENDING_SOUTH;
6564
import static com.sk89q.worldedit.util.Direction.ASCENDING_WEST;
65+
import static com.sk89q.worldedit.util.Direction.DESCENDING_EAST;
66+
import static com.sk89q.worldedit.util.Direction.DESCENDING_NORTH;
67+
import static com.sk89q.worldedit.util.Direction.DESCENDING_SOUTH;
68+
import static com.sk89q.worldedit.util.Direction.DESCENDING_WEST;
6669
import static com.sk89q.worldedit.util.Direction.DOWN;
6770
import static com.sk89q.worldedit.util.Direction.EAST;
6871
import static com.sk89q.worldedit.util.Direction.Flag;
@@ -75,7 +78,6 @@
7578
import static com.sk89q.worldedit.util.Direction.UP;
7679
import static com.sk89q.worldedit.util.Direction.WEST;
7780
import static com.sk89q.worldedit.util.Direction.findClosest;
78-
import static com.sk89q.worldedit.util.Direction.values;
7981

8082
/**
8183
* Transforms blocks themselves (but not their position) according to a
@@ -96,7 +98,8 @@ public class BlockTransformExtent extends ResettableExtent {
9698
PropertyKey.NORTH,
9799
PropertyKey.EAST,
98100
PropertyKey.SOUTH,
99-
PropertyKey.WEST
101+
PropertyKey.WEST,
102+
PropertyKey.ORIENTATION
100103
);
101104

102105
private static final Map<Direction, PropertyKey> directionMap = ImmutableMap.of(
@@ -159,12 +162,11 @@ private static long[] adapt(Long... dirs) {
159162
return arr;
160163
}
161164

162-
private static long[] getDirections(AbstractProperty property) {
163-
if (property instanceof DirectionalProperty) {
164-
DirectionalProperty directional = (DirectionalProperty) property;
165-
return adapt(directional.getValues().toArray(new Direction[0]));
165+
private static long[] getDirections(AbstractProperty<?> property) {
166+
if (property instanceof final DirectionalProperty dir) {
167+
return adapt(dir.getValues().toArray(new Direction[0]));
166168
} else {
167-
List values = property.getValues();
169+
List<?> values = property.getValues();
168170
PropertyKey key = property.getKey();
169171
switch (key.getName().toLowerCase()) {
170172
case "half": {
@@ -176,20 +178,19 @@ private static long[] getDirections(AbstractProperty property) {
176178
case "rotation": {
177179
List<Direction> directions = new ArrayList<>();
178180
for (Object value : values) {
179-
directions.add(Direction.fromRotationIndex((Integer) value).get());
181+
directions.add(Direction.fromRotationIndex((Integer) value).orElseThrow());
180182
}
181183
return adapt(directions.toArray(new Direction[0]));
182184
}
183185
case "axis": {
184-
switch (property.getValues().size()) {
185-
case 3:
186-
return adapt(combine(EAST, WEST), combine(UP, DOWN), combine(SOUTH, NORTH));
187-
case 2:
188-
return adapt(combine(EAST, WEST), combine(SOUTH, NORTH));
189-
default:
186+
return switch (property.getValues().size()) {
187+
case 3 -> adapt(combine(EAST, WEST), combine(UP, DOWN), combine(SOUTH, NORTH));
188+
case 2 -> adapt(combine(EAST, WEST), combine(SOUTH, NORTH));
189+
default -> {
190190
LOGGER.error("Invalid {} {}", property.getName(), property.getValues());
191-
return null;
192-
}
191+
yield null;
192+
}
193+
};
193194
}
194195
case "facing": {
195196
List<Direction> directions = new ArrayList<>();
@@ -222,28 +223,14 @@ private static long[] getDirections(AbstractProperty property) {
222223
case "straight":
223224
result.add(combine(NORTH, EAST, SOUTH, WEST));
224225
continue;
225-
case "inner_left":
226+
case "inner_left", "inner_right":
226227
result.add(orIndex(
227228
combine(NORTHEAST, NORTHWEST, SOUTHWEST, SOUTHEAST),
228229
property.getIndexFor("outer_right"),
229230
property.getIndexFor("outer_left")
230231
));
231232
continue;
232-
case "inner_right":
233-
result.add(orIndex(
234-
combine(NORTHEAST, NORTHWEST, SOUTHWEST, SOUTHEAST),
235-
property.getIndexFor("outer_right"),
236-
property.getIndexFor("outer_left")
237-
));
238-
continue;
239-
case "outer_left":
240-
result.add(orIndex(
241-
combine(NORTHEAST, NORTHWEST, SOUTHWEST, SOUTHEAST),
242-
property.getIndexFor("inner_left"),
243-
property.getIndexFor("inner_right")
244-
));
245-
continue;
246-
case "outer_right":
233+
case "outer_left", "outer_right":
247234
result.add(orIndex(
248235
combine(NORTHEAST, NORTHWEST, SOUTHWEST, SOUTHEAST),
249236
property.getIndexFor("inner_left"),
@@ -298,6 +285,38 @@ private static long[] getDirections(AbstractProperty property) {
298285
return adapt(directions.toArray(new Long[0]));
299286
}
300287
}
288+
case "orientiation": {
289+
List<Long> directions = new ArrayList<>();
290+
for (Object value : values) {
291+
switch (value.toString()) {
292+
case "ascending_east":
293+
directions.add(combine(ASCENDING_EAST));
294+
break;
295+
case "ascending_west":
296+
directions.add(combine(ASCENDING_WEST));
297+
break;
298+
case "ascending_north":
299+
directions.add(combine(ASCENDING_NORTH));
300+
break;
301+
case "ascending_south":
302+
directions.add(combine(ASCENDING_SOUTH));
303+
break;
304+
case "descending_east":
305+
directions.add(combine(DESCENDING_EAST));
306+
break;
307+
case "descending_west":
308+
directions.add(combine(DESCENDING_WEST));
309+
break;
310+
case "descending_north":
311+
directions.add(combine(DESCENDING_NORTH));
312+
break;
313+
case "descending_south":
314+
directions.add(combine(DESCENDING_SOUTH));
315+
break;
316+
}
317+
}
318+
return adapt(directions.toArray(new Long[0]));
319+
}
301320
}
302321
}
303322
return null;
@@ -309,13 +328,13 @@ private static boolean hasDirection(long mask, Direction dir) {
309328

310329
private static long orIndex(long mask, int... indexes) {
311330
for (int index : indexes) {
312-
mask = mask | (1L << (index + values().length));
331+
mask = mask | (1L << (index + Direction.values().length));
313332
}
314333
return mask;
315334
}
316335

317336
private static boolean hasIndex(long mask, int index) {
318-
return ((mask >> values().length) & (1 << index)) == 0;
337+
return ((mask >> Direction.values().length) & (1L << index)) == 0;
319338
}
320339

321340
@Nullable
@@ -326,7 +345,7 @@ private static Integer getNewStateIndex(Transform transform, long[] directions,
326345
}
327346
Integer newIndex = null;
328347

329-
for (Direction oldDirection : values()) {
348+
for (Direction oldDirection : Direction.values()) {
330349
if (!hasDirection(oldDirMask, oldDirection)) {
331350
continue;
332351
}
@@ -370,7 +389,7 @@ private static Integer getNewStateIndex(Transform transform, long[] directions,
370389
return newIndex;
371390
}
372391

373-
private static boolean isDirectional(Property property) {
392+
private static boolean isDirectional(Property<?> property) {
374393
if (property instanceof DirectionalProperty) {
375394
return true;
376395
}
@@ -381,35 +400,33 @@ private static boolean isDirectional(Property property) {
381400
return (values.contains("top") || values.contains("left"));
382401
}
383402

384-
private static BaseBlock transformBaseBlockNBT(BlockState transformed, CompoundTag tag, Transform transform) {
385-
if (tag != null) {
386-
if (tag.containsKey("Rot")) {
387-
int rot = tag.asInt("Rot");
388-
389-
Direction direction = MCDirections.fromRotation(rot);
390-
391-
if (direction != null) {
392-
Vector3 applyAbsolute = transform.apply(direction.toVector());
393-
Vector3 applyOrigin = transform.apply(Vector3.ZERO);
394-
applyAbsolute.mutX(applyAbsolute.x() - applyOrigin.x());
395-
applyAbsolute.mutY(applyAbsolute.y() - applyOrigin.y());
396-
applyAbsolute.mutZ(applyAbsolute.z() - applyOrigin.z());
397-
398-
Direction newDirection = Direction.findClosest(
399-
applyAbsolute,
400-
Direction.Flag.CARDINAL | Direction.Flag.ORDINAL | Direction.Flag.SECONDARY_ORDINAL
401-
);
402-
403-
if (newDirection != null) {
404-
Map<String, Tag<?, ?>> values = new HashMap<>(tag.getValue());
405-
values.put("Rot", new ByteTag((byte) MCDirections.toRotation(newDirection)));
406-
tag = new CompoundTag(values);
407-
}
403+
private static BaseBlock transformBaseBlockNBT(BlockState transformed, @Nonnull LinCompoundTag tag, Transform transform) {
404+
Map<String, LinTag<?>> value = tag.value();
405+
if (value.get("Rot") instanceof LinNumberTag<?> rotTag) {
406+
int rot = rotTag.value().intValue();
407+
408+
Direction direction = MCDirections.fromRotation(rot);
409+
410+
if (direction != null) {
411+
Vector3 applyAbsolute = transform.apply(direction.toVector());
412+
Vector3 applyOrigin = transform.apply(Vector3.ZERO);
413+
applyAbsolute.mutX(applyAbsolute.x() - applyOrigin.x());
414+
applyAbsolute.mutY(applyAbsolute.y() - applyOrigin.y());
415+
applyAbsolute.mutZ(applyAbsolute.z() - applyOrigin.z());
416+
417+
Direction newDirection = Direction.findClosest(
418+
applyAbsolute,
419+
Direction.Flag.CARDINAL | Direction.Flag.ORDINAL | Direction.Flag.SECONDARY_ORDINAL
420+
);
421+
422+
if (newDirection != null) {
423+
LinCompoundTag.Builder builder = tag.toBuilder();
424+
builder.putByte("Rot", (byte) MCDirections.toRotation(newDirection));
425+
return transformed.toBaseBlock(builder.build());
408426
}
409427
}
410-
return new BaseBlock(transformed, tag);
411428
}
412-
return transformed.toBaseBlock();
429+
return transformed.toBaseBlock(tag);
413430
}
414431

415432
private static int transformState(BlockState state, Transform transform) {
@@ -432,7 +449,7 @@ private static int transformState(BlockState state, Transform transform) {
432449
newMaskedId = tmp.getInternalId();
433450
}
434451
// True if relying on two different "directions" for the result, e.g. stairs with both facing and shape
435-
for (AbstractProperty property : (List<AbstractProperty<?>>) type.getProperties()) {
452+
for (AbstractProperty<?> property : (List<AbstractProperty<?>>) type.getProperties()) {
436453
if (isDirectional(property)) {
437454
long[] directions = getDirections(property);
438455
if (directions != null) {
@@ -467,7 +484,7 @@ private void cache() {
467484
BLOCK_TRANSFORM_INVERSE[i] = ALL;
468485
BlockType type = BlockTypes.get(i);
469486
int bitMask = 0;
470-
for (AbstractProperty property : (Collection<AbstractProperty>) (Collection) type.getProperties()) {
487+
for (AbstractProperty<?> property : (Collection<AbstractProperty>) (Collection) type.getProperties()) {
471488
if (isDirectional(property)) {
472489
BLOCK_TRANSFORM[i] = null;
473490
BLOCK_TRANSFORM_INVERSE[i] = null;
@@ -556,8 +573,8 @@ public static <B extends BlockStateHolder<B>> B transform(@Nonnull B block, @Non
556573
int transformedId = transformState(state, transform);
557574
BlockState transformed = BlockState.getFromInternalId(transformedId);
558575
boolean baseBlock = block instanceof BaseBlock;
559-
if (baseBlock && block.hasNbtData()) {
560-
return (B) transformBaseBlockNBT(transformed, block.getNbtData(), transform);
576+
if (baseBlock && block.getNbt() != null) {
577+
return (B) transformBaseBlockNBT(transformed, block.getNbt(), transform);
561578
}
562579
return (B) (baseBlock? transformed.toBaseBlock() : transformed);
563580
//FAWE end
@@ -591,16 +608,16 @@ private BlockState transform(BlockState state, int[][] transformArray, Transform
591608

592609
public final BaseBlock transform(BlockStateHolder<BaseBlock> block) {
593610
BlockState transformed = transform(block.toImmutableState());
594-
if (block.hasNbtData()) {
595-
return transformBaseBlockNBT(transformed, block.getNbtData(), transform);
611+
if (block.getNbt() != null) {
612+
return transformBaseBlockNBT(transformed, block.getNbt(), transform);
596613
}
597614
return transformed.toBaseBlock();
598615
}
599616

600617
protected final BlockStateHolder transformInverse(BlockStateHolder block) {
601618
BlockState transformed = transformInverse(block.toImmutableState());
602-
if (block.hasNbtData()) {
603-
return transformBaseBlockNBT(transformed, block.getNbtData(), transformInverse);
619+
if (block.getNbt() != null) {
620+
return transformBaseBlockNBT(transformed, block.getNbt(), transformInverse);
604621
}
605622
return transformed;
606623
}

0 commit comments

Comments
 (0)