Advanced Arm Applications
- Mechanical Arms remember their targets when placed by Schematicannon (for real this time) - Mechanical Arms will now rotate/mirror their targets when rotated/mirrored in a schematic or contraption
This commit is contained in:
parent
2300e0e58a
commit
f3a521121d
7 changed files with 104 additions and 16 deletions
|
@ -1057,6 +1057,8 @@ public abstract class Contraption {
|
|||
mountedStorage.addStorageToWorld(tileEntity);
|
||||
}
|
||||
}
|
||||
|
||||
transform.apply(tileEntity);
|
||||
}
|
||||
}
|
||||
for (BlockInfo block : blocks.values()) {
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
package com.simibubi.create.content.contraptions.components.structureMovement;
|
||||
|
||||
public interface ITransformableTE {
|
||||
|
||||
void transform(StructureTransform transform);
|
||||
|
||||
}
|
|
@ -27,9 +27,11 @@ import net.minecraft.state.properties.BellAttachment;
|
|||
import net.minecraft.state.properties.BlockStateProperties;
|
||||
import net.minecraft.state.properties.Half;
|
||||
import net.minecraft.state.properties.SlabType;
|
||||
import net.minecraft.tileentity.TileEntity;
|
||||
import net.minecraft.util.Direction;
|
||||
import net.minecraft.util.Direction.Axis;
|
||||
import net.minecraft.util.Direction.AxisDirection;
|
||||
import net.minecraft.util.Mirror;
|
||||
import net.minecraft.util.Rotation;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.math.vector.Vector3d;
|
||||
|
@ -41,27 +43,33 @@ public class StructureTransform {
|
|||
int angle;
|
||||
Axis rotationAxis;
|
||||
BlockPos offset;
|
||||
Mirror mirror;
|
||||
|
||||
private StructureTransform(BlockPos offset, int angle, Axis axis, Rotation rotation) {
|
||||
private StructureTransform(BlockPos offset, int angle, Axis axis, Rotation rotation, Mirror mirror) {
|
||||
this.offset = offset;
|
||||
this.angle = angle;
|
||||
rotationAxis = axis;
|
||||
this.rotation = rotation;
|
||||
this.mirror = mirror;
|
||||
}
|
||||
|
||||
public StructureTransform(BlockPos offset, Axis axis, Rotation rotation, Mirror mirror) {
|
||||
this(offset, rotation == Rotation.NONE ? 0 : (4 - rotation.ordinal())*90, axis, rotation, mirror);
|
||||
}
|
||||
|
||||
public StructureTransform(BlockPos offset, float xRotation, float yRotation, float zRotation) {
|
||||
this.offset = offset;
|
||||
if (xRotation != 0) {
|
||||
rotationAxis = Axis.X;
|
||||
angle = (int) (Math.round(xRotation / 90) * 90);
|
||||
angle = Math.round(xRotation / 90) * 90;
|
||||
}
|
||||
if (yRotation != 0) {
|
||||
rotationAxis = Axis.Y;
|
||||
angle = (int) (Math.round(yRotation / 90) * 90);
|
||||
angle = Math.round(yRotation / 90) * 90;
|
||||
}
|
||||
if (zRotation != 0) {
|
||||
rotationAxis = Axis.Z;
|
||||
angle = (int) (Math.round(zRotation / 90) * 90);
|
||||
angle = Math.round(zRotation / 90) * 90;
|
||||
}
|
||||
|
||||
angle %= 360;
|
||||
|
@ -76,22 +84,33 @@ public class StructureTransform {
|
|||
if (angle == 180)
|
||||
this.rotation = Rotation.CLOCKWISE_180;
|
||||
|
||||
mirror = Mirror.NONE;
|
||||
}
|
||||
|
||||
public Vector3d apply(Vector3d localVec) {
|
||||
public Vector3d applyWithoutOffset(Vector3d localVec) {
|
||||
Vector3d vec = localVec;
|
||||
if (mirror != null)
|
||||
vec = VecHelper.mirrorCentered(vec, mirror);
|
||||
if (rotationAxis != null)
|
||||
vec = VecHelper.rotateCentered(vec, angle, rotationAxis);
|
||||
vec = vec.add(Vector3d.of(offset));
|
||||
return vec;
|
||||
}
|
||||
|
||||
public Vector3d apply(Vector3d localVec) {
|
||||
return applyWithoutOffset(localVec).add(Vector3d.of(offset));
|
||||
}
|
||||
|
||||
public BlockPos applyWithoutOffset(BlockPos localPos) {
|
||||
return new BlockPos(applyWithoutOffset(VecHelper.getCenterOf(localPos)));
|
||||
}
|
||||
|
||||
public BlockPos apply(BlockPos localPos) {
|
||||
Vector3d vec = VecHelper.getCenterOf(localPos);
|
||||
if (rotationAxis != null)
|
||||
vec = VecHelper.rotateCentered(vec, angle, rotationAxis);
|
||||
localPos = new BlockPos(vec);
|
||||
return localPos.add(offset);
|
||||
return applyWithoutOffset(localPos).add(offset);
|
||||
}
|
||||
|
||||
public void apply(TileEntity te) {
|
||||
if (te instanceof ITransformableTE)
|
||||
((ITransformableTE) te).transform(this);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -100,6 +119,9 @@ public class StructureTransform {
|
|||
* horizontal axes
|
||||
*/
|
||||
public BlockState apply(BlockState state) {
|
||||
if (mirror != null)
|
||||
state = state.mirror(mirror);
|
||||
|
||||
Block block = state.getBlock();
|
||||
|
||||
if (rotationAxis == Axis.Y) {
|
||||
|
@ -299,6 +321,8 @@ public class StructureTransform {
|
|||
}
|
||||
|
||||
public Direction transformFacing(Direction facing) {
|
||||
if (mirror != null)
|
||||
facing = mirror.mirror(facing);
|
||||
for (int i = 0; i < rotation.ordinal(); i++)
|
||||
facing = DirectionHelper.rotateAround(facing, rotationAxis);
|
||||
return facing;
|
||||
|
@ -335,8 +359,10 @@ public class StructureTransform {
|
|||
int readAngle = buffer.readInt();
|
||||
int axisIndex = buffer.readVarInt();
|
||||
int rotationIndex = buffer.readVarInt();
|
||||
int mirrorIndex = buffer.readVarInt();
|
||||
return new StructureTransform(readBlockPos, readAngle, axisIndex == -1 ? null : Axis.values()[axisIndex],
|
||||
rotationIndex == -1 ? null : Rotation.values()[rotationIndex]);
|
||||
rotationIndex == -1 ? null : Rotation.values()[rotationIndex],
|
||||
mirrorIndex == -1 ? null : Mirror.values()[mirrorIndex]);
|
||||
}
|
||||
|
||||
public void writeToBuffer(PacketBuffer buffer) {
|
||||
|
@ -344,6 +370,7 @@ public class StructureTransform {
|
|||
buffer.writeInt(angle);
|
||||
buffer.writeVarInt(rotationAxis == null ? -1 : rotationAxis.ordinal());
|
||||
buffer.writeVarInt(rotation == null ? -1 : rotation.ordinal());
|
||||
buffer.writeVarInt(mirror == null ? - 1 : mirror.ordinal());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -17,6 +17,7 @@ import com.simibubi.create.content.contraptions.components.crafter.MechanicalCra
|
|||
import com.simibubi.create.content.contraptions.components.crafter.MechanicalCrafterTileEntity;
|
||||
import com.simibubi.create.content.contraptions.components.deployer.DeployerBlock;
|
||||
import com.simibubi.create.content.contraptions.components.saw.SawBlock;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.StructureTransform;
|
||||
import com.simibubi.create.content.contraptions.processing.burner.BlazeBurnerBlock;
|
||||
import com.simibubi.create.content.contraptions.relays.belt.BeltHelper;
|
||||
import com.simibubi.create.content.contraptions.relays.belt.BeltTileEntity;
|
||||
|
@ -218,6 +219,12 @@ public abstract class ArmInteractionPoint {
|
|||
return interactionPoint;
|
||||
}
|
||||
|
||||
protected static void transformPos(StructureTransform transform, CompoundNBT nbt) {
|
||||
BlockPos pos = NBTUtil.readBlockPos(nbt.getCompound("Pos"));
|
||||
pos = transform.applyWithoutOffset(pos);
|
||||
nbt.put("Pos", NBTUtil.writeBlockPos(pos));
|
||||
}
|
||||
|
||||
public static abstract class TopFaceArmInteractionPoint extends ArmInteractionPoint {
|
||||
|
||||
@Override
|
||||
|
|
|
@ -7,6 +7,8 @@ import javax.annotation.Nullable;
|
|||
|
||||
import com.simibubi.create.Create;
|
||||
import com.simibubi.create.content.contraptions.base.KineticTileEntity;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.ITransformableTE;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.StructureTransform;
|
||||
import com.simibubi.create.content.logistics.block.mechanicalArm.ArmInteractionPoint.Jukebox;
|
||||
import com.simibubi.create.content.logistics.block.mechanicalArm.ArmInteractionPoint.Mode;
|
||||
import com.simibubi.create.foundation.advancement.AllTriggers;
|
||||
|
@ -41,7 +43,7 @@ import net.minecraftforge.api.distmarker.Dist;
|
|||
import net.minecraftforge.api.distmarker.OnlyIn;
|
||||
import net.minecraftforge.common.util.Constants.NBT;
|
||||
|
||||
public class ArmTileEntity extends KineticTileEntity {
|
||||
public class ArmTileEntity extends KineticTileEntity implements ITransformableTE {
|
||||
|
||||
// Server
|
||||
List<ArmInteractionPoint> inputs;
|
||||
|
@ -384,6 +386,19 @@ public class ArmTileEntity extends KineticTileEntity {
|
|||
searchForItem();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void transform(StructureTransform transform) {
|
||||
if (interactionPointTag == null)
|
||||
return;
|
||||
|
||||
for (INBT inbt : interactionPointTag) {
|
||||
ArmInteractionPoint.transformPos(transform, (CompoundNBT) inbt);
|
||||
}
|
||||
|
||||
sendData();
|
||||
markDirty();
|
||||
}
|
||||
|
||||
protected void initInteractionPoints() {
|
||||
if (!updateInteractionPoints || interactionPointTag == null)
|
||||
return;
|
||||
|
|
|
@ -6,6 +6,7 @@ import java.util.stream.Collectors;
|
|||
|
||||
import com.simibubi.create.AllBlocks;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.BlockMovementChecks;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.StructureTransform;
|
||||
import com.simibubi.create.content.schematics.item.SchematicItem;
|
||||
import com.simibubi.create.foundation.utility.BlockHelper;
|
||||
|
||||
|
@ -81,6 +82,12 @@ public class SchematicPrinter {
|
|||
blockReader = new SchematicWorld(schematicAnchor, originalWorld);
|
||||
activeTemplate.place(blockReader, schematicAnchor, settings, blockReader.getRandom());
|
||||
|
||||
StructureTransform transform = new StructureTransform(settings.getCenterOffset(), Direction.Axis.Y,
|
||||
settings.getRotation(), settings.getMirror());
|
||||
for (TileEntity te : blockReader.tileEntities.values()) {
|
||||
transform.apply(te);
|
||||
}
|
||||
|
||||
printingEntityIndex = -1;
|
||||
printStage = PrintStage.BLOCKS;
|
||||
deferredBlocks.clear();
|
||||
|
@ -292,7 +299,8 @@ public class SchematicPrinter {
|
|||
}
|
||||
|
||||
public static boolean shouldDeferBlock(BlockState state) {
|
||||
return state.getBlock().is(AllBlocks.GANTRY_CARRIAGE.get()) || BlockMovementChecks.isBrittle(state);
|
||||
return AllBlocks.GANTRY_CARRIAGE.has(state) || AllBlocks.MECHANICAL_ARM.has(state)
|
||||
|| BlockMovementChecks.isBrittle(state);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -12,6 +12,7 @@ import net.minecraft.nbt.DoubleNBT;
|
|||
import net.minecraft.nbt.ListNBT;
|
||||
import net.minecraft.util.Direction;
|
||||
import net.minecraft.util.Direction.Axis;
|
||||
import net.minecraft.util.Mirror;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.math.MathHelper;
|
||||
import net.minecraft.util.math.vector.Quaternion;
|
||||
|
@ -34,8 +35,7 @@ public class VecHelper {
|
|||
|
||||
public static Vector3d rotateCentered(Vector3d vec, double deg, Axis axis) {
|
||||
Vector3d shift = getCenterOf(BlockPos.ZERO);
|
||||
return VecHelper.rotate(vec.subtract(shift), deg, axis)
|
||||
.add(shift);
|
||||
return VecHelper.rotate(vec.subtract(shift), deg, axis).add(shift);
|
||||
}
|
||||
|
||||
public static Vector3d rotate(Vector3d vec, double deg, Axis axis) {
|
||||
|
@ -60,6 +60,28 @@ public class VecHelper {
|
|||
return vec;
|
||||
}
|
||||
|
||||
public static Vector3d mirrorCentered(Vector3d vec, Mirror mirror) {
|
||||
Vector3d shift = getCenterOf(BlockPos.ZERO);
|
||||
return VecHelper.mirror(vec.subtract(shift), mirror).add(shift);
|
||||
}
|
||||
|
||||
public static Vector3d mirror(Vector3d vec, Mirror mirror) {
|
||||
if (mirror == null || mirror == Mirror.NONE)
|
||||
return vec;
|
||||
if (vec == Vector3d.ZERO)
|
||||
return vec;
|
||||
|
||||
double x = vec.x;
|
||||
double y = vec.y;
|
||||
double z = vec.z;
|
||||
|
||||
if (mirror == Mirror.LEFT_RIGHT)
|
||||
return new Vector3d(x, y, -z);
|
||||
if (mirror == Mirror.FRONT_BACK)
|
||||
return new Vector3d(-x, y, z);
|
||||
return vec;
|
||||
}
|
||||
|
||||
public static Vector3d lookAt(Vector3d vec, Vector3d fwd) {
|
||||
fwd = fwd.normalize();
|
||||
Vector3d up = new Vector3d(0,1,0);
|
||||
|
|
Loading…
Reference in a new issue