From 58b97a8d80fcc12b373d5ef1e7aded48cd148218 Mon Sep 17 00:00:00 2001 From: TheBrokenRail Date: Mon, 20 Jul 2020 17:03:17 -0400 Subject: [PATCH] Improve Structure --- .../energonrelics/block/TestBlock.java | 2 +- .../entity/DefensiveLaserBlockEntity.java | 5 +- .../block/entity/EnergonLightBlockEntity.java | 4 +- .../PassiveBatteryControllerBlockEntity.java | 6 +- .../core/EnergyProviderBlockEntity.java | 6 +- .../energy/core/util/Action.java | 36 ++++- .../structure/StructurePart.java | 69 ++++++--- .../structure/StructurePlacer.java | 15 +- .../AbstractResearchComplexRoomPart.java | 135 ++++++++++++++++++ .../ResearchComplexHallwayPart.java | 87 +++++++++-- .../ResearchComplexStartPart.java | 74 +++++----- .../researchcomplex/ResearchComplexState.java | 21 ++- .../chests/research_complex_barrel.json | 97 +++++++++++++ 13 files changed, 460 insertions(+), 97 deletions(-) create mode 100644 src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/AbstractResearchComplexRoomPart.java create mode 100644 src/main/resources/data/energonrelics/loot_tables/chests/research_complex_barrel.json diff --git a/src/main/java/com/thebrokenrail/energonrelics/block/TestBlock.java b/src/main/java/com/thebrokenrail/energonrelics/block/TestBlock.java index 9ae261d..f2b675d 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/block/TestBlock.java +++ b/src/main/java/com/thebrokenrail/energonrelics/block/TestBlock.java @@ -22,7 +22,7 @@ public class TestBlock extends SimpleBlock { public void onBlockAdded(BlockState state, World world, BlockPos pos, BlockState oldState, boolean notify) { super.onBlockAdded(state, world, pos, oldState, notify); if (!world.isClient()) { - new StructurePlacer(new ResearchComplexStartPart(new ResearchComplexState(world), Collections.emptyList())).place(world, pos); + new StructurePlacer(new ResearchComplexStartPart(new ResearchComplexState(world, world.random), Collections.emptyList())).place(world, pos); } } } diff --git a/src/main/java/com/thebrokenrail/energonrelics/block/entity/DefensiveLaserBlockEntity.java b/src/main/java/com/thebrokenrail/energonrelics/block/entity/DefensiveLaserBlockEntity.java index 6e096ed..d67f5e0 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/block/entity/DefensiveLaserBlockEntity.java +++ b/src/main/java/com/thebrokenrail/energonrelics/block/entity/DefensiveLaserBlockEntity.java @@ -16,6 +16,7 @@ import net.minecraft.entity.player.PlayerEntity; import net.minecraft.nbt.CompoundTag; import net.minecraft.particle.ParticleTypes; import net.minecraft.server.world.ServerWorld; +import net.minecraft.util.Identifier; import net.minecraft.util.hit.HitResult; import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.Box; @@ -225,7 +226,7 @@ public class DefensiveLaserBlockEntity extends EnergyReceiverBlockEntity { @Override protected void tickEnergy() { assert getWorld() != null; - addAction(Action.createBlockStatePropertyAction(HardcodedConfig.DEFENSIVE_LASER_IDLE_ENERGY_REQUIRED, DefensiveLaserBlock.POWERED, true, false)); + addAction(Action.createBlockStatePropertyAction(HardcodedConfig.DEFENSIVE_LASER_IDLE_ENERGY_REQUIRED, DefensiveLaserBlock.POWERED, true, false, new Identifier(EnergonRelics.NAMESPACE, "defensive_laser_idle"))); if (getCachedState().get(DefensiveLaserBlock.POWERED)) { if (countdown > 0) { countdown--; @@ -234,7 +235,7 @@ public class DefensiveLaserBlockEntity extends EnergyReceiverBlockEntity { addAction(new Action(HardcodedConfig.DEFENSIVE_LASER_FIRE_ENERGY_REQUIRED, (world, pos, state) -> { firing = false; fire(world, pos); - }, (world, pos, state) -> firing = false)); + }, (world, pos, state) -> firing = false, new Identifier(EnergonRelics.NAMESPACE, "defensive_laser_fire"))); target = null; firing = true; } else if (countdown < 1 && !firing) { diff --git a/src/main/java/com/thebrokenrail/energonrelics/block/entity/EnergonLightBlockEntity.java b/src/main/java/com/thebrokenrail/energonrelics/block/entity/EnergonLightBlockEntity.java index 0ee5ebe..c9c70ac 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/block/entity/EnergonLightBlockEntity.java +++ b/src/main/java/com/thebrokenrail/energonrelics/block/entity/EnergonLightBlockEntity.java @@ -1,10 +1,12 @@ package com.thebrokenrail.energonrelics.block.entity; +import com.thebrokenrail.energonrelics.EnergonRelics; import com.thebrokenrail.energonrelics.config.HardcodedConfig; import com.thebrokenrail.energonrelics.block.EnergonLightBlock; import com.thebrokenrail.energonrelics.energy.core.EnergyReceiverBlockEntity; import com.thebrokenrail.energonrelics.energy.core.util.Action; import net.minecraft.block.entity.BlockEntityType; +import net.minecraft.util.Identifier; public class EnergonLightBlockEntity extends EnergyReceiverBlockEntity { public EnergonLightBlockEntity(BlockEntityType type) { @@ -13,6 +15,6 @@ public class EnergonLightBlockEntity extends EnergyReceiverBlockEntity { @Override protected void tickEnergy() { - addAction(Action.createBlockStatePropertyAction(HardcodedConfig.ENERGON_LIGHT_ENERGY_REQUIRED, EnergonLightBlock.POWERED, true, false)); + addAction(Action.createBlockStatePropertyAction(HardcodedConfig.ENERGON_LIGHT_ENERGY_REQUIRED, EnergonLightBlock.POWERED, true, false, new Identifier(EnergonRelics.NAMESPACE, "energon_light"))); } } diff --git a/src/main/java/com/thebrokenrail/energonrelics/block/entity/battery/PassiveBatteryControllerBlockEntity.java b/src/main/java/com/thebrokenrail/energonrelics/block/entity/battery/PassiveBatteryControllerBlockEntity.java index 35901ef..ba1da2f 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/block/entity/battery/PassiveBatteryControllerBlockEntity.java +++ b/src/main/java/com/thebrokenrail/energonrelics/block/entity/battery/PassiveBatteryControllerBlockEntity.java @@ -9,6 +9,7 @@ import com.thebrokenrail.energonrelics.energy.helper.EnergyGenerator; import net.minecraft.block.BlockState; import net.minecraft.block.entity.BlockEntity; import net.minecraft.block.entity.BlockEntityType; +import net.minecraft.util.Identifier; import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.Direction; import net.minecraft.world.World; @@ -18,11 +19,12 @@ public class PassiveBatteryControllerBlockEntity extends EnergyReceiverBlockEnti super(type); } - private static class UnlimitedAction implements Action.PropagatedAction { + private static class UnlimitedAction extends Action.UniqueAction implements Action.PropagatedAction { private final World world; private final BlockPos pos; private UnlimitedAction(World world, BlockPos pos) { + super(new Identifier(EnergonRelics.NAMESPACE, "active_battery_controller"), pos); this.world = world; this.pos = pos; } @@ -56,7 +58,7 @@ public class PassiveBatteryControllerBlockEntity extends EnergyReceiverBlockEnti PassiveBatteryControllerBlockEntity battery = (PassiveBatteryControllerBlockEntity) entity; battery.setEnergy(battery.getEnergy() + charge); } - }, (world, pos, state) -> {})); + }, (world, pos, state) -> {}, new Identifier(EnergonRelics.NAMESPACE, "passive_battery_controller"))); } else { propagateAction(new UnlimitedAction(getWorld(), getPos())); } diff --git a/src/main/java/com/thebrokenrail/energonrelics/energy/core/EnergyProviderBlockEntity.java b/src/main/java/com/thebrokenrail/energonrelics/energy/core/EnergyProviderBlockEntity.java index 7bff6b1..9ea49db 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/energy/core/EnergyProviderBlockEntity.java +++ b/src/main/java/com/thebrokenrail/energonrelics/energy/core/EnergyProviderBlockEntity.java @@ -90,8 +90,12 @@ public class EnergyProviderBlockEntity extends BlockEntity implements EnergyProv private void tickPropagatedActions() { if (isEnergyProvider()) { + List done = new ArrayList<>(); for (Action.PropagatedAction action : pendingPropagatedActions) { - handlePropagatedAction(action); + if (!done.contains(action)) { + handlePropagatedAction(action); + done.add(action); + } } NetworkComponent component = NetworkComponent.getInstance((ServerWorld) Objects.requireNonNull(getWorld())); diff --git a/src/main/java/com/thebrokenrail/energonrelics/energy/core/util/Action.java b/src/main/java/com/thebrokenrail/energonrelics/energy/core/util/Action.java index 2c1531a..6ed165e 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/energy/core/util/Action.java +++ b/src/main/java/com/thebrokenrail/energonrelics/energy/core/util/Action.java @@ -3,9 +3,12 @@ package com.thebrokenrail.energonrelics.energy.core.util; import net.minecraft.block.Block; import net.minecraft.block.BlockState; import net.minecraft.state.property.Property; +import net.minecraft.util.Identifier; import net.minecraft.util.math.BlockPos; import net.minecraft.world.World; +import java.util.Objects; + public class Action { public interface ActionFunction { void run(World world, BlockPos pos, BlockState state); @@ -14,14 +17,16 @@ public class Action { private final long cost; private final ActionFunction success; private final ActionFunction fail; + private final Identifier id; - public Action(long cost, ActionFunction success, ActionFunction fail) { + public Action(long cost, ActionFunction success, ActionFunction fail, Identifier id) { this.cost = cost; this.success = success; this.fail = fail; + this.id = id; } - public static > Action createBlockStatePropertyAction(long cost, Property property, T successValue, T failureValue) { + public static > Action createBlockStatePropertyAction(long cost, Property property, T successValue, T failureValue, Identifier id) { return new Action(cost, (world, pos, state) -> { if (!state.get(property).equals(successValue)) { world.setBlockState(pos, state.with(property, successValue)); @@ -30,7 +35,7 @@ public class Action { if (!state.get(property).equals(failureValue)) { world.setBlockState(pos, state.with(property, failureValue)); } - }); + }, id); } public interface PropagatedAction { @@ -39,7 +44,28 @@ public class Action { void pay(long amount); } - public static class PropagatedActionImpl implements PropagatedAction { + public static class UniqueAction { + private final Identifier id; + private final BlockPos pos; + + public UniqueAction(Identifier id, BlockPos pos) { + this.id = id; + this.pos = pos; + } + + @Override + public boolean equals(Object obj) { + if (this == obj) { + return true; + } else if (obj instanceof UniqueAction) { + return Objects.equals(id, ((UniqueAction) obj).id) && Objects.equals(pos, ((UniqueAction) obj).pos); + } else { + return false; + } + } + } + + public static class PropagatedActionImpl extends UniqueAction implements PropagatedAction { private final Action action; private final World world; private final BlockPos pos; @@ -49,7 +75,7 @@ public class Action { private long amountPaid = 0; public PropagatedActionImpl(Action action, World world, BlockPos pos, Block block) { - super(); + super(action.id, pos); this.action = action; this.world = world; this.pos = pos; diff --git a/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePart.java b/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePart.java index 3f2d837..7349ebf 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePart.java +++ b/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePart.java @@ -3,9 +3,9 @@ package com.thebrokenrail.energonrelics.structure; import com.thebrokenrail.energonrelics.util.MissingCaseException; import net.minecraft.block.BlockState; import net.minecraft.block.Blocks; +import net.minecraft.util.BlockMirror; import net.minecraft.util.BlockRotation; import net.minecraft.util.math.BlockPos; -import net.minecraft.util.math.Vec3d; import net.minecraft.world.World; import java.util.ArrayList; @@ -15,7 +15,7 @@ import java.util.Map; public abstract class StructurePart { protected interface Transformation { - Vec3d transform(Vec3d vec); + BlockPos transform(BlockPos pos); BlockState transform(BlockState state); } @@ -36,8 +36,8 @@ public abstract class StructurePart { protected static final Transformation NONE = new Transformation() { @Override - public Vec3d transform(Vec3d vec) { - return vec; + public BlockPos transform(BlockPos pos) { + return pos; } @Override @@ -47,8 +47,8 @@ public abstract class StructurePart { }; protected static final Transformation CLOCKWISE_90 = new Transformation() { @Override - public Vec3d transform(Vec3d vec) { - return new Vec3d(-vec.getZ(), vec.getY(), vec.getX()); + public BlockPos transform(BlockPos pos) { + return new BlockPos(-pos.getZ(), pos.getY(), pos.getX()); } @Override @@ -58,8 +58,8 @@ public abstract class StructurePart { }; protected static final Transformation CLOCKWISE_180 = new Transformation() { @Override - public Vec3d transform(Vec3d vec) { - return new Vec3d(-vec.getX(), vec.getY(), -vec.getZ()); + public BlockPos transform(BlockPos pos) { + return new BlockPos(-pos.getX(), pos.getY(), -pos.getZ()); } @Override @@ -69,8 +69,8 @@ public abstract class StructurePart { }; protected static final Transformation COUNTERCLOCKWISE_90 = new Transformation() { @Override - public Vec3d transform(Vec3d vec) { - return new Vec3d(vec.getZ(), vec.getY(), -vec.getX()); + public BlockPos transform(BlockPos pos) { + return new BlockPos(pos.getZ(), pos.getY(), -pos.getX()); } @Override @@ -78,10 +78,21 @@ public abstract class StructurePart { return state.rotate(BlockRotation.COUNTERCLOCKWISE_90); } }; + protected static final Transformation MIRROR = new Transformation() { + @Override + public BlockPos transform(BlockPos pos) { + return new BlockPos(pos.getX(), pos.getY(), -pos.getZ()); + } + + @Override + public BlockState transform(BlockState state) { + return state.mirror(BlockMirror.LEFT_RIGHT); + } + }; protected abstract void build(StructureContext context); - private Vec3d transform(Vec3d pos) { + private BlockPos transform(BlockPos pos) { for (Transformation transformation : transformations) { pos = transformation.transform(pos); } @@ -95,22 +106,22 @@ public abstract class StructurePart { return state; } - protected void set(int x, int y, int z, BlockState state) { - Vec3d vec = transform(new Vec3d(x, y, z)); - blocks.put(new BlockPos(vec.getX(), vec.getY(), vec.getZ()).asLong(), transform(state)); + protected void set(BlockPos originalPos, BlockState state) { + BlockPos pos = transform(originalPos); + blocks.put(pos.asLong(), transform(state)); } - protected void rect(int xPos, int yPos, int zPos, int width, int height, int depth, BlockState state) { + protected void rect(BlockPos pos, int width, int height, int depth, BlockState state) { for (int x = 0; x < width; x++) { for (int y = 0; y < height; y++) { for (int z = 0; z < depth; z++) { - set(x + xPos, y + yPos, z + zPos, state); + set(pos.add(x, y, z), state); } } } } - protected void repeat(Transformation[] functions, Runnable action) { + protected void rotate(Transformation[] functions, Runnable action) { for (Transformation function : functions) { transformations.add(function); action.run(); @@ -118,8 +129,8 @@ public abstract class StructurePart { } } - protected void repeat(Runnable action) { - repeat(new Transformation[]{NONE, CLOCKWISE_90, CLOCKWISE_180, COUNTERCLOCKWISE_90}, action); + protected void rotate(Runnable action) { + rotate(new Transformation[]{NONE, CLOCKWISE_90, CLOCKWISE_180, COUNTERCLOCKWISE_90}, action); } public void place(World world, BlockPos pos) { @@ -156,12 +167,26 @@ public abstract class StructurePart { } } - protected void part(StructureContext context, int x, int y, int z, StructurePart part) { - Vec3d vec = transform(new Vec3d(x, y, z)); - context.addPart((int) vec.getX(), (int) vec.getY(), (int) vec.getZ(), part); + protected void part(StructureContext context, BlockPos originalPos, StructurePart part) { + BlockPos pos = transform(originalPos); + context.addPart(pos.getX(), pos.getY(), pos.getZ(), part); } protected List getTransformations() { return transformations; } + + private BlockPos pos = null; + + private BlockPos getPos() { + return pos; + } + + protected BlockPos getPosFromOrigin(BlockPos pos) { + return transform(pos).add(getPos()); + } + + void setPos(BlockPos pos) { + this.pos = pos; + } } diff --git a/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePlacer.java b/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePlacer.java index 2266ed9..9cc3c1c 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePlacer.java +++ b/src/main/java/com/thebrokenrail/energonrelics/structure/StructurePlacer.java @@ -1,6 +1,5 @@ package com.thebrokenrail.energonrelics.structure; -import net.minecraft.block.Blocks; import net.minecraft.util.math.BlockPos; import net.minecraft.world.World; @@ -34,12 +33,8 @@ public class StructurePlacer { while (!pendingParts.isEmpty()) { List newPendingParts = new ArrayList<>(); for (StructurePos part : pendingParts) { - if (part.part != null) { - part.part.build((x, y, z, newPart) -> { - newPendingParts.add(new StructurePos(x + part.x, y + part.y, z + part.z, null)); - //newPendingParts.add(new StructurePos(x + part.x, y + part.y, z + part.z, newPart)); - }); - } + part.part.setPos(new BlockPos(part.x, part.y, part.z)); + part.part.build((x, y, z, newPart) -> newPendingParts.add(new StructurePos(x + part.x, y + part.y, z + part.z, newPart))); parts.add(part); } pendingParts.clear(); @@ -50,11 +45,7 @@ public class StructurePlacer { public void place(World world, BlockPos pos) { for (StructurePos part : parts) { BlockPos newPos = pos.add(part.x, part.y, part.z); - if (part.part != null) { - part.part.place(world, newPos); - } else { - world.setBlockState(newPos, Blocks.DIORITE.getDefaultState()); - } + part.part.place(world, newPos); } } } diff --git a/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/AbstractResearchComplexRoomPart.java b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/AbstractResearchComplexRoomPart.java new file mode 100644 index 0000000..69e9e71 --- /dev/null +++ b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/AbstractResearchComplexRoomPart.java @@ -0,0 +1,135 @@ +package com.thebrokenrail.energonrelics.structure.researchcomplex; + +import com.thebrokenrail.energonrelics.EnergonRelics; +import com.thebrokenrail.energonrelics.config.HardcodedConfig; +import com.thebrokenrail.energonrelics.structure.StructureContext; +import net.minecraft.block.BlockState; +import net.minecraft.block.Blocks; +import net.minecraft.block.DoorBlock; +import net.minecraft.block.entity.BarrelBlockEntity; +import net.minecraft.block.entity.BlockEntity; +import net.minecraft.block.enums.DoubleBlockHalf; +import net.minecraft.util.Identifier; +import net.minecraft.util.math.BlockPos; +import net.minecraft.util.math.Direction; +import net.minecraft.world.World; + +import java.util.ArrayList; +import java.util.List; + +public abstract class AbstractResearchComplexRoomPart extends BaseResearchComplexPart { + public AbstractResearchComplexRoomPart(ResearchComplexState state, List list) { + super(state, list); + } + + @Override + protected void build(StructureContext context) { + if (hasEnergy()) { + BlockState air = Blocks.AIR.getDefaultState(); + BlockState bricks = Blocks.QUARTZ_BRICKS.getDefaultState(); + + rect(new BlockPos(-1, 0, 2), getWidth() * 3, 3, 3, air); + rect(new BlockPos(-1, -1, 2), getWidth() * 3, 1, 3, bricks); + rect(new BlockPos(-1, 3, 2), getWidth() * 3, 1, 3, bricks); + rect(new BlockPos(-1, 0, 5), getWidth() * 3, 3, 1, bricks); + rect(new BlockPos(-1, 0, 1), getWidth() * 3, 3, 1, bricks); + rect(new BlockPos(-2, 0, 2), 1, 3, 3, bricks); + rect(new BlockPos(-1 + getWidth() * 3, 0, 2), 1, 3, 3, bricks); + + BlockState plate = Blocks.HEAVY_WEIGHTED_PRESSURE_PLATE.getDefaultState(); + + set(new BlockPos(0, -1, 0), bricks); + set(new BlockPos(0, 0, 0), plate); + + BlockState door = Blocks.IRON_DOOR.getDefaultState().with(DoorBlock.FACING, Direction.SOUTH); + BlockState bottomDoor = door.with(DoorBlock.HALF, DoubleBlockHalf.LOWER); + BlockState topDoor = door.with(DoorBlock.HALF, DoubleBlockHalf.UPPER); + + set(new BlockPos(0, 0, 1), bottomDoor); + set(new BlockPos(0, 1, 1), topDoor); + set(new BlockPos(0, -1, 1), bricks); + + set(new BlockPos(0, 0, 2), plate); + + BlockState light = EnergonRelics.ENERGON_LIGHT_BLOCK.getDefaultState(); + List list = getLights(); + for (BlockPos pos : list) { + set(pos, light); + } + + buildInterior(); + } + } + + protected abstract void buildInterior(); + + private List getLights() { + List lights = new ArrayList<>(); + for (int i = 0; i < getWidth(); i++) { + lights.add(new BlockPos(i * 3, 3, 3)); + } + return lights; + } + + protected boolean hasEnergy() { + List list = getLights(); + return getState().hasEnergy(list.size() * HardcodedConfig.ENERGON_LIGHT_ENERGY_REQUIRED, getPosFromOrigin(list.get(list.size() - 1))); + } + + abstract int getWidth(); + + static AbstractResearchComplexRoomPart get(ResearchComplexState state, List transformations) { + if (state.random.nextFloat() <= Barrel.CHANCE) { + return new Barrel(state, transformations); + } else { + return new Simple(state, transformations); + } + } + + private static class Simple extends AbstractResearchComplexRoomPart { + private Simple(ResearchComplexState state, List list) { + super(state, list); + } + + @Override + int getWidth() { + return 1; + } + + @Override + protected void buildInterior() { + + } + } + + private static class Barrel extends AbstractResearchComplexRoomPart { + private static final float CHANCE = 0.05f; + + private Barrel(ResearchComplexState state, List list) { + super(state, list); + } + + @Override + int getWidth() { + return 2; + } + + @Override + protected void buildInterior() { + BlockState barrel = Blocks.BARREL.getDefaultState(); + rect(new BlockPos(3, 0, 2), 2, 2, 3, barrel); + rect(new BlockPos(2, 0, 3), 1, 1, 2, barrel); + rect(new BlockPos(4, 2, 3), 1, 1, 2, barrel); + set(new BlockPos(1, 0, 4), barrel); + } + + @Override + protected void handleBlockPlace(World world, BlockPos pos, BlockState state) { + super.handleBlockPlace(world, pos, state); + BlockEntity entity = world.getBlockEntity(pos); + if (entity instanceof BarrelBlockEntity) { + ((BarrelBlockEntity) entity).setLootTable(new Identifier(EnergonRelics.NAMESPACE, "chests/research_complex_barrel"), getState().random.nextLong()); + } + } + } +} diff --git a/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexHallwayPart.java b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexHallwayPart.java index 76a43b3..3febd9e 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexHallwayPart.java +++ b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexHallwayPart.java @@ -1,14 +1,31 @@ package com.thebrokenrail.energonrelics.structure.researchcomplex; +import com.thebrokenrail.energonrelics.EnergonRelics; +import com.thebrokenrail.energonrelics.config.HardcodedConfig; import com.thebrokenrail.energonrelics.structure.StructureContext; import net.minecraft.block.BlockState; import net.minecraft.block.Blocks; +import net.minecraft.block.StairsBlock; +import net.minecraft.block.enums.BlockHalf; +import net.minecraft.util.math.BlockPos; +import net.minecraft.util.math.Direction; +import java.util.ArrayList; import java.util.List; public class ResearchComplexHallwayPart extends BaseResearchComplexPart { - public ResearchComplexHallwayPart(ResearchComplexState state, List list) { + private final boolean hasLight; + + private int rightRoomPadding; + private int leftRoomPadding; + + private static final float ROOM_CHANCE = 0.4f; + + public ResearchComplexHallwayPart(ResearchComplexState state, List list, boolean hasLight, int rightRoomPadding, int leftRoomPadding) { super(state, list); + this.hasLight = hasLight; + this.rightRoomPadding = rightRoomPadding; + this.leftRoomPadding = leftRoomPadding; } private int getHeight() { @@ -22,14 +39,68 @@ public class ResearchComplexHallwayPart extends BaseResearchComplexPart { @Override protected void build(StructureContext context) { BlockState bricks = Blocks.QUARTZ_BRICKS.getDefaultState(); - BlockState air = Blocks.AIR.getDefaultState(); - for (int y = 0; y < getHeight(); y++) { - boolean isBricks = y == 0 || y == getHeight() - 1; - BlockState state = isBricks ? bricks : air; - rect(2, y, 0, 3, 1, getDepth(), state); - if (y > 1 && y < getHeight() - 2) { - rect(0, y, 0, 1, 2, getDepth(), bricks); + if (!hasLight || getState().hasEnergy(HardcodedConfig.ENERGON_LIGHT_ENERGY_REQUIRED, getPosFromOrigin(new BlockPos(3, 5, 1)))) { + BlockState air = Blocks.AIR.getDefaultState(); + + BlockState stairs = Blocks.QUARTZ_STAIRS.getDefaultState(); + BlockState westStairs = stairs.with(StairsBlock.FACING, Direction.WEST); + BlockState eastStairs = stairs.with(StairsBlock.FACING, Direction.EAST); + + for (int y = 0; y < getHeight(); y++) { + BlockState state = y == 0 || y == getHeight() - 1 ? bricks : air; + if (y > 1 && y < getHeight() - 2) { + rect(new BlockPos(1, y, 0), 5, 1, getDepth(), air); + rect(new BlockPos(0, y, 0), 1, 1, getDepth(), bricks); + rect(new BlockPos(6, y, 0), 1, 1, getDepth(), bricks); + } else { + rect(new BlockPos(2, y, 0), 3, 1, getDepth(), state); + } + if (y == 1 || y == getHeight() - 2) { + if (y == getHeight() - 2) { + eastStairs = eastStairs.with(StairsBlock.HALF, BlockHalf.TOP); + westStairs = westStairs.with(StairsBlock.HALF, BlockHalf.TOP); + } + rect(new BlockPos(1, y, 0), 1, 1, getDepth(), westStairs); + rect(new BlockPos(5, y, 0), 1, 1, getDepth(), eastStairs); + } } + + if (hasLight) { + set(new BlockPos(3, 5, 1), EnergonRelics.ENERGON_LIGHT_BLOCK.getDefaultState()); + } + + if (leftRoomPadding == 0) { + if (getState().random.nextFloat() <= ROOM_CHANCE) { + AbstractResearchComplexRoomPart room = AbstractResearchComplexRoomPart.get(getState(), getRoomTransformation(true)); + part(context, new BlockPos(5, 1, 1), room); + leftRoomPadding = room.getWidth(); + } + } else { + leftRoomPadding = leftRoomPadding - 1; + } + if (rightRoomPadding == 0) { + if (getState().random.nextFloat() <= ROOM_CHANCE) { + AbstractResearchComplexRoomPart room = AbstractResearchComplexRoomPart.get(getState(), getRoomTransformation(false)); + part(context, new BlockPos(1, 1, 1), room); + rightRoomPadding = room.getWidth(); + } + } else { + rightRoomPadding = rightRoomPadding - 1; + } + + part(context, new BlockPos(0, 0, getDepth()), new ResearchComplexHallwayPart(getState(), getTransformations(), !hasLight, rightRoomPadding, leftRoomPadding)); + } else { + rect(new BlockPos(1, 1, 0), 5, 4, 1, bricks); } } + + private List getRoomTransformation(boolean mirror) { + List list = new ArrayList<>(); + if (mirror) { + list.add(MIRROR); + } + list.addAll(getTransformations()); + list.add(com.thebrokenrail.energonrelics.structure.StructurePart.CLOCKWISE_90); + return list; + } } diff --git a/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexStartPart.java b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexStartPart.java index ed32d83..33e7280 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexStartPart.java +++ b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexStartPart.java @@ -23,12 +23,12 @@ public class ResearchComplexStartPart extends BaseResearchComplexPart { super(state, list); } - private void setBlockOrAir(int x, int y, int z, BlockState stairs) { - if (y == 1 || y == 4) { - set(x, y, z, stairs); + private void setBlockOrAir(BlockPos pos, BlockState state) { + if (pos.getY() == 1 || pos.getY() == 4) { + set(pos, state); } else { BlockState air = Blocks.AIR.getDefaultState(); - set(x, y, z, air); + set(pos, air); } } @@ -38,12 +38,12 @@ public class ResearchComplexStartPart extends BaseResearchComplexPart { BlockState state = yOffset == 0 || yOffset == 5 ? bricks : air; - rect(0, yOffset, 0, 2, 1, 6, state); - rect(0, yOffset, 0, 6, 1, 2, state); + rect(new BlockPos(0, yOffset, 0), 2, 1, 6, state); + rect(new BlockPos(0, yOffset, 0), 6, 1, 2, state); - set(2, yOffset, 3, state); - set(3, yOffset, 2, state); - set(3, yOffset, 3, state); + set(new BlockPos(2, yOffset, 3), state); + set(new BlockPos(3, yOffset, 2), state); + set(new BlockPos(2, yOffset, 2), state); if (yOffset != 0 && yOffset != 5) { BlockState stairs = Blocks.QUARTZ_STAIRS.getDefaultState(); @@ -51,52 +51,52 @@ public class ResearchComplexStartPart extends BaseResearchComplexPart { BlockHalf half = yOffset == 1 ? BlockHalf.BOTTOM : BlockHalf.TOP; stairs = stairs.with(StairsBlock.HALF, half); - BlockState westStairs = stairs.with(StairsBlock.FACING, Direction.WEST); - BlockState northStairs = stairs.with(StairsBlock.FACING, Direction.NORTH); - BlockState outerLeftStairs = northStairs.with(StairsBlock.SHAPE, StairShape.OUTER_LEFT); - BlockState innerLeftStairs = northStairs.with(StairsBlock.SHAPE, StairShape.INNER_LEFT); - BlockState innerRightStairs = westStairs.with(StairsBlock.SHAPE, StairShape.INNER_RIGHT); - BlockState outerRightStairs = westStairs.with(StairsBlock.SHAPE, StairShape.OUTER_RIGHT); + BlockState eastStairs = stairs.with(StairsBlock.FACING, Direction.EAST); + BlockState southStairs = stairs.with(StairsBlock.FACING, Direction.SOUTH); + BlockState outerLeftStairs = southStairs.with(StairsBlock.SHAPE, StairShape.OUTER_LEFT); + BlockState innerLeftStairs = southStairs.with(StairsBlock.SHAPE, StairShape.INNER_LEFT); + BlockState innerRightStairs = eastStairs.with(StairsBlock.SHAPE, StairShape.INNER_RIGHT); + BlockState outerRightStairs = eastStairs.with(StairsBlock.SHAPE, StairShape.OUTER_RIGHT); - setBlockOrAir(3, yOffset, 0, westStairs); - setBlockOrAir(3, yOffset, 1, outerLeftStairs); - setBlockOrAir(2, yOffset, 1, innerRightStairs); - setBlockOrAir(2, yOffset, 2, outerLeftStairs); - setBlockOrAir(1, yOffset, 2, innerLeftStairs); - setBlockOrAir(1, yOffset, 3, outerRightStairs); - setBlockOrAir(0, yOffset, 3, northStairs); + setBlockOrAir(new BlockPos(2, yOffset, 5), eastStairs); + setBlockOrAir(new BlockPos(2, yOffset, 4), outerLeftStairs); + setBlockOrAir(new BlockPos(3, yOffset, 4), innerRightStairs); + setBlockOrAir(new BlockPos(3, yOffset, 3), outerLeftStairs); + setBlockOrAir(new BlockPos(4, yOffset, 3), innerLeftStairs); + setBlockOrAir(new BlockPos(4, yOffset, 2), outerRightStairs); + setBlockOrAir(new BlockPos(5, yOffset, 2), southStairs); if (yOffset != 1 && yOffset != 4) { - set(2, yOffset, 0, bricks); - set(1, yOffset, 1, bricks); - set(0, yOffset, 2, bricks); + set(new BlockPos(3, yOffset, 5), bricks); + set(new BlockPos(4, yOffset, 4), bricks); + set(new BlockPos(5, yOffset, 3), bricks); } } if (yOffset == 5) { - set(3, yOffset, 3, EnergonRelics.ENERGON_LIGHT_BLOCK.getDefaultState()); + set(new BlockPos(2, yOffset, 2), EnergonRelics.ENERGON_LIGHT_BLOCK.getDefaultState()); } } private void buildReactor() { - set(0, 1, 0, EnergonRelics.THERMAL_CASING_BLOCK.getDefaultState()); - set(1, 2, 0, EnergonRelics.THERMAL_CASING_BLOCK.getDefaultState()); - set(0, 2, 0, EnergonRelics.REACTOR_CORE_BLOCK.getDefaultState()); - set(-1, 2, 0, EnergonRelics.THERMAL_CASING_BLOCK.getDefaultState()); - set(0, 3, 0, EnergonRelics.REACTOR_INPUT_BLOCK.getDefaultState()); - set(0, 2, 1, EnergonRelics.REACTOR_CONTROLLER_BLOCK.getDefaultState()); - set(0, 1, 1, Blocks.LEVER.getDefaultState().with(LeverBlock.FACE, WallMountLocation.FLOOR)); - set(0, 2, -1, EnergonRelics.THERMAL_GLASS_BLOCK.getDefaultState()); + set(new BlockPos(0, 1, 0), EnergonRelics.THERMAL_CASING_BLOCK.getDefaultState()); + set(new BlockPos(1, 2, 0), EnergonRelics.THERMAL_CASING_BLOCK.getDefaultState()); + set(new BlockPos(0, 2, 0), EnergonRelics.REACTOR_CORE_BLOCK.getDefaultState()); + set(new BlockPos(-1, 2, 0), EnergonRelics.THERMAL_CASING_BLOCK.getDefaultState()); + set(new BlockPos(0, 3, 0), EnergonRelics.REACTOR_INPUT_BLOCK.getDefaultState()); + set(new BlockPos(0, 2, -1), EnergonRelics.REACTOR_CONTROLLER_BLOCK.getDefaultState()); + set(new BlockPos(0, 1, -1), Blocks.LEVER.getDefaultState().with(LeverBlock.FACE, WallMountLocation.FLOOR)); + set(new BlockPos(0, 2, 1), EnergonRelics.THERMAL_GLASS_BLOCK.getDefaultState()); } @Override protected void build(StructureContext context) { - if (getState().hasEnergy(HardcodedConfig.ENERGON_LIGHT_ENERGY_REQUIRED * 4)) { - repeat(() -> { + if (getState().hasEnergy(HardcodedConfig.ENERGON_LIGHT_ENERGY_REQUIRED * 4, new BlockPos(0, 2, 0))) { + rotate(() -> { for (int i = 0; i < 6; i++) { buildBase(i); } - //part(context, 1, 0, getWidth() / 2, new ResearchComplexHallwayPart(getState(), getTransformations())); + part(context, new BlockPos(-3, 0, 6), new ResearchComplexHallwayPart(getState(), getTransformations(), true, 1, 1)); }); buildReactor(); } diff --git a/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexState.java b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexState.java index b4b7f0a..47d398e 100644 --- a/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexState.java +++ b/src/main/java/com/thebrokenrail/energonrelics/structure/researchcomplex/ResearchComplexState.java @@ -3,17 +3,22 @@ package com.thebrokenrail.energonrelics.structure.researchcomplex; import com.thebrokenrail.energonrelics.component.NetworkComponent; import com.thebrokenrail.energonrelics.config.HardcodedConfig; import net.minecraft.server.world.ServerWorld; -import net.minecraft.util.BlockRotation; +import net.minecraft.util.math.BlockPos; import net.minecraft.world.World; +import java.util.Random; + public class ResearchComplexState { private final int baseID; private long energyBudget = HardcodedConfig.REACTOR_ENERGY_OUTPUT; - public ResearchComplexState(World world) { + final Random random; + + public ResearchComplexState(World world, Random random) { ServerWorld serverWorld = (ServerWorld) world; NetworkComponent component = NetworkComponent.getInstance(serverWorld); baseID = component.create(); + this.random = random; } private int getID(int id) { @@ -24,10 +29,14 @@ public class ResearchComplexState { return getID(0); } - boolean hasEnergy(long amount) { - if (amount <= energyBudget) { - energyBudget = energyBudget - amount; - return true; + boolean hasEnergy(long amount, BlockPos pos) { + if (pos.isWithinDistance(new BlockPos(0, 2, 0), HardcodedConfig.POWER_RANGE)) { + if (amount <= energyBudget) { + energyBudget = energyBudget - amount; + return true; + } else { + return false; + } } else { return false; } diff --git a/src/main/resources/data/energonrelics/loot_tables/chests/research_complex_barrel.json b/src/main/resources/data/energonrelics/loot_tables/chests/research_complex_barrel.json new file mode 100644 index 0000000..08ecc12 --- /dev/null +++ b/src/main/resources/data/energonrelics/loot_tables/chests/research_complex_barrel.json @@ -0,0 +1,97 @@ +{ + "type": "minecraft:chest", + "pools": [ + { + "rolls": 4, + "entries": [ + { + "type": "minecraft:item", + "name": "minecraft:string", + "weight": 31, + "functions": [ + { + "function": "minecraft:set_count", + "count": { + "type": "minecraft:uniform", + "min": 1, + "max": 5 + } + } + ] + }, + { + "type": "minecraft:item", + "name": "minecraft:bread", + "weight": 14, + "functions": [ + { + "function": "minecraft:set_count", + "count": { + "type": "minecraft:uniform", + "min": 1, + "max": 3 + } + } + ] + }, + { + "type": "minecraft:item", + "name": "minecraft:iron_ingot", + "weight": 5, + "functions": [ + { + "function": "minecraft:set_count", + "count": { + "type": "minecraft:uniform", + "min": 1, + "max": 2 + } + } + ] + }, + { + "type": "minecraft:item", + "name": "minecraft:gold_ingot", + "weight": 2, + "functions": [ + { + "function": "minecraft:set_count", + "count": 1 + } + ] + } + ] + }, + { + "rolls": 1, + "entries": [ + { + "type": "minecraft:item", + "name": "energonrelics:circuit_board", + "weight": 12, + "functions": [ + { + "function": "minecraft:set_count", + "count": { + "type": "minecraft:uniform", + "min": 1, + "max": 6 + } + } + ] + }, + { + "type": "minecraft:item", + "name": "energonrelics:veridium_ingot", + "weight": 2, + "functions": [ + { + "function": "minecraft:set_count", + "count": 1 + } + ] + } + ] + } + ] +} \ No newline at end of file