Rise of the Jank
- address some bezier track z fighting - portable storage interfaces now stay connected until a contraption departs - seats can now collect entities when collided with on a contraption - clicking on seats now tries to mount any leashed mobs first - fixed seated entities not staying on seats on disassembly. this probably also fixed issues with sub-contraptions (oops) - fixed portable storage interface not working on train contraptions
This commit is contained in:
parent
66b6304fd3
commit
a6e86520f5
19 changed files with 247 additions and 124 deletions
|
@ -1,5 +1,6 @@
|
|||
package com.simibubi.create;
|
||||
|
||||
import static com.simibubi.create.AllInteractionBehaviours.addInteractionBehaviour;
|
||||
import static com.simibubi.create.AllMovementBehaviours.addMovementBehaviour;
|
||||
import static com.simibubi.create.AllTags.axeOnly;
|
||||
import static com.simibubi.create.AllTags.axeOrPickaxe;
|
||||
|
@ -26,6 +27,7 @@ import com.simibubi.create.content.contraptions.components.actors.PortableStorag
|
|||
import com.simibubi.create.content.contraptions.components.actors.PortableStorageInterfaceMovement;
|
||||
import com.simibubi.create.content.contraptions.components.actors.SawMovementBehaviour;
|
||||
import com.simibubi.create.content.contraptions.components.actors.SeatBlock;
|
||||
import com.simibubi.create.content.contraptions.components.actors.SeatInteractionBehaviour;
|
||||
import com.simibubi.create.content.contraptions.components.actors.SeatMovementBehaviour;
|
||||
import com.simibubi.create.content.contraptions.components.clock.CuckooClockBlock;
|
||||
import com.simibubi.create.content.contraptions.components.crafter.CrafterCTBehaviour;
|
||||
|
@ -36,6 +38,7 @@ import com.simibubi.create.content.contraptions.components.crusher.CrushingWheel
|
|||
import com.simibubi.create.content.contraptions.components.crusher.CrushingWheelControllerBlock;
|
||||
import com.simibubi.create.content.contraptions.components.deployer.DeployerBlock;
|
||||
import com.simibubi.create.content.contraptions.components.deployer.DeployerMovementBehaviour;
|
||||
import com.simibubi.create.content.contraptions.components.deployer.DeployerMovingInteraction;
|
||||
import com.simibubi.create.content.contraptions.components.fan.EncasedFanBlock;
|
||||
import com.simibubi.create.content.contraptions.components.fan.NozzleBlock;
|
||||
import com.simibubi.create.content.contraptions.components.flywheel.FlywheelBlock;
|
||||
|
@ -59,6 +62,7 @@ import com.simibubi.create.content.contraptions.components.structureMovement.cha
|
|||
import com.simibubi.create.content.contraptions.components.structureMovement.chassis.StickerBlock;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.gantry.GantryCarriageBlock;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.controls.ControlsBlock;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.controls.ControlsInteractionBehaviour;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.controls.ControlsMovementBehaviour;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.mounted.CartAssemblerBlock;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.mounted.CartAssemblerBlock.MinecartAnchorBlock;
|
||||
|
@ -1036,6 +1040,7 @@ public class AllBlocks {
|
|||
.blockstate(BlockStateGen.directionalAxisBlockProvider())
|
||||
.transform(BlockStressDefaults.setImpact(4.0))
|
||||
.onRegister(addMovementBehaviour(new DeployerMovementBehaviour()))
|
||||
.onRegister(addInteractionBehaviour(new DeployerMovingInteraction()))
|
||||
.item(AssemblyOperatorBlockItem::new)
|
||||
.transform(customItemModel())
|
||||
.register();
|
||||
|
@ -1083,10 +1088,12 @@ public class AllBlocks {
|
|||
public static final DyedBlockList<SeatBlock> SEATS = new DyedBlockList<>(colour -> {
|
||||
String colourName = colour.getSerializedName();
|
||||
SeatMovementBehaviour movementBehaviour = new SeatMovementBehaviour();
|
||||
SeatInteractionBehaviour interactionBehaviour = new SeatInteractionBehaviour();
|
||||
return REGISTRATE.block(colourName + "_seat", p -> new SeatBlock(p, colour, colour == DyeColor.RED))
|
||||
.initialProperties(SharedProperties::wooden)
|
||||
.transform(axeOnly())
|
||||
.onRegister(addMovementBehaviour(movementBehaviour))
|
||||
.onRegister(addInteractionBehaviour(interactionBehaviour))
|
||||
.blockstate((c, p) -> {
|
||||
p.simpleBlock(c.get(), p.models()
|
||||
.withExistingParent(colourName + "_seat", p.modLoc("block/seat"))
|
||||
|
@ -1292,6 +1299,7 @@ public class AllBlocks {
|
|||
.blockstate((c, p) -> p.horizontalBlock(c.get(),
|
||||
s -> AssetLookup.partialBaseModel(c, p, s.getValue(ControlsBlock.OPEN) ? "open" : "closed")))
|
||||
.onRegister(addMovementBehaviour(new ControlsMovementBehaviour()))
|
||||
.onRegister(addInteractionBehaviour(new ControlsInteractionBehaviour()))
|
||||
.item()
|
||||
.transform(customItemModel())
|
||||
.register();
|
||||
|
|
|
@ -6,12 +6,11 @@ import java.util.function.Supplier;
|
|||
import javax.annotation.Nullable;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import com.simibubi.create.content.contraptions.components.deployer.DeployerMovingInteraction;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.MovingInteractionBehaviour;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.DoorMovingInteraction;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.LeverMovingInteraction;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.TrapdoorMovingInteraction;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.controls.ControlsInteractionBehaviour;
|
||||
import com.tterrag.registrate.util.nullness.NonNullConsumer;
|
||||
|
||||
import net.minecraft.resources.ResourceLocation;
|
||||
import net.minecraft.world.level.block.Block;
|
||||
|
@ -31,6 +30,11 @@ public class AllInteractionBehaviours {
|
|||
addInteractionBehaviour(block.getRegistryName(), behaviour);
|
||||
}
|
||||
|
||||
public static <B extends Block> NonNullConsumer<? super B> addInteractionBehaviour(
|
||||
MovingInteractionBehaviour movementBehaviour) {
|
||||
return b -> addInteractionBehaviour(b.getRegistryName(), () -> movementBehaviour);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static MovingInteractionBehaviour of(ResourceLocation loc) {
|
||||
return (INTERACT_BEHAVIOURS.get(loc) == null) ? null
|
||||
|
@ -49,11 +53,9 @@ public class AllInteractionBehaviours {
|
|||
|
||||
static void register() {
|
||||
addInteractionBehaviour(Blocks.LEVER.getRegistryName(), LeverMovingInteraction::new);
|
||||
addInteractionBehaviour(AllBlocks.DEPLOYER.getId(), DeployerMovingInteraction::new);
|
||||
addInteractionBehaviour(AllBlocks.CONTROLS.getId(), ControlsInteractionBehaviour::new);
|
||||
|
||||
// TODO: Scan registry for instanceof (-> modded door support)
|
||||
|
||||
|
||||
for (Block trapdoor : ImmutableList.of(Blocks.ACACIA_TRAPDOOR, Blocks.OAK_TRAPDOOR, Blocks.DARK_OAK_TRAPDOOR,
|
||||
Blocks.SPRUCE_TRAPDOOR, Blocks.JUNGLE_TRAPDOOR, Blocks.BIRCH_TRAPDOOR, Blocks.WARPED_TRAPDOOR,
|
||||
Blocks.CRIMSON_TRAPDOOR)) {
|
||||
|
|
|
@ -52,7 +52,7 @@ public class AllMovementBehaviours {
|
|||
MovementBehaviour movementBehaviour) {
|
||||
return b -> addMovementBehaviour(b.getRegistryName(), movementBehaviour);
|
||||
}
|
||||
|
||||
|
||||
static void register() {
|
||||
addMovementBehaviour(Blocks.BELL, new BellMovementBehaviour());
|
||||
addMovementBehaviour(Blocks.CAMPFIRE, new CampfireMovementBehaviour());
|
||||
|
|
|
@ -16,7 +16,7 @@ import net.minecraftforge.items.ItemStackHandler;
|
|||
public class PortableItemInterfaceTileEntity extends PortableStorageInterfaceTileEntity {
|
||||
|
||||
protected LazyOptional<IItemHandlerModifiable> capability;
|
||||
|
||||
|
||||
public PortableItemInterfaceTileEntity(BlockEntityType<?> type, BlockPos pos, BlockState state) {
|
||||
super(type, pos, state);
|
||||
capability = createEmptyHandler();
|
||||
|
|
|
@ -9,6 +9,7 @@ import com.simibubi.create.foundation.block.WrenchableDirectionalBlock;
|
|||
|
||||
import net.minecraft.MethodsReturnNonnullByDefault;
|
||||
import net.minecraft.core.BlockPos;
|
||||
import net.minecraft.core.Direction;
|
||||
import net.minecraft.world.item.context.BlockPlaceContext;
|
||||
import net.minecraft.world.level.BlockGetter;
|
||||
import net.minecraft.world.level.Level;
|
||||
|
@ -46,8 +47,11 @@ public class PortableStorageInterfaceBlock extends WrenchableDirectionalBlock
|
|||
|
||||
@Override
|
||||
public BlockState getStateForPlacement(BlockPlaceContext context) {
|
||||
return defaultBlockState().setValue(FACING, context.getNearestLookingDirection()
|
||||
.getOpposite());
|
||||
Direction direction = context.getNearestLookingDirection();
|
||||
if (context.getPlayer() != null && context.getPlayer()
|
||||
.isSteppingCarefully())
|
||||
direction = direction.getOpposite();
|
||||
return defaultBlockState().setValue(FACING, direction.getOpposite());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -11,7 +11,10 @@ import com.simibubi.create.content.contraptions.components.structureMovement.Mov
|
|||
import com.simibubi.create.content.contraptions.components.structureMovement.MovementContext;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.render.ContraptionMatrices;
|
||||
import com.simibubi.create.content.logistics.trains.entity.CarriageContraption;
|
||||
import com.simibubi.create.foundation.utility.VecHelper;
|
||||
import com.simibubi.create.foundation.utility.animation.LerpedFloat;
|
||||
import com.simibubi.create.foundation.utility.animation.LerpedFloat.Chaser;
|
||||
|
||||
import net.minecraft.client.renderer.MultiBufferSource;
|
||||
import net.minecraft.core.BlockPos;
|
||||
|
@ -32,7 +35,8 @@ public class PortableStorageInterfaceMovement extends MovementBehaviour {
|
|||
@Override
|
||||
public Vec3 getActiveAreaOffset(MovementContext context) {
|
||||
return Vec3.atLowerCornerOf(context.state.getValue(PortableStorageInterfaceBlock.FACING)
|
||||
.getNormal()).scale(1.85f);
|
||||
.getNormal())
|
||||
.scale(1.85f);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -42,7 +46,8 @@ public class PortableStorageInterfaceMovement extends MovementBehaviour {
|
|||
|
||||
@Nullable
|
||||
@Override
|
||||
public ActorInstance createInstance(MaterialManager materialManager, VirtualRenderWorld simulationWorld, MovementContext context) {
|
||||
public ActorInstance createInstance(MaterialManager materialManager, VirtualRenderWorld simulationWorld,
|
||||
MovementContext context) {
|
||||
return new PSIActorInstance(materialManager, simulationWorld, context);
|
||||
}
|
||||
|
||||
|
@ -56,9 +61,56 @@ public class PortableStorageInterfaceMovement extends MovementBehaviour {
|
|||
|
||||
@Override
|
||||
public void visitNewPosition(MovementContext context, BlockPos pos) {
|
||||
context.data.remove(_workingPos_);
|
||||
if (findInterface(context, pos))
|
||||
if (!findInterface(context, pos))
|
||||
context.data.remove(_workingPos_);
|
||||
// if (findInterface(context, pos))
|
||||
// context.stall = true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void tick(MovementContext context) {
|
||||
if (context.world.isClientSide) {
|
||||
getAnimation(context).tickChaser();
|
||||
BlockPos pos = new BlockPos(context.position);
|
||||
findInterface(context, pos);
|
||||
if (!context.data.contains(_clientPrevPos_)
|
||||
|| !NbtUtils.readBlockPos(context.data.getCompound(_clientPrevPos_))
|
||||
.equals(pos)) {
|
||||
if (!findInterface(context, pos))
|
||||
reset(context);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (!context.data.contains(_workingPos_))
|
||||
return;
|
||||
|
||||
BlockPos pos = NbtUtils.readBlockPos(context.data.getCompound(_workingPos_));
|
||||
Vec3 target = VecHelper.getCenterOf(pos);
|
||||
|
||||
if (!context.stall
|
||||
&& context.position.closerThan(target, target.distanceTo(context.position.add(context.motion))))
|
||||
context.stall = true;
|
||||
|
||||
Optional<Direction> currentFacingIfValid = getCurrentFacingIfValid(context);
|
||||
if (!currentFacingIfValid.isPresent())
|
||||
return;
|
||||
|
||||
PortableStorageInterfaceTileEntity stationaryInterface =
|
||||
getStationaryInterfaceAt(context.world, pos, context.state, currentFacingIfValid.get());
|
||||
if (stationaryInterface == null) {
|
||||
reset(context);
|
||||
return;
|
||||
}
|
||||
|
||||
if (stationaryInterface.connectedEntity == null)
|
||||
stationaryInterface.startTransferringTo(context.contraption, stationaryInterface.distance);
|
||||
|
||||
boolean timerBelow = stationaryInterface.transferTimer <= PortableStorageInterfaceTileEntity.ANIMATION;
|
||||
stationaryInterface.keepAlive = 2;
|
||||
if (context.stall && timerBelow) {
|
||||
context.stall = false;
|
||||
}
|
||||
}
|
||||
|
||||
protected boolean findInterface(MovementContext context, BlockPos pos) {
|
||||
|
@ -71,9 +123,9 @@ public class PortableStorageInterfaceMovement extends MovementBehaviour {
|
|||
findStationaryInterface(context.world, pos, context.state, currentFacing);
|
||||
if (psi == null)
|
||||
return false;
|
||||
|
||||
if ((psi.isTransferring() || psi.isPowered()) && !context.world.isClientSide)
|
||||
return false;
|
||||
|
||||
context.data.put(_workingPos_, NbtUtils.writeBlockPos(psi.getBlockPos()));
|
||||
if (!context.world.isClientSide) {
|
||||
Vec3 diff = VecHelper.getCenterOf(psi.getBlockPos())
|
||||
|
@ -83,51 +135,24 @@ public class PortableStorageInterfaceMovement extends MovementBehaviour {
|
|||
psi.startTransferringTo(context.contraption, distance);
|
||||
} else {
|
||||
context.data.put(_clientPrevPos_, NbtUtils.writeBlockPos(pos));
|
||||
if (context.contraption instanceof CarriageContraption || context.contraption.entity.isStalled()
|
||||
|| context.motion.lengthSqr() == 0)
|
||||
getAnimation(context).chase(psi.getConnectionDistance() / 2, 0.25f, Chaser.LINEAR);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void tick(MovementContext context) {
|
||||
if (context.world.isClientSide) {
|
||||
boolean stalled = context.contraption.stalled;
|
||||
if (stalled && !context.data.contains(_workingPos_)) {
|
||||
BlockPos pos = new BlockPos(context.position);
|
||||
if (!context.data.contains(_clientPrevPos_)
|
||||
|| !NbtUtils.readBlockPos(context.data.getCompound(_clientPrevPos_))
|
||||
.equals(pos))
|
||||
findInterface(context, pos);
|
||||
}
|
||||
if (!stalled)
|
||||
reset(context);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!context.data.contains(_workingPos_))
|
||||
return;
|
||||
|
||||
BlockPos pos = NbtUtils.readBlockPos(context.data.getCompound(_workingPos_));
|
||||
Optional<Direction> currentFacingIfValid = getCurrentFacingIfValid(context);
|
||||
if (!currentFacingIfValid.isPresent())
|
||||
return;
|
||||
|
||||
PortableStorageInterfaceTileEntity stationaryInterface =
|
||||
getStationaryInterfaceAt(context.world, pos, context.state, currentFacingIfValid.get());
|
||||
if (stationaryInterface == null || !stationaryInterface.isTransferring()) {
|
||||
reset(context);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void stopMoving(MovementContext context) {
|
||||
reset(context);
|
||||
// reset(context);
|
||||
}
|
||||
|
||||
public void reset(MovementContext context) {
|
||||
context.data.remove(_clientPrevPos_);
|
||||
context.data.remove(_workingPos_);
|
||||
context.stall = false;
|
||||
getAnimation(context).chase(0, 0.25f, Chaser.LINEAR);
|
||||
}
|
||||
|
||||
private PortableStorageInterfaceTileEntity findStationaryInterface(Level world, BlockPos pos, BlockState state,
|
||||
|
@ -165,4 +190,13 @@ public class PortableStorageInterfaceMovement extends MovementBehaviour {
|
|||
return Optional.of(facingFromVector);
|
||||
}
|
||||
|
||||
public static LerpedFloat getAnimation(MovementContext context) {
|
||||
if (!(context.temporaryData instanceof LerpedFloat lf)) {
|
||||
LerpedFloat nlf = LerpedFloat.linear();
|
||||
context.temporaryData = nlf;
|
||||
return nlf;
|
||||
}
|
||||
return lf;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,6 +16,7 @@ import com.simibubi.create.foundation.render.SuperByteBuffer;
|
|||
import com.simibubi.create.foundation.tileEntity.renderer.SafeTileEntityRenderer;
|
||||
import com.simibubi.create.foundation.utility.AngleHelper;
|
||||
import com.simibubi.create.foundation.utility.AnimationTickHolder;
|
||||
import com.simibubi.create.foundation.utility.animation.LerpedFloat;
|
||||
|
||||
import net.minecraft.client.renderer.MultiBufferSource;
|
||||
import net.minecraft.client.renderer.RenderType;
|
||||
|
@ -28,8 +29,7 @@ import net.minecraft.world.level.block.state.BlockState;
|
|||
|
||||
public class PortableStorageInterfaceRenderer extends SafeTileEntityRenderer<PortableStorageInterfaceTileEntity> {
|
||||
|
||||
public PortableStorageInterfaceRenderer(BlockEntityRendererProvider.Context context) {
|
||||
}
|
||||
public PortableStorageInterfaceRenderer(BlockEntityRendererProvider.Context context) {}
|
||||
|
||||
@Override
|
||||
protected void renderSafe(PortableStorageInterfaceTileEntity te, float partialTicks, PoseStack ms,
|
||||
|
@ -44,24 +44,20 @@ public class PortableStorageInterfaceRenderer extends SafeTileEntityRenderer<Por
|
|||
public static void renderInContraption(MovementContext context, VirtualRenderWorld renderWorld,
|
||||
ContraptionMatrices matrices, MultiBufferSource buffer) {
|
||||
BlockState blockState = context.state;
|
||||
PortableStorageInterfaceTileEntity te = getTargetPSI(context);
|
||||
VertexConsumer vb = buffer.getBuffer(RenderType.solid());
|
||||
float renderPartialTicks = AnimationTickHolder.getPartialTicks();
|
||||
|
||||
float progress = 0;
|
||||
boolean lit = false;
|
||||
if (te != null) {
|
||||
progress = te.getExtensionDistance(renderPartialTicks);
|
||||
lit = te.isConnected();
|
||||
}
|
||||
|
||||
render(blockState, lit, progress, matrices.getModel(), sbb -> sbb.light(matrices.getWorld(),
|
||||
ContraptionRenderDispatcher.getContraptionWorldLight(context, renderWorld))
|
||||
.renderInto(matrices.getViewProjection(), vb));
|
||||
LerpedFloat animation = PortableStorageInterfaceMovement.getAnimation(context);
|
||||
float progress = animation.getValue(renderPartialTicks);
|
||||
boolean lit = animation.settled();
|
||||
render(blockState, lit, progress, matrices.getModel(),
|
||||
sbb -> sbb
|
||||
.light(matrices.getWorld(), ContraptionRenderDispatcher.getContraptionWorldLight(context, renderWorld))
|
||||
.renderInto(matrices.getViewProjection(), vb));
|
||||
}
|
||||
|
||||
private static void render(BlockState blockState, boolean lit, float progress,
|
||||
PoseStack local, Consumer<SuperByteBuffer> drawCallback) {
|
||||
private static void render(BlockState blockState, boolean lit, float progress, PoseStack local,
|
||||
Consumer<SuperByteBuffer> drawCallback) {
|
||||
SuperByteBuffer middle = CachedBufferer.partial(getMiddleForState(blockState, lit), blockState);
|
||||
SuperByteBuffer top = CachedBufferer.partial(getTopForState(blockState), blockState);
|
||||
|
||||
|
@ -88,7 +84,7 @@ public class PortableStorageInterfaceRenderer extends SafeTileEntityRenderer<Por
|
|||
|
||||
static PortableStorageInterfaceTileEntity getTargetPSI(MovementContext context) {
|
||||
String _workingPos_ = PortableStorageInterfaceMovement._workingPos_;
|
||||
if (!context.contraption.stalled || !context.data.contains(_workingPos_))
|
||||
if (!context.data.contains(_workingPos_))
|
||||
return null;
|
||||
|
||||
BlockPos pos = NbtUtils.readBlockPos(context.data.getCompound(_workingPos_));
|
||||
|
|
|
@ -20,12 +20,15 @@ import net.minecraftforge.api.distmarker.OnlyIn;
|
|||
|
||||
public abstract class PortableStorageInterfaceTileEntity extends SmartTileEntity {
|
||||
|
||||
public static final int ANIMATION = 4;
|
||||
protected int transferTimer;
|
||||
protected float distance;
|
||||
protected LerpedFloat connectionAnimation;
|
||||
protected boolean powered;
|
||||
protected Entity connectedEntity;
|
||||
|
||||
public int keepAlive = 0;
|
||||
|
||||
public PortableStorageInterfaceTileEntity(BlockEntityType<?> type, BlockPos pos, BlockState state) {
|
||||
super(type, pos, state);
|
||||
transferTimer = 0;
|
||||
|
@ -57,11 +60,29 @@ public abstract class PortableStorageInterfaceTileEntity extends SmartTileEntity
|
|||
public void tick() {
|
||||
super.tick();
|
||||
boolean wasConnected = isConnected();
|
||||
int timeUnit = getTransferTimeout() / 2;
|
||||
int timeUnit = getTransferTimeout();
|
||||
int animation = ANIMATION;
|
||||
|
||||
if (transferTimer > 0 && (!isVirtual() || transferTimer != timeUnit)) {
|
||||
if (keepAlive > 0) {
|
||||
keepAlive--;
|
||||
if (keepAlive == 0 && !level.isClientSide) {
|
||||
stopTransferring();
|
||||
transferTimer = ANIMATION - 1;
|
||||
sendData();
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
transferTimer = Math.min(transferTimer, ANIMATION * 2 + getTransferTimeout());
|
||||
|
||||
boolean timerCanDecrement = transferTimer > ANIMATION || transferTimer > 0 && keepAlive == 0
|
||||
&& (isVirtual() || !level.isClientSide || transferTimer != ANIMATION);
|
||||
|
||||
if (timerCanDecrement && (!isVirtual() || transferTimer != timeUnit)) {
|
||||
transferTimer--;
|
||||
if (transferTimer == 0 || powered)
|
||||
if (transferTimer == ANIMATION - 1)
|
||||
sendData();
|
||||
if (transferTimer <= 0 || powered)
|
||||
stopTransferring();
|
||||
}
|
||||
|
||||
|
@ -72,10 +93,10 @@ public abstract class PortableStorageInterfaceTileEntity extends SmartTileEntity
|
|||
float progress = 0;
|
||||
if (isConnected)
|
||||
progress = 1;
|
||||
else if (transferTimer >= timeUnit * 3)
|
||||
progress = Mth.lerp((transferTimer - timeUnit * 3) / (float) timeUnit, 1, 0);
|
||||
else if (transferTimer < timeUnit)
|
||||
progress = Mth.lerp(transferTimer / (float) timeUnit, 0, 1);
|
||||
else if (transferTimer >= timeUnit + animation)
|
||||
progress = Mth.lerp((transferTimer - timeUnit - animation) / (float) animation, 1, 0);
|
||||
else if (transferTimer < animation)
|
||||
progress = Mth.lerp(transferTimer / (float) animation, 0, 1);
|
||||
connectionAnimation.setValue(progress);
|
||||
}
|
||||
|
||||
|
@ -125,16 +146,16 @@ public abstract class PortableStorageInterfaceTileEntity extends SmartTileEntity
|
|||
}
|
||||
|
||||
public boolean isTransferring() {
|
||||
return transferTimer != 0;
|
||||
return transferTimer > ANIMATION;
|
||||
}
|
||||
|
||||
boolean isConnected() {
|
||||
int timeUnit = getTransferTimeout() / 2;
|
||||
return transferTimer >= timeUnit && transferTimer <= timeUnit * 3;
|
||||
int timeUnit = getTransferTimeout();
|
||||
return transferTimer >= ANIMATION && transferTimer <= timeUnit + ANIMATION;
|
||||
}
|
||||
|
||||
float getExtensionDistance(float partialTicks) {
|
||||
return connectionAnimation.getValue(partialTicks) * distance / 2;
|
||||
return (float) (Math.pow(connectionAnimation.getValue(partialTicks), 2) * distance / 2);
|
||||
}
|
||||
|
||||
float getConnectionDistance() {
|
||||
|
@ -142,12 +163,12 @@ public abstract class PortableStorageInterfaceTileEntity extends SmartTileEntity
|
|||
}
|
||||
|
||||
public void startConnecting() {
|
||||
transferTimer = getTransferTimeout() * 2;
|
||||
transferTimer = getTransferTimeout() + ANIMATION * 2;
|
||||
}
|
||||
|
||||
public void onContentTransferred() {
|
||||
int timeUnit = getTransferTimeout() / 2;
|
||||
transferTimer = timeUnit * 3;
|
||||
int timeUnit = getTransferTimeout();
|
||||
transferTimer = timeUnit + ANIMATION;
|
||||
sendData();
|
||||
}
|
||||
|
||||
|
|
|
@ -5,6 +5,7 @@ import java.util.List;
|
|||
import javax.annotation.Nullable;
|
||||
import javax.annotation.ParametersAreNonnullByDefault;
|
||||
|
||||
import com.google.common.base.Optional;
|
||||
import com.simibubi.create.AllBlocks;
|
||||
import com.simibubi.create.AllShapes;
|
||||
import com.simibubi.create.foundation.utility.BlockHelper;
|
||||
|
@ -131,7 +132,7 @@ public class SeatBlock extends Block {
|
|||
|
||||
if (world.isClientSide)
|
||||
return InteractionResult.SUCCESS;
|
||||
sitDown(world, pos, player);
|
||||
sitDown(world, pos, getLeashed(world, player).or(player));
|
||||
return InteractionResult.SUCCESS;
|
||||
}
|
||||
|
||||
|
@ -140,6 +141,15 @@ public class SeatBlock extends Block {
|
|||
.isEmpty();
|
||||
}
|
||||
|
||||
public static Optional<Entity> getLeashed(Level level, Player player) {
|
||||
List<Entity> entities = player.level.getEntities((Entity) null, player.getBoundingBox()
|
||||
.inflate(10), e -> true);
|
||||
for (Entity e : entities)
|
||||
if (e instanceof Mob mob && mob.getLeashHolder() == player && SeatBlock.canBePickedUp(e))
|
||||
return Optional.of(mob);
|
||||
return Optional.absent();
|
||||
}
|
||||
|
||||
public static boolean canBePickedUp(Entity passenger) {
|
||||
return !(passenger instanceof Player) && (passenger instanceof LivingEntity);
|
||||
}
|
||||
|
|
|
@ -0,0 +1,32 @@
|
|||
package com.simibubi.create.content.contraptions.components.actors;
|
||||
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.AbstractContraptionEntity;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.Contraption;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.MovingInteractionBehaviour;
|
||||
|
||||
import net.minecraft.core.BlockPos;
|
||||
import net.minecraft.world.InteractionHand;
|
||||
import net.minecraft.world.entity.Entity;
|
||||
import net.minecraft.world.entity.player.Player;
|
||||
|
||||
public class SeatInteractionBehaviour extends MovingInteractionBehaviour {
|
||||
|
||||
@Override
|
||||
public boolean handlePlayerInteraction(Player player, InteractionHand activeHand, BlockPos localPos,
|
||||
AbstractContraptionEntity contraptionEntity) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleEntityCollision(Entity entity, BlockPos localPos, AbstractContraptionEntity contraptionEntity) {
|
||||
Contraption contraption = contraptionEntity.getContraption();
|
||||
int index = contraption.getSeats()
|
||||
.indexOf(localPos);
|
||||
if (index == -1)
|
||||
return;
|
||||
if (!SeatBlock.canBePickedUp(entity))
|
||||
return;
|
||||
contraptionEntity.addSittingPassenger(entity, index);
|
||||
}
|
||||
|
||||
}
|
|
@ -1,6 +1,5 @@
|
|||
package com.simibubi.create.content.contraptions.components.actors;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
|
||||
|
@ -14,7 +13,6 @@ import net.minecraft.world.entity.Entity;
|
|||
import net.minecraft.world.level.block.SlabBlock;
|
||||
import net.minecraft.world.level.block.state.BlockState;
|
||||
import net.minecraft.world.level.block.state.properties.SlabType;
|
||||
import net.minecraft.world.phys.AABB;
|
||||
import net.minecraft.world.phys.Vec3;
|
||||
|
||||
public class SeatMovementBehaviour extends MovementBehaviour {
|
||||
|
@ -30,7 +28,7 @@ public class SeatMovementBehaviour extends MovementBehaviour {
|
|||
@Override
|
||||
public void visitNewPosition(MovementContext context, BlockPos pos) {
|
||||
super.visitNewPosition(context, pos);
|
||||
|
||||
|
||||
AbstractContraptionEntity contraptionEntity = context.contraption.entity;
|
||||
if (contraptionEntity == null)
|
||||
return;
|
||||
|
@ -40,42 +38,34 @@ public class SeatMovementBehaviour extends MovementBehaviour {
|
|||
|
||||
Map<UUID, Integer> seatMapping = context.contraption.getSeatMapping();
|
||||
BlockState blockState = context.world.getBlockState(pos);
|
||||
boolean slab = blockState.getBlock() instanceof SlabBlock && blockState.getValue(SlabBlock.TYPE) == SlabType.BOTTOM;
|
||||
boolean slab =
|
||||
blockState.getBlock() instanceof SlabBlock && blockState.getValue(SlabBlock.TYPE) == SlabType.BOTTOM;
|
||||
boolean solid = blockState.canOcclude() || slab;
|
||||
|
||||
// Occupied
|
||||
if (seatMapping.containsValue(index)) {
|
||||
if (!solid)
|
||||
return;
|
||||
Entity toDismount = null;
|
||||
for (Map.Entry<UUID, Integer> entry : seatMapping.entrySet()) {
|
||||
if (entry.getValue() != index)
|
||||
if (!seatMapping.containsValue(index))
|
||||
return;
|
||||
if (!solid)
|
||||
return;
|
||||
Entity toDismount = null;
|
||||
for (Map.Entry<UUID, Integer> entry : seatMapping.entrySet()) {
|
||||
if (entry.getValue() != index)
|
||||
continue;
|
||||
for (Entity entity : contraptionEntity.getPassengers()) {
|
||||
if (!entry.getKey()
|
||||
.equals(entity.getUUID()))
|
||||
continue;
|
||||
for (Entity entity : contraptionEntity.getPassengers()) {
|
||||
if (!entry.getKey()
|
||||
.equals(entity.getUUID()))
|
||||
continue;
|
||||
toDismount = entity;
|
||||
}
|
||||
toDismount = entity;
|
||||
}
|
||||
if (toDismount != null) {
|
||||
toDismount.stopRiding();
|
||||
Vec3 position = VecHelper.getCenterOf(pos)
|
||||
.add(0, slab ? .5f : 1f, 0);
|
||||
toDismount.teleportTo(position.x, position.y, position.z);
|
||||
toDismount.getPersistentData()
|
||||
.remove("ContraptionDismountLocation");
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (solid)
|
||||
if (toDismount == null)
|
||||
return;
|
||||
|
||||
List<Entity> nearbyEntities = context.world.getEntitiesOfClass(Entity.class,
|
||||
new AABB(pos).deflate(1 / 16f), SeatBlock::canBePickedUp);
|
||||
if (!nearbyEntities.isEmpty())
|
||||
contraptionEntity.addSittingPassenger(nearbyEntities.get(0), index);
|
||||
toDismount.stopRiding();
|
||||
Vec3 position = VecHelper.getCenterOf(pos)
|
||||
.add(0, slab ? .5f : 1f, 0);
|
||||
toDismount.teleportTo(position.x, position.y, position.z);
|
||||
toDismount.getPersistentData()
|
||||
.remove("ContraptionDismountLocation");
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -17,6 +17,7 @@ import com.mojang.blaze3d.vertex.PoseStack;
|
|||
import com.simibubi.create.AllMovementBehaviours;
|
||||
import com.simibubi.create.AllSoundEvents;
|
||||
import com.simibubi.create.Create;
|
||||
import com.simibubi.create.content.contraptions.components.actors.SeatBlock;
|
||||
import com.simibubi.create.content.contraptions.components.actors.SeatEntity;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.glue.SuperGlueEntity;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.mounted.MountedContraption;
|
||||
|
@ -186,7 +187,7 @@ public abstract class AbstractContraptionEntity extends Entity implements IEntit
|
|||
.handlePlayerInteraction(player, interactionHand, localPos, this);
|
||||
if (player.isPassenger())
|
||||
return false;
|
||||
|
||||
|
||||
// Eject potential existing passenger
|
||||
Entity toDismount = null;
|
||||
for (Entry<UUID, Integer> entry : contraption.getSeatMapping()
|
||||
|
@ -212,7 +213,8 @@ public abstract class AbstractContraptionEntity extends Entity implements IEntit
|
|||
|
||||
if (level.isClientSide)
|
||||
return true;
|
||||
addSittingPassenger(player, indexOfSeat);
|
||||
addSittingPassenger(SeatBlock.getLeashed(level, player)
|
||||
.or(player), indexOfSeat);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -466,11 +468,9 @@ public abstract class AbstractContraptionEntity extends Entity implements IEntit
|
|||
AllPackets.channel.send(PacketDistributor.TRACKING_ENTITY.with(() -> this),
|
||||
new ContraptionDisassemblyPacket(this.getId(), transform));
|
||||
|
||||
discard();
|
||||
|
||||
contraption.addBlocksToWorld(level, transform);
|
||||
contraption.addPassengersToWorld(level, transform, getPassengers());
|
||||
|
||||
|
||||
for (Entity entity : getPassengers()) {
|
||||
if (!(entity instanceof OrientedContraptionEntity))
|
||||
continue;
|
||||
|
@ -482,6 +482,8 @@ public abstract class AbstractContraptionEntity extends Entity implements IEntit
|
|||
entity.setPos(transformed.getX(), transformed.getY(), transformed.getZ());
|
||||
((AbstractContraptionEntity) entity).disassemble();
|
||||
}
|
||||
|
||||
discard();
|
||||
|
||||
ejectPassengers();
|
||||
moveCollidedEntitiesOnDisassembly(transform);
|
||||
|
|
|
@ -348,7 +348,7 @@ public abstract class Contraption {
|
|||
}
|
||||
|
||||
// Bogeys tend to have sticky sides
|
||||
if (state.getBlock() instanceof IBogeyBlock bogey)
|
||||
if (state.getBlock()instanceof IBogeyBlock bogey)
|
||||
for (Direction d : bogey.getStickySurfaces(world, pos, state))
|
||||
if (!visited.contains(pos.relative(d)))
|
||||
frontier.add(pos.relative(d));
|
||||
|
@ -882,7 +882,7 @@ public abstract class Contraption {
|
|||
}
|
||||
|
||||
ListTag paletteNBT = new ListTag();
|
||||
for(int i = 0; i < palette.getSize(); ++i)
|
||||
for (int i = 0; i < palette.getSize(); ++i)
|
||||
paletteNBT.add(NbtUtils.writeBlockState(palette.values.byId(i)));
|
||||
|
||||
compound.put("Palette", paletteNBT);
|
||||
|
@ -1139,6 +1139,8 @@ public abstract class Contraption {
|
|||
if (getSeatMapping().isEmpty())
|
||||
continue;
|
||||
Integer seatIndex = getSeatMapping().get(seatedEntity.getUUID());
|
||||
if (seatIndex == null)
|
||||
continue;
|
||||
BlockPos seatPos = getSeats().get(seatIndex);
|
||||
seatPos = transform.apply(seatPos);
|
||||
if (!(world.getBlockState(seatPos)
|
||||
|
|
|
@ -235,6 +235,11 @@ public class ContraptionCollider {
|
|||
.containsKey(pos)) {
|
||||
BlockState blockState = contraption.getBlocks()
|
||||
.get(pos).state;
|
||||
|
||||
MovingInteractionBehaviour movingInteractionBehaviour = contraption.interactors.get(pos);
|
||||
if (movingInteractionBehaviour != null)
|
||||
movingInteractionBehaviour.handleEntityCollision(entity, pos, contraptionEntity);
|
||||
|
||||
bounce = BlockHelper.getBounceMultiplier(blockState.getBlock());
|
||||
slide = Math.max(0, blockState.getFriction(contraption.world, pos, entity) - .6f);
|
||||
}
|
||||
|
|
|
@ -216,7 +216,7 @@ public class ControlledContraptionEntity extends AbstractContraptionEntity {
|
|||
@Override
|
||||
protected void handleStallInformation(float x, float y, float z, float angle) {
|
||||
setPosRaw(x, y, z);
|
||||
this.angle = angle;
|
||||
this.angle = this.prevAngle = angle;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -6,6 +6,7 @@ import com.simibubi.create.content.contraptions.components.structureMovement.ren
|
|||
|
||||
import net.minecraft.core.BlockPos;
|
||||
import net.minecraft.world.InteractionHand;
|
||||
import net.minecraft.world.entity.Entity;
|
||||
import net.minecraft.world.entity.player.Player;
|
||||
import net.minecraft.world.level.levelgen.structure.templatesystem.StructureTemplate.StructureBlockInfo;
|
||||
import net.minecraftforge.api.distmarker.Dist;
|
||||
|
@ -16,15 +17,16 @@ public abstract class MovingInteractionBehaviour {
|
|||
|
||||
public MovingInteractionBehaviour() {}
|
||||
|
||||
protected void setContraptionActorData(AbstractContraptionEntity contraptionEntity, int index, StructureBlockInfo info,
|
||||
MovementContext ctx) {
|
||||
protected void setContraptionActorData(AbstractContraptionEntity contraptionEntity, int index,
|
||||
StructureBlockInfo info, MovementContext ctx) {
|
||||
contraptionEntity.contraption.actors.remove(index);
|
||||
contraptionEntity.contraption.actors.add(index, MutablePair.of(info, ctx));
|
||||
if (contraptionEntity.level.isClientSide)
|
||||
DistExecutor.unsafeRunWhenOn(Dist.CLIENT, () -> () -> invalidate(contraptionEntity.contraption));
|
||||
}
|
||||
|
||||
protected void setContraptionBlockData(AbstractContraptionEntity contraptionEntity, BlockPos pos, StructureBlockInfo info) {
|
||||
protected void setContraptionBlockData(AbstractContraptionEntity contraptionEntity, BlockPos pos,
|
||||
StructureBlockInfo info) {
|
||||
contraptionEntity.contraption.blocks.put(pos, info);
|
||||
if (contraptionEntity.level.isClientSide)
|
||||
DistExecutor.unsafeRunWhenOn(Dist.CLIENT, () -> () -> invalidate(contraptionEntity.contraption));
|
||||
|
@ -40,4 +42,6 @@ public abstract class MovingInteractionBehaviour {
|
|||
return true;
|
||||
}
|
||||
|
||||
public void handleEntityCollision(Entity entity, BlockPos localPos, AbstractContraptionEntity contraptionEntity) {}
|
||||
|
||||
}
|
||||
|
|
|
@ -92,8 +92,10 @@ public class MechanicalBearingTileEntity extends GeneratingKineticTileEntity
|
|||
if (!clientPacket)
|
||||
return;
|
||||
if (running) {
|
||||
clientAngleDiff = AngleHelper.getShortestAngleDiff(angleBefore, angle);
|
||||
angle = angleBefore;
|
||||
if (movedContraption == null || !movedContraption.isStalled()) {
|
||||
clientAngleDiff = AngleHelper.getShortestAngleDiff(angleBefore, angle);
|
||||
angle = angleBefore;
|
||||
}
|
||||
} else
|
||||
movedContraption = null;
|
||||
}
|
||||
|
|
|
@ -2,9 +2,12 @@ package com.simibubi.create.content.logistics.trains.entity;
|
|||
|
||||
import java.util.Collection;
|
||||
|
||||
import org.apache.commons.lang3.tuple.MutablePair;
|
||||
|
||||
import com.google.common.base.Strings;
|
||||
import com.simibubi.create.AllEntityTypes;
|
||||
import com.simibubi.create.Create;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.MovementContext;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.OrientedContraptionEntity;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.interaction.controls.ControlsBlock;
|
||||
import com.simibubi.create.content.logistics.trains.entity.TravellingPoint.SteerDirection;
|
||||
|
@ -201,6 +204,11 @@ public class CarriageContraptionEntity extends OrientedContraptionEntity {
|
|||
}
|
||||
|
||||
tickActors();
|
||||
contraption.stalled = false;
|
||||
for (MutablePair<StructureBlockInfo, MovementContext> pair : contraption.getActors()) {
|
||||
MovementContext context = pair.right;
|
||||
context.stall = false;
|
||||
}
|
||||
|
||||
if (!level.isClientSide)
|
||||
return;
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package com.simibubi.create.content.logistics.trains.track;
|
||||
|
||||
import com.jozufozu.flywheel.repack.joml.Math;
|
||||
import com.jozufozu.flywheel.util.transform.MatrixTransformStack;
|
||||
import com.mojang.blaze3d.vertex.PoseStack;
|
||||
import com.mojang.blaze3d.vertex.VertexConsumer;
|
||||
import com.simibubi.create.AllBlockPartials;
|
||||
|
@ -40,6 +41,8 @@ public class TrackRenderer extends SafeTileEntityRenderer<TrackTileEntity> {
|
|||
return;
|
||||
|
||||
ms.pushPose();
|
||||
new MatrixTransformStack(ms).nudge((int) bc.tePositions.getFirst()
|
||||
.asLong());
|
||||
|
||||
BlockPos tePosition = bc.tePositions.getFirst();
|
||||
Vec3 end1 = bc.starts.getFirst()
|
||||
|
@ -122,7 +125,7 @@ public class TrackRenderer extends SafeTileEntityRenderer<TrackTileEntity> {
|
|||
.rotateYRadians(angles.y)
|
||||
.rotateXRadians(angles.x)
|
||||
.rotateZRadians(angles.z)
|
||||
.translate(0, -2 / 16f + 1 / 1024f, 0)
|
||||
.translate(0, -2 / 16f + (i % 2 == 0 ? 1 : -1) / 2048f - 1 / 1024f, 0)
|
||||
.scale(1, 1, (float) diff.length() * 2.1f);
|
||||
|
||||
sbb.light(LevelRenderer.getLightColor(Minecraft.getInstance().level,
|
||||
|
|
Loading…
Reference in a new issue