Abstraction, separation, battery containers

This commit is contained in:
DBotThePony 2021-08-10 15:30:47 +07:00
parent e8665ddde2
commit f440a593f3
Signed by: DBot
GPG Key ID: DCC23B5715498507
12 changed files with 465 additions and 182 deletions

View File

@ -1,29 +1,14 @@
package ru.dbotthepony.mc.otm.block;
import net.minecraft.core.BlockPos;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.resources.ResourceLocation;
import net.minecraft.tags.BlockTags;
import net.minecraft.world.InteractionHand;
import net.minecraft.world.InteractionResult;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.level.BlockGetter;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.block.Block;
import net.minecraft.world.level.block.EntityBlock;
import net.minecraft.world.level.block.entity.BlockEntity;
import net.minecraft.world.level.block.entity.BlockEntityTicker;
import net.minecraft.world.level.block.entity.BlockEntityType;
import net.minecraft.world.level.block.state.BlockBehaviour;
import net.minecraft.world.level.block.state.BlockState;
import net.minecraft.world.level.material.Material;
import net.minecraft.world.level.material.MaterialColor;
import net.minecraft.world.level.storage.loot.LootContext;
import net.minecraft.world.level.storage.loot.parameters.LootContextParam;
import net.minecraft.world.level.storage.loot.parameters.LootContextParams;
import net.minecraft.world.phys.BlockHitResult;
import net.minecraft.world.phys.shapes.CollisionContext;
import net.minecraft.world.phys.shapes.Shapes;
import net.minecraft.world.phys.shapes.VoxelShape;
@ -31,26 +16,16 @@ import ru.dbotthepony.mc.otm.OverdriveThatMatters;
import ru.dbotthepony.mc.otm.block.entity.BlockEntityAndroidStation;
import javax.annotation.Nullable;
import java.util.Collections;
import java.util.List;
public class BlockAndroidStation extends Block implements EntityBlock {
public class BlockAndroidStation extends BlockMatteryMachineBase implements EntityBlock {
public static final ResourceLocation REGISTRY_NAME = new ResourceLocation(OverdriveThatMatters.MOD_ID, "android_station");
private final VoxelShape SHAPE = Shapes.box(0, 0, 0, 1, 0.5, 1);
public BlockAndroidStation() {
super(BlockBehaviour.Properties.of(Material.STONE, MaterialColor.STONE).requiresCorrectToolForDrops().strength(1.5F, 6.0F));
super();
this.setRegistryName(REGISTRY_NAME);
}
@Override
public void setPlacedBy(Level p_49847_, BlockPos p_49848_, BlockState p_49849_, @Nullable LivingEntity p_49850_, ItemStack p_49851_) {
if (p_49851_.hasCustomHoverName() && !p_49847_.isClientSide && p_49847_.getBlockEntity(p_49848_) instanceof BlockEntityAndroidStation tile) {
tile.setDisplayName(p_49851_.getDisplayName());
}
super.setPlacedBy(p_49847_, p_49848_, p_49849_, p_49850_, p_49851_);
}
@Override
public VoxelShape getShape(BlockState p_151964_, BlockGetter p_151965_, BlockPos p_151966_, CollisionContext p_151967_) {
return SHAPE;
@ -67,14 +42,4 @@ public class BlockAndroidStation extends Block implements EntityBlock {
public <T extends BlockEntity> BlockEntityTicker<T> getTicker(Level level, BlockState state, BlockEntityType<T> type) {
return level.isClientSide || type != OverdriveThatMatters.ANDROID_STATION_FACTORY ? null : BlockEntityAndroidStation::tick;
}
@Override
public InteractionResult use(BlockState p_60503_, Level level, BlockPos pos, Player ply, InteractionHand p_60507_, BlockHitResult p_60508_) {
if (!level.isClientSide && level.getBlockEntity(pos) instanceof BlockEntityAndroidStation tile) {
ply.openMenu(tile);
return InteractionResult.CONSUME;
}
return InteractionResult.SUCCESS;
}
}

View File

@ -0,0 +1,53 @@
package ru.dbotthepony.mc.otm.block;
import net.minecraft.core.BlockPos;
import net.minecraft.world.InteractionHand;
import net.minecraft.world.InteractionResult;
import net.minecraft.world.MenuProvider;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.block.Block;
import net.minecraft.world.level.block.EntityBlock;
import net.minecraft.world.level.block.state.BlockBehaviour;
import net.minecraft.world.level.block.state.BlockState;
import net.minecraft.world.level.material.Material;
import net.minecraft.world.level.material.MaterialColor;
import net.minecraft.world.phys.BlockHitResult;
import ru.dbotthepony.mc.otm.block.entity.BlockEntityAndroidStation;
import ru.dbotthepony.mc.otm.block.entity.BlockEntityMatteryMachine;
import javax.annotation.Nullable;
public abstract class BlockMatteryMachineBase extends Block {
public BlockMatteryMachineBase(Properties p_49795_) {
super(p_49795_);
}
public BlockMatteryMachineBase() {
this(BlockBehaviour.Properties.of(Material.STONE, MaterialColor.STONE).requiresCorrectToolForDrops().strength(1.5F, 6.0F));
}
@Override
public void setPlacedBy(Level p_49847_, BlockPos p_49848_, BlockState p_49849_, @Nullable LivingEntity p_49850_, ItemStack p_49851_) {
if (this instanceof EntityBlock && p_49851_.hasCustomHoverName() && !p_49847_.isClientSide && p_49847_.getBlockEntity(p_49848_) instanceof BlockEntityMatteryMachine tile) {
tile.setDisplayName(p_49851_.getDisplayName());
}
super.setPlacedBy(p_49847_, p_49848_, p_49849_, p_49850_, p_49851_);
}
@Override
public InteractionResult use(BlockState p_60503_, Level level, BlockPos pos, Player ply, InteractionHand p_60507_, BlockHitResult p_60508_) {
if (this instanceof EntityBlock && !level.isClientSide && level.getBlockEntity(pos) instanceof MenuProvider tile) {
ply.openMenu(tile);
return InteractionResult.CONSUME;
}
if (this instanceof EntityBlock && level.isClientSide)
return InteractionResult.SUCCESS;
return super.use(p_60503_, level, pos, ply, p_60507_, p_60508_);
}
}

View File

@ -5,7 +5,6 @@ import net.minecraft.core.Direction;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.nbt.StringTag;
import net.minecraft.network.chat.Component;
import net.minecraft.network.chat.TranslatableComponent;
import net.minecraft.world.MenuProvider;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.entity.player.Inventory;
@ -29,97 +28,48 @@ import javax.annotation.Nullable;
import java.math.BigDecimal;
import java.util.List;
public class BlockEntityAndroidStation extends BlockEntity implements MenuProvider {
private Component display_name;
public void setDisplayName(Component text) {
display_name = text;
}
@Override
public Component getDisplayName() {
return display_name != null ? display_name : new TranslatableComponent("container.otm.android_station");
}
public class BlockEntityAndroidStation extends BlockEntityMatteryPoweredMachine implements MenuProvider {
@Nullable
@Override
public AbstractContainerMenu createMenu(int containerID, Inventory inventory, Player ply) {
return new AndroidStationMenu(containerID, inventory, new AndroidStationMenu.AndroidStationContainer(ply), this);
return new AndroidStationMenu(containerID, inventory, this);
}
private final MatteryMachineEnergyStorage energy = new MatteryMachineEnergyStorage(MatteryMachineEnergyStorage.MachineType.WORKER);
public BlockEntityAndroidStation(BlockPos p_155229_, BlockState p_155230_) {
super(OverdriveThatMatters.ANDROID_STATION_FACTORY, p_155229_, p_155230_);
energy = new MatteryMachineEnergyStorage(MatteryMachineEnergyStorage.MachineType.WORKER, new BigDecimal(128_000));
energy_resolver = LazyOptional.of(() -> energy);
}
@Nonnull
public <T> LazyOptional<T> getCapability(@Nonnull Capability<T> cap, @Nullable Direction side) {
if (cap == MatteryCapability.ENERGY || cap == CapabilityEnergy.ENERGY) {
return LazyOptional.of(() -> energy).cast();
}
public static <T extends BlockEntity> void tick(Level level, BlockPos blockPos, BlockState blockState, T t) {
if (t instanceof BlockEntityAndroidStation tile) {
tile.tickBatteryCharge();
return super.getCapability(cap, side);
}
BlockPos pos = tile.getBlockPos();
List<LivingEntity> entities = tile.getLevel().getEntitiesOfClass(LivingEntity.class, new AABB(pos.getX(), pos.getY(), pos.getZ(), pos.getX() + 1, pos.getY() + 2, pos.getZ() + 1));
@Override
public CompoundTag save(CompoundTag nbt) {
nbt.put("energy_cap", energy.serializeNBT());
for (LivingEntity ent : entities) {
LazyOptional<IAndroidCapability> resolver = ent.getCapability(MatteryCapability.ANDROID);
if (display_name != null) {
nbt.putString("Name", Component.Serializer.toJson(display_name));
}
if (resolver.isPresent()) {
IAndroidCapability capability = resolver.resolve().get();
return super.save(nbt);
}
BigDecimal missing = capability.getMissingPower();
public void load(CompoundTag nbt) {
super.load(nbt);
if (missing.compareTo(BigDecimal.ZERO) == 1) {
BigDecimal extract = tile.energy.extractEnergyInner(missing, true);
if (nbt.contains("energy_cap") && nbt.get("energy_cap") instanceof CompoundTag tag)
energy.deserializeNBT(tag);
if (extract.compareTo(BigDecimal.ZERO) == 1) {
BigDecimal received = capability.receiveEnergyOuter(extract, true);
if (nbt.contains("Name") && nbt.get("Name") instanceof StringTag tag)
display_name = Component.Serializer.fromJson(tag.getAsString());
}
void tick() {
if (!hasLevel())
return;
if (energy.getEnergyStored() <= 0)
return;
BlockPos pos = getBlockPos();
List<LivingEntity> entities = getLevel().getEntitiesOfClass(LivingEntity.class, new AABB(pos.getX(), pos.getY(), pos.getZ(), pos.getX() + 1, pos.getY() + 2, pos.getZ() + 1));
for (LivingEntity ent : entities) {
LazyOptional<IAndroidCapability> resolver = ent.getCapability(MatteryCapability.ANDROID);
if (resolver.isPresent()) {
IAndroidCapability capability = resolver.resolve().get();
BigDecimal missing = capability.getMissingPower();
if (missing.compareTo(BigDecimal.ZERO) == 1) {
BigDecimal extract = energy.extractEnergyInner(missing, true);
if (extract.compareTo(BigDecimal.ZERO) == 1) {
BigDecimal received = capability.receiveEnergyOuter(extract, true);
if (received.compareTo(BigDecimal.ZERO) == 1) {
energy.extractEnergyInner(extract, false);
capability.receiveEnergyOuter(extract, false);
if (received.compareTo(BigDecimal.ZERO) == 1) {
tile.energy.extractEnergyInner(extract, false);
capability.receiveEnergyOuter(extract, false);
}
}
}
}
}
}
}
public static <T extends BlockEntity> void tick(Level level, BlockPos blockPos, BlockState blockState, T t) {
if (t instanceof BlockEntityAndroidStation tile) {
tile.tick();
}
}
}

View File

@ -0,0 +1,56 @@
package ru.dbotthepony.mc.otm.block.entity;
import net.minecraft.core.BlockPos;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.nbt.StringTag;
import net.minecraft.network.chat.Component;
import net.minecraft.network.chat.TranslatableComponent;
import net.minecraft.world.MenuProvider;
import net.minecraft.world.entity.player.Inventory;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.inventory.AbstractContainerMenu;
import net.minecraft.world.level.block.entity.BlockEntity;
import net.minecraft.world.level.block.entity.BlockEntityType;
import net.minecraft.world.level.block.state.BlockState;
import javax.annotation.Nullable;
public abstract class BlockEntityMatteryMachine extends BlockEntity implements MenuProvider {
protected Component display_name;
public BlockEntityMatteryMachine(BlockEntityType<?> p_155228_, BlockPos p_155229_, BlockState p_155230_) {
super(p_155228_, p_155229_, p_155230_);
}
public void setDisplayName(Component text) {
display_name = text;
}
@Override
public Component getDisplayName() {
return display_name != null ? display_name : new TranslatableComponent("container.otm.android_station");
}
@Nullable
@Override
abstract public AbstractContainerMenu createMenu(int containerID, Inventory inventory, Player ply);
public boolean canOpenMachine(Player ply) {
return false;
}
@Override
public CompoundTag save(CompoundTag nbt) {
if (display_name != null)
nbt.putString("Name", Component.Serializer.toJson(display_name));
return super.save(nbt);
}
public void load(CompoundTag nbt) {
super.load(nbt);
if (nbt.contains("Name") && nbt.get("Name") instanceof StringTag tag)
display_name = Component.Serializer.fromJson(tag.getAsString());
}
}

View File

@ -0,0 +1,110 @@
package ru.dbotthepony.mc.otm.block.entity;
import net.minecraft.core.BlockPos;
import net.minecraft.core.Direction;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.nbt.StringTag;
import net.minecraft.network.chat.Component;
import net.minecraft.world.SimpleContainer;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.level.block.entity.BlockEntityType;
import net.minecraft.world.level.block.state.BlockState;
import net.minecraftforge.common.capabilities.Capability;
import net.minecraftforge.common.util.LazyOptional;
import net.minecraftforge.energy.CapabilityEnergy;
import net.minecraftforge.energy.IEnergyStorage;
import ru.dbotthepony.mc.otm.capability.IMatteryEnergyStorage;
import ru.dbotthepony.mc.otm.capability.MatteryCapability;
import ru.dbotthepony.mc.otm.capability.MatteryMachineEnergyStorage;
import ru.dbotthepony.mc.otm.container.SimpleSerializableContainer;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import java.math.BigDecimal;
import java.util.Optional;
abstract public class BlockEntityMatteryPoweredMachine extends BlockEntityMatteryMachine {
protected MatteryMachineEnergyStorage energy = null;
protected LazyOptional<MatteryMachineEnergyStorage> energy_resolver = null;
public SimpleSerializableContainer battery_container = new SimpleSerializableContainer(1);
protected void tickBatteryCharge() {
if (energy.getMissingPower().compareTo(BigDecimal.ZERO) <= 0)
return;
BigDecimal demand = energy.getMissingPower();
demand = demand.min(energy.receiveEnergyOuter(demand, true));
for (int i = 0; i < battery_container.getContainerSize() && demand.compareTo(BigDecimal.ZERO) > 0; i++) {
ItemStack stack = battery_container.getItem(i);
if (!stack.isEmpty()) {
Optional<IMatteryEnergyStorage> mattery_storage = stack.getCapability(MatteryCapability.ENERGY).resolve();
if (mattery_storage.isPresent()) {
IMatteryEnergyStorage storage = mattery_storage.get();
BigDecimal drain = storage.extractEnergyOuter(demand, true);
if (!drain.equals(BigDecimal.ZERO)) {
BigDecimal receive = energy.receiveEnergyOuter(drain, true);
storage.extractEnergyOuter(receive, false);
energy.receiveEnergyOuter(receive, false);
demand = demand.subtract(receive, MatteryCapability.ROUND_RULES);
}
} else if (demand.compareTo(BigDecimal.ONE) >= 0) {
Optional<IEnergyStorage> storage = stack.getCapability(CapabilityEnergy.ENERGY).resolve();
if (storage.isPresent()) {
IEnergyStorage energy_fe = storage.get();
BigDecimal drain = MatteryCapability.drainFE(energy_fe, demand, true);
if (!drain.equals(BigDecimal.ZERO)) {
BigDecimal receive = energy.receiveEnergyOuter(drain, true);
MatteryCapability.drainFE(energy_fe, receive, false);
energy.receiveEnergyOuter(receive, false);
demand = demand.subtract(receive, MatteryCapability.ROUND_RULES);
}
}
}
}
}
}
public BlockEntityMatteryPoweredMachine(BlockEntityType<?> p_155228_, BlockPos p_155229_, BlockState p_155230_) {
super(p_155228_, p_155229_, p_155230_);
}
@Nonnull
public <T> LazyOptional<T> getCapability(@Nonnull Capability<T> cap, @Nullable Direction side) {
if ((cap == MatteryCapability.ENERGY || cap == CapabilityEnergy.ENERGY) && energy_resolver != null) {
return energy_resolver.cast();
}
return super.getCapability(cap, side);
}
@Override
public CompoundTag save(CompoundTag nbt) {
nbt.put("energy_cap", energy.serializeNBT());
nbt.put("battery_container", battery_container.serializeNBT());
return super.save(nbt);
}
public void load(CompoundTag nbt) {
if (nbt.contains("energy_cap") && nbt.get("energy_cap") instanceof CompoundTag tag)
energy.deserializeNBT(tag);
if (nbt.contains("battery_container") && nbt.get("battery_container") instanceof CompoundTag tag)
battery_container = SimpleSerializableContainer.of(tag, 1);
super.load(nbt);
}
}

View File

@ -2,6 +2,7 @@ package ru.dbotthepony.mc.otm.capability;
import net.minecraftforge.common.capabilities.Capability;
import net.minecraftforge.common.capabilities.CapabilityInject;
import net.minecraftforge.energy.IEnergyStorage;
import java.math.BigDecimal;
import java.math.MathContext;
@ -21,4 +22,32 @@ public class MatteryCapability {
public static final BigDecimal LONG_MAX_VALUE = new BigDecimal(Long.MAX_VALUE);
public static final BigDecimal LONG_MIN_VALUE = new BigDecimal(Long.MIN_VALUE);
public static BigDecimal drainFE(IEnergyStorage capability, BigDecimal howMuch, boolean simulate) {
if (howMuch.compareTo(BigDecimal.ONE) < 0)
return BigDecimal.ZERO;
int howMuchInt;
if (howMuch.compareTo(INT_MAX_VALUE) > 0)
howMuchInt = Integer.MAX_VALUE;
else
howMuchInt = howMuch.intValue();
return new BigDecimal(capability.extractEnergy(howMuchInt, simulate));
}
public static BigDecimal fillFE(IEnergyStorage capability, BigDecimal howMuch, boolean simulate) {
if (howMuch.compareTo(BigDecimal.ONE) < 0)
return BigDecimal.ZERO;
int howMuchInt;
if (howMuch.compareTo(INT_MAX_VALUE) > 0)
howMuchInt = Integer.MAX_VALUE;
else
howMuchInt = howMuch.intValue();
return new BigDecimal(capability.receiveEnergy(howMuchInt, simulate));
}
}

View File

@ -0,0 +1,47 @@
package ru.dbotthepony.mc.otm.container;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.nbt.ListTag;
import net.minecraft.world.SimpleContainer;
import net.minecraft.world.item.ItemStack;
public class SimpleSerializableContainer extends SimpleContainer {
public SimpleSerializableContainer(int i) {
super(i);
}
public SimpleSerializableContainer(ItemStack... p_19152_) {
super(p_19152_);
}
public CompoundTag serializeNBT() {
CompoundTag tag = new CompoundTag();
tag.putInt("size", getContainerSize());
ListTag list = new ListTag();
tag.put("items", list);
for (int i = 0; i < getContainerSize(); i++)
list.add(getItem(i).serializeNBT());
return tag;
}
public static SimpleSerializableContainer of(CompoundTag tag, int fallback_size) {
if (tag == null)
return new SimpleSerializableContainer(fallback_size);
SimpleSerializableContainer container;
if (tag.contains("size"))
container = new SimpleSerializableContainer(tag.getInt("size"));
else
container = new SimpleSerializableContainer(fallback_size);
if (tag.get("items") instanceof ListTag list)
for (int i = 0; i < Math.min(list.size(), container.getContainerSize()); i++)
if (list.get(i) instanceof CompoundTag get_tag)
container.setItem(i, ItemStack.of(get_tag));
return container;
}
}

View File

@ -17,10 +17,11 @@ import ru.dbotthepony.mc.otm.capability.IAndroidCapability;
import ru.dbotthepony.mc.otm.capability.IMatteryEnergyStorage;
import ru.dbotthepony.mc.otm.capability.MatteryCapability;
import ru.dbotthepony.mc.otm.menu.data.BigDecimalDataContainer;
import ru.dbotthepony.mc.otm.menu.slot.BatterySlot;
import javax.annotation.Nullable;
public class AndroidStationMenu extends AbstractContainerMenu {
public class AndroidStationMenu extends PoweredMachineMenu {
public static class AndroidStationContainer extends SimpleContainer {
public final Player player;
private final IAndroidCapability android;
@ -38,7 +39,7 @@ public class AndroidStationMenu extends AbstractContainerMenu {
}
}
public static class AndroidBatterySlot extends Slot {
public static class AndroidBatterySlot extends BatterySlot {
private final IAndroidCapability android;
public AndroidBatterySlot(AndroidStationContainer container, int index, int x, int y) {
@ -46,12 +47,6 @@ public class AndroidStationMenu extends AbstractContainerMenu {
android = container.android;
}
@Override
public boolean mayPlace(ItemStack stack) {
LazyOptional<IEnergyStorage> capability = stack.getCapability(CapabilityEnergy.ENERGY);
return capability.isPresent() && capability.resolve().get().canExtract();
}
@Override
public void set(ItemStack stack) {
super.set(stack);
@ -59,77 +54,26 @@ public class AndroidStationMenu extends AbstractContainerMenu {
}
}
private BlockEntityAndroidStation tile;
private Inventory inventory;
private Player ply;
private AndroidStationContainer container;
public BigDecimalDataContainer energy;
public BigDecimalDataContainer max_energy;
// Clientside
public AndroidStationMenu(int containerID, Inventory inventory) {
this(containerID, inventory, new AndroidStationContainer(inventory.player), null);
this(containerID, inventory,null);
}
// Serverside
public AndroidStationMenu(int containerID, Inventory inventory, AndroidStationContainer container, @Nullable BlockEntityAndroidStation tile) {
super(OverdriveThatMatters.ANDROID_STATION_MENU_TYPE, containerID);
this.inventory = inventory;
this.container = container;
this.tile = tile;
this.ply = inventory.player;
public AndroidStationMenu(
int containerID,
Inventory inventory,
@Nullable BlockEntityAndroidStation tile
) {
super(
OverdriveThatMatters.ANDROID_STATION_MENU_TYPE,
containerID,
inventory,
tile);
if (tile == null) {
energy = new BigDecimalDataContainer();
max_energy = new BigDecimalDataContainer();
} else {
energy = new BigDecimalDataContainer() {
@Override
protected void updateValue() {
LazyOptional<IMatteryEnergyStorage> capability = tile.getCapability(MatteryCapability.ENERGY);
addSlot(new AndroidBatterySlot(new AndroidStationContainer(inventory.player), 0, 39, 15));
addBatterySlot();
if (capability.isPresent())
setDecimal(capability.resolve().get().getBatteryLevel());
}
};
max_energy = new BigDecimalDataContainer() {
@Override
protected void updateValue() {
LazyOptional<IMatteryEnergyStorage> capability = tile.getCapability(MatteryCapability.ENERGY);
if (capability.isPresent())
setDecimal(capability.resolve().get().getMaxBatteryLevel());
}
};
}
this.addSlot(new AndroidBatterySlot(this.container, 0, 39, 15));
for (int i = 0; i < 3; ++i) {
for (int j = 0; j < 9; ++j) {
this.addSlot(new Slot(inventory, j + i * 9 + 9, 8 + j * 18, 97 + i * 18));
}
}
for (int k = 0; k < 9; ++k) {
this.addSlot(new Slot(inventory, k, 8 + k * 18, 155));
}
this.addDataSlots(energy);
this.addDataSlots(max_energy);
}
@Override
public boolean stillValid(Player player) {
if (tile == null)
return true;
if (player.level.getBlockEntity(tile.getBlockPos()) != tile) {
return false;
}
BlockPos pos = tile.getBlockPos();
return player.distanceToSqr((double)pos.getX() + 0.5D, (double)pos.getY() + 0.5D, (double)pos.getZ() + 0.5D) <= 64.0D;
addInventorySlots();
}
}

View File

@ -0,0 +1,104 @@
package ru.dbotthepony.mc.otm.menu;
import net.minecraft.core.BlockPos;
import net.minecraft.world.Container;
import net.minecraft.world.SimpleContainer;
import net.minecraft.world.entity.player.Inventory;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.inventory.AbstractContainerMenu;
import net.minecraft.world.inventory.MenuType;
import net.minecraft.world.inventory.Slot;
import net.minecraftforge.common.util.LazyOptional;
import ru.dbotthepony.mc.otm.block.entity.BlockEntityMatteryPoweredMachine;
import ru.dbotthepony.mc.otm.capability.IMatteryEnergyStorage;
import ru.dbotthepony.mc.otm.capability.MatteryCapability;
import ru.dbotthepony.mc.otm.menu.data.BigDecimalDataContainer;
import ru.dbotthepony.mc.otm.menu.slot.BatterySlot;
import javax.annotation.Nullable;
abstract public class PoweredMachineMenu extends AbstractContainerMenu {
protected BlockEntityMatteryPoweredMachine tile;
protected Inventory inventory;
protected Player ply;
public BigDecimalDataContainer energy;
public BigDecimalDataContainer max_energy;
protected PoweredMachineMenu(
@Nullable MenuType<?> menuType,
int containerID,
Inventory inventory,
@Nullable BlockEntityMatteryPoweredMachine tile
) {
super(menuType, containerID);
this.tile = tile;
this.inventory = inventory;
this.ply = inventory.player;
if (tile == null) {
energy = new BigDecimalDataContainer();
max_energy = new BigDecimalDataContainer();
} else {
energy = new BigDecimalDataContainer() {
@Override
protected void updateValue() {
LazyOptional<IMatteryEnergyStorage> capability = tile.getCapability(MatteryCapability.ENERGY);
if (capability.isPresent())
setDecimal(capability.resolve().get().getBatteryLevel());
}
};
max_energy = new BigDecimalDataContainer() {
@Override
protected void updateValue() {
LazyOptional<IMatteryEnergyStorage> capability = tile.getCapability(MatteryCapability.ENERGY);
if (capability.isPresent())
setDecimal(capability.resolve().get().getMaxBatteryLevel());
}
};
}
this.addDataSlots(energy);
this.addDataSlots(max_energy);
}
protected void addBatterySlot() {
addBatterySlot(8, 66);
}
protected void addBatterySlot(int x, int y) {
Container battery_container = tile != null ? tile.battery_container : new SimpleContainer(1);
this.addSlot(new BatterySlot(battery_container, 0, x, y));
}
protected void addInventorySlots() {
addInventorySlots(97);
}
protected void addInventorySlots(int offset) {
for (int i = 0; i < 3; ++i) {
for (int j = 0; j < 9; ++j) {
this.addSlot(new Slot(inventory, j + i * 9 + 9, 8 + j * 18, offset + i * 18));
}
}
for (int k = 0; k < 9; ++k) {
this.addSlot(new Slot(inventory, k, 8 + k * 18, offset + 58));
}
}
@Override
public boolean stillValid(Player player) {
if (tile == null)
return true;
if (player.level.getBlockEntity(tile.getBlockPos()) != tile) {
return false;
}
BlockPos pos = tile.getBlockPos();
return player.distanceToSqr((double)pos.getX() + 0.5D, (double)pos.getY() + 0.5D, (double)pos.getZ() + 0.5D) <= 64.0D;
}
}

View File

@ -0,0 +1,20 @@
package ru.dbotthepony.mc.otm.menu.slot;
import net.minecraft.world.Container;
import net.minecraft.world.inventory.Slot;
import net.minecraft.world.item.ItemStack;
import net.minecraftforge.common.util.LazyOptional;
import net.minecraftforge.energy.CapabilityEnergy;
import net.minecraftforge.energy.IEnergyStorage;
public class BatterySlot extends Slot {
public BatterySlot(Container container, int index, int x, int y) {
super(container, index, x, y);
}
@Override
public boolean mayPlace(ItemStack stack) {
LazyOptional<IEnergyStorage> capability = stack.getCapability(CapabilityEnergy.ENERGY);
return capability.isPresent() && capability.resolve().get().canExtract();
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.9 KiB

View File

@ -21,6 +21,11 @@
"target": "BlockEntityTag.energy_cap",
"op": "replace"
},
{
"source": "battery_container",
"target": "BlockEntityTag.battery_container",
"op": "replace"
},
{
"source": "Name",
"target": "BlockEntityTag.Name",