Added Somewhat functional Transmission between storages
This commit is contained in:
@@ -11,7 +11,7 @@ import org.KaiFlo.SolarCell.Components.EnergyConsumer.IEnergyConsumer;
|
|||||||
import org.KaiFlo.SolarCell.SolarCellPlugin;
|
import org.KaiFlo.SolarCell.SolarCellPlugin;
|
||||||
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
||||||
|
|
||||||
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.LOGGER;
|
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.HyLogger;
|
||||||
|
|
||||||
public class EnergyConsumerComponent implements Component<ChunkStore>, IEnergyConsumer {
|
public class EnergyConsumerComponent implements Component<ChunkStore>, IEnergyConsumer {
|
||||||
public static final BuilderCodec<EnergyConsumerComponent> CODEC = BuilderCodec.builder(EnergyConsumerComponent.class, EnergyConsumerComponent::new)
|
public static final BuilderCodec<EnergyConsumerComponent> CODEC = BuilderCodec.builder(EnergyConsumerComponent.class, EnergyConsumerComponent::new)
|
||||||
@@ -59,7 +59,7 @@ public class EnergyConsumerComponent implements Component<ChunkStore>, IEnergyCo
|
|||||||
try {
|
try {
|
||||||
super.clone();
|
super.clone();
|
||||||
} catch (CloneNotSupportedException e) {
|
} catch (CloneNotSupportedException e) {
|
||||||
LOGGER.atWarning().log("Cloning of " + this.getClass().getName() + " failed.");
|
HyLogger.atWarning().log("Cloning of " + this.getClass().getName() + " failed.");
|
||||||
}
|
}
|
||||||
return new EnergyConsumerComponent().copyFrom(this);
|
return new EnergyConsumerComponent().copyFrom(this);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,10 +11,9 @@ import org.KaiFlo.SolarCell.Components.EnergySource.IEnergySource;
|
|||||||
import org.KaiFlo.SolarCell.SolarCellPlugin;
|
import org.KaiFlo.SolarCell.SolarCellPlugin;
|
||||||
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
||||||
|
|
||||||
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.LOGGER;
|
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.HyLogger;
|
||||||
|
|
||||||
public class EnergySourceComponent implements Component<ChunkStore>, IEnergySource {
|
public class EnergySourceComponent implements Component<ChunkStore>, IEnergySource {
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
public static final BuilderCodec<EnergySourceComponent> CODEC = BuilderCodec.builder(EnergySourceComponent.class, EnergySourceComponent::new)
|
public static final BuilderCodec<EnergySourceComponent> CODEC = BuilderCodec.builder(EnergySourceComponent.class, EnergySourceComponent::new)
|
||||||
.append(new KeyedCodec<>("GeneratesPerTick", Codec.LONG),
|
.append(new KeyedCodec<>("GeneratesPerTick", Codec.LONG),
|
||||||
(component, value) -> component.generatesPerTick = value,
|
(component, value) -> component.generatesPerTick = value,
|
||||||
@@ -27,7 +26,7 @@ public class EnergySourceComponent implements Component<ChunkStore>, IEnergySour
|
|||||||
(component, value) -> component.energyCapacity = value,
|
(component, value) -> component.energyCapacity = value,
|
||||||
(component) -> component.energyCapacity
|
(component) -> component.energyCapacity
|
||||||
)
|
)
|
||||||
.addValidator(Validators.or(Validators.equal(-1L), Validators.greaterThanOrEqual(0L)))
|
.addValidator(Validators.greaterThanOrEqual(-1L))
|
||||||
.documentation("EnergyCapacity defines how long energy can be produced (Set to -1 if endless energy production)")
|
.documentation("EnergyCapacity defines how long energy can be produced (Set to -1 if endless energy production)")
|
||||||
.add()
|
.add()
|
||||||
.build();
|
.build();
|
||||||
@@ -51,7 +50,7 @@ public class EnergySourceComponent implements Component<ChunkStore>, IEnergySour
|
|||||||
try {
|
try {
|
||||||
super.clone();
|
super.clone();
|
||||||
} catch (CloneNotSupportedException e) {
|
} catch (CloneNotSupportedException e) {
|
||||||
LOGGER.atWarning().log("Cloning of " + this.getClass().getName() + " failed.");
|
HyLogger.atWarning().log("Cloning of " + this.getClass().getName() + " failed.");
|
||||||
}
|
}
|
||||||
return new EnergySourceComponent().copyFrom(this);
|
return new EnergySourceComponent().copyFrom(this);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,7 +11,9 @@ import org.KaiFlo.SolarCell.Components.EnergyStorage.IEnergyStorage;
|
|||||||
import org.KaiFlo.SolarCell.SolarCellPlugin;
|
import org.KaiFlo.SolarCell.SolarCellPlugin;
|
||||||
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
||||||
|
|
||||||
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.LOGGER;
|
import java.util.Arrays;
|
||||||
|
|
||||||
|
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.HyLogger;
|
||||||
|
|
||||||
public class EnergyStorageComponent implements Component<ChunkStore>, IEnergyStorage {
|
public class EnergyStorageComponent implements Component<ChunkStore>, IEnergyStorage {
|
||||||
public static final BuilderCodec<EnergyStorageComponent> CODEC = BuilderCodec.builder(EnergyStorageComponent.class, EnergyStorageComponent::new)
|
public static final BuilderCodec<EnergyStorageComponent> CODEC = BuilderCodec.builder(EnergyStorageComponent.class, EnergyStorageComponent::new)
|
||||||
@@ -100,6 +102,12 @@ public class EnergyStorageComponent implements Component<ChunkStore>, IEnergySto
|
|||||||
public long extractEnergy(long requiredEnergy) {
|
public long extractEnergy(long requiredEnergy) {
|
||||||
var extractedEnergy = Math.min(currentEnergyAmount, Math.min(requiredEnergy, extractEnergyPerTick));
|
var extractedEnergy = Math.min(currentEnergyAmount, Math.min(requiredEnergy, extractEnergyPerTick));
|
||||||
currentEnergyAmount -= extractedEnergy;
|
currentEnergyAmount -= extractedEnergy;
|
||||||
|
if (extractedEnergy >=1000){
|
||||||
|
HyLogger.atInfo().log("Extracted Energy: " + extractedEnergy + " now at " + currentEnergyAmount);
|
||||||
|
for (StackTraceElement element : Arrays.stream(Thread.currentThread().getStackTrace()).limit(7).toList()) {
|
||||||
|
HyLogger.atInfo().log(String.valueOf(element));
|
||||||
|
}
|
||||||
|
}
|
||||||
return extractedEnergy;
|
return extractedEnergy;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -107,6 +115,7 @@ public class EnergyStorageComponent implements Component<ChunkStore>, IEnergySto
|
|||||||
public long receiveEnergy(long inputEnergy) {
|
public long receiveEnergy(long inputEnergy) {
|
||||||
var receivedEnergy = Math.min(maxCapacity - currentEnergyAmount, Math.min(inputEnergy, receiveEnergyPerTick));
|
var receivedEnergy = Math.min(maxCapacity - currentEnergyAmount, Math.min(inputEnergy, receiveEnergyPerTick));
|
||||||
currentEnergyAmount += receivedEnergy;
|
currentEnergyAmount += receivedEnergy;
|
||||||
|
// HyLogger.atInfo().log("Received Energy: " + receivedEnergy + " now at " + currentEnergyAmount);
|
||||||
return receivedEnergy;
|
return receivedEnergy;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -124,7 +133,7 @@ public class EnergyStorageComponent implements Component<ChunkStore>, IEnergySto
|
|||||||
try {
|
try {
|
||||||
super.clone();
|
super.clone();
|
||||||
} catch (CloneNotSupportedException e) {
|
} catch (CloneNotSupportedException e) {
|
||||||
LOGGER.atWarning().log("Cloning of " + this.getClass().getName() + " failed.");
|
HyLogger.atWarning().log("Cloning of " + this.getClass().getName() + " failed.");
|
||||||
}
|
}
|
||||||
return new EnergyStorageComponent().copyFrom(this);
|
return new EnergyStorageComponent().copyFrom(this);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,12 +5,14 @@ import com.hypixel.hytale.component.Ref;
|
|||||||
import com.hypixel.hytale.logger.HytaleLogger;
|
import com.hypixel.hytale.logger.HytaleLogger;
|
||||||
import com.hypixel.hytale.math.util.ChunkUtil;
|
import com.hypixel.hytale.math.util.ChunkUtil;
|
||||||
import com.hypixel.hytale.server.core.modules.block.BlockModule;
|
import com.hypixel.hytale.server.core.modules.block.BlockModule;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.World;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.chunk.BlockComponentChunk;
|
||||||
import com.hypixel.hytale.server.core.universe.world.chunk.WorldChunk;
|
import com.hypixel.hytale.server.core.universe.world.chunk.WorldChunk;
|
||||||
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
||||||
import org.checkerframework.checker.nullness.compatqual.NonNullDecl;
|
import org.checkerframework.checker.nullness.compatqual.NonNullDecl;
|
||||||
|
|
||||||
public class BlockHelper {
|
public class BlockHelper {
|
||||||
public static final HytaleLogger LOGGER = HytaleLogger.getLogger();
|
public static final HytaleLogger HyLogger = HytaleLogger.getLogger();
|
||||||
|
|
||||||
public static void executeForCubeAround(int x, int y, int z, int size, boolean own, Callback callback) {
|
public static void executeForCubeAround(int x, int y, int z, int size, boolean own, Callback callback) {
|
||||||
for (int xOffset = 0; xOffset < size; xOffset++) {
|
for (int xOffset = 0; xOffset < size; xOffset++) {
|
||||||
@@ -21,17 +23,67 @@ public class BlockHelper {
|
|||||||
var zPos = (zOffset - size / 2) + z;
|
var zPos = (zOffset - size / 2) + z;
|
||||||
if (!(xPos == x && yPos == y && zPos == z)) {
|
if (!(xPos == x && yPos == y && zPos == z)) {
|
||||||
callback.accept(xPos, yPos, zPos);
|
callback.accept(xPos, yPos, zPos);
|
||||||
}
|
} else if (own) {
|
||||||
else if (own) {
|
|
||||||
callback.accept(xPos, yPos, zPos);
|
callback.accept(xPos, yPos, zPos);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static void executeForCubeAroundChunkSafe(
|
||||||
|
int centerX, int centerY, int centerZ,
|
||||||
|
int size,
|
||||||
|
boolean includeCenter,
|
||||||
|
World world,
|
||||||
|
CommandBuffer<ChunkStore> commandBuffer,
|
||||||
|
ChunkSafeCallback chunkSafeCallback
|
||||||
|
) {
|
||||||
|
int halfSize = size / 2;
|
||||||
|
|
||||||
|
for (int xOffset = -halfSize; xOffset <= halfSize; xOffset++) {
|
||||||
|
for (int yOffset = -halfSize; yOffset <= halfSize; yOffset++) {
|
||||||
|
for (int zOffset = -halfSize; zOffset <= halfSize; zOffset++) {
|
||||||
|
|
||||||
|
int xPos = centerX + xOffset;
|
||||||
|
int yPos = centerY + yOffset;
|
||||||
|
int zPos = centerZ + zOffset;
|
||||||
|
|
||||||
|
if (!includeCenter && xPos == centerX && yPos == centerY && zPos == centerZ) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
int chunkX = Math.floorDiv(xPos, 32);
|
||||||
|
int chunkZ = Math.floorDiv(zPos, 32);
|
||||||
|
|
||||||
|
int localX = Math.floorMod(xPos, 32);
|
||||||
|
int localZ = Math.floorMod(zPos, 32);
|
||||||
|
|
||||||
|
WorldChunk targetChunk = world.getChunk(ChunkUtil.indexChunk(chunkX, chunkZ));
|
||||||
|
if (targetChunk == null) continue;
|
||||||
|
|
||||||
|
var blockComponentChunk = commandBuffer.getComponent(
|
||||||
|
targetChunk.getReference(),
|
||||||
|
BlockComponentChunk.getComponentType()
|
||||||
|
);
|
||||||
|
if (blockComponentChunk == null) continue;
|
||||||
|
|
||||||
|
int index = ChunkUtil.indexBlockInColumn(localX, yPos, localZ);
|
||||||
|
var targetRef = blockComponentChunk.getEntityReference(index);
|
||||||
|
if (targetRef == null) continue;
|
||||||
|
|
||||||
|
chunkSafeCallback.accept(xPos, yPos, zPos, targetRef, blockComponentChunk, targetChunk);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
public interface Callback {
|
public interface Callback {
|
||||||
void accept(int x, int y, int z);
|
void accept(int x, int y, int z);
|
||||||
}
|
}
|
||||||
|
public interface ChunkSafeCallback {
|
||||||
|
|
||||||
|
void accept(int x, int y, int z, Ref<ChunkStore> targetRef, BlockComponentChunk blockComponentChunk, WorldChunk targetChunk);
|
||||||
|
}
|
||||||
|
|
||||||
public static void setBlockRefTicking(Ref<ChunkStore> blockRef, @NonNullDecl CommandBuffer<ChunkStore> commandBuffer) {
|
public static void setBlockRefTicking(Ref<ChunkStore> blockRef, @NonNullDecl CommandBuffer<ChunkStore> commandBuffer) {
|
||||||
BlockModule.BlockStateInfo blockInfo = commandBuffer.getComponent(blockRef, BlockModule.BlockStateInfo.getComponentType());
|
BlockModule.BlockStateInfo blockInfo = commandBuffer.getComponent(blockRef, BlockModule.BlockStateInfo.getComponentType());
|
||||||
@@ -45,7 +97,6 @@ public class BlockHelper {
|
|||||||
int z = ChunkUtil.zFromBlockInColumn(blockInfo.getIndex());
|
int z = ChunkUtil.zFromBlockInColumn(blockInfo.getIndex());
|
||||||
|
|
||||||
worldChunk.setTicking(x, y, z, true);
|
worldChunk.setTicking(x, y, z, true);
|
||||||
HytaleLogger.getLogger().atInfo().log(String.valueOf(worldChunk.isTicking(x, y, z)));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,16 @@
|
|||||||
|
package org.KaiFlo.SolarCell.Helpers;
|
||||||
|
|
||||||
|
import com.hypixel.hytale.component.Component;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Optional;
|
||||||
|
|
||||||
|
public class ComponentHelper {
|
||||||
|
public static<T> Optional<T> getComponentOfType(List<Component<ChunkStore>> components, Class<T> type){
|
||||||
|
return components.stream()
|
||||||
|
.filter(x -> x.getClass() == type)
|
||||||
|
.map(type::cast)
|
||||||
|
.findFirst();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -10,9 +10,13 @@ import org.KaiFlo.SolarCell.Components.EnergyConsumer.Implementations.EnergyCons
|
|||||||
import org.KaiFlo.SolarCell.Components.EnergySource.Implementations.EnergySourceComponent;
|
import org.KaiFlo.SolarCell.Components.EnergySource.Implementations.EnergySourceComponent;
|
||||||
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
||||||
import org.KaiFlo.SolarCell.Systems.EnergySource.EnergySourceInitializerSystem;
|
import org.KaiFlo.SolarCell.Systems.EnergySource.EnergySourceInitializerSystem;
|
||||||
|
import org.KaiFlo.SolarCell.Systems.EnergySource.TickingImplementations.SolarCellSourceTicking;
|
||||||
|
import org.KaiFlo.SolarCell.Systems.EnergyStorage.EnergyStorageInitializerSystem;
|
||||||
|
import org.KaiFlo.SolarCell.Systems.EnergyStorage.TickingImplementations.BatteryStorageTicking;
|
||||||
import org.KaiFlo.SolarCell.Systems.EnergyTickingSystem;
|
import org.KaiFlo.SolarCell.Systems.EnergyTickingSystem;
|
||||||
|
|
||||||
import javax.annotation.Nonnull;
|
import javax.annotation.Nonnull;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
public class SolarCellPlugin extends JavaPlugin {
|
public class SolarCellPlugin extends JavaPlugin {
|
||||||
|
|
||||||
@@ -44,8 +48,13 @@ public class SolarCellPlugin extends JavaPlugin {
|
|||||||
|
|
||||||
this.getCommandRegistry().registerCommand(new ExampleCommand(this.getName(), this.getManifest().getVersion().toString()));
|
this.getCommandRegistry().registerCommand(new ExampleCommand(this.getName(), this.getManifest().getVersion().toString()));
|
||||||
|
|
||||||
|
var energyTickingSystem = new EnergyTickingSystem()
|
||||||
|
.withTickingSystemForComponentTypes(List.of(energyStorageComponentType), new BatteryStorageTicking())
|
||||||
|
.withTickingSystemForComponentTypes(List.of(energySourceComponentType,energyStorageComponentType), new SolarCellSourceTicking());
|
||||||
|
|
||||||
this.getChunkStoreRegistry().registerSystem(new EnergySourceInitializerSystem());
|
this.getChunkStoreRegistry().registerSystem(new EnergySourceInitializerSystem());
|
||||||
this.getChunkStoreRegistry().registerSystem(new EnergyTickingSystem());
|
this.getChunkStoreRegistry().registerSystem(new EnergyStorageInitializerSystem());
|
||||||
|
this.getChunkStoreRegistry().registerSystem(energyTickingSystem);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,12 +0,0 @@
|
|||||||
package org.KaiFlo.SolarCell.Systems.EnergySource;
|
|
||||||
|
|
||||||
import com.hypixel.hytale.component.CommandBuffer;
|
|
||||||
import com.hypixel.hytale.protocol.Vector3i;
|
|
||||||
import com.hypixel.hytale.server.core.universe.world.chunk.BlockComponentChunk;
|
|
||||||
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
|
||||||
import org.KaiFlo.SolarCell.Components.EnergySource.Implementations.EnergySourceComponent;
|
|
||||||
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
|
||||||
|
|
||||||
public interface IEnergySourceTicking{
|
|
||||||
void accept (EnergySourceComponent thisEnergySource, EnergyStorageComponent thisEnergyStorage, Vector3i globalPosition, BlockComponentChunk blockComponentChunk, CommandBuffer<ChunkStore> commandBuffer);
|
|
||||||
}
|
|
||||||
@@ -1,33 +0,0 @@
|
|||||||
package org.KaiFlo.SolarCell.Systems.EnergySource;
|
|
||||||
|
|
||||||
import com.hypixel.hytale.component.CommandBuffer;
|
|
||||||
import com.hypixel.hytale.math.util.ChunkUtil;
|
|
||||||
import com.hypixel.hytale.protocol.Vector3i;
|
|
||||||
import com.hypixel.hytale.server.core.universe.world.chunk.BlockComponentChunk;
|
|
||||||
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
|
||||||
import org.KaiFlo.SolarCell.Components.EnergySource.Implementations.EnergySourceComponent;
|
|
||||||
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
|
||||||
import org.KaiFlo.SolarCell.Helpers.BlockHelper;
|
|
||||||
|
|
||||||
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.LOGGER;
|
|
||||||
|
|
||||||
public class SolarCellSourceTicking implements IEnergySourceTicking{
|
|
||||||
@Override
|
|
||||||
public void accept(EnergySourceComponent thisEnergySource, EnergyStorageComponent thisEnergyStorage, Vector3i globalPosition, BlockComponentChunk blockComponentChunk, CommandBuffer<ChunkStore> commandBuffer){
|
|
||||||
|
|
||||||
BlockHelper.executeForCubeAround(globalPosition.x, globalPosition.y, globalPosition.z, 5, false, (x, y, z) -> {
|
|
||||||
var index = ChunkUtil.indexBlockInColumn(x, y, z);
|
|
||||||
var targetRef = blockComponentChunk.getEntityReference(index);
|
|
||||||
if (targetRef == null) return;
|
|
||||||
var targetEnergySource = commandBuffer.getComponent(targetRef, EnergySourceComponent.getComponentType());
|
|
||||||
var targetEnergyStorage = commandBuffer.getComponent(targetRef, EnergyStorageComponent.getComponentType());
|
|
||||||
if (targetEnergySource == null || targetEnergyStorage == null) return;
|
|
||||||
|
|
||||||
var energy = targetEnergyStorage.extractEnergy(targetEnergySource.getGeneratesPerTick());
|
|
||||||
var inserted = thisEnergyStorage.receiveEnergy(energy);
|
|
||||||
LOGGER.atInfo().log("Inserted " + inserted + "/" + energy + " |" + targetEnergyStorage.getCurrentEnergyAmount() + "| into storage" +
|
|
||||||
" at Block " + globalPosition.x + ", " + globalPosition.y + ", " + globalPosition.z + ", " +
|
|
||||||
thisEnergyStorage.getCurrentEnergyAmount() + "/" + thisEnergyStorage.getMaxCapacity());
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,33 @@
|
|||||||
|
package org.KaiFlo.SolarCell.Systems.EnergySource.TickingImplementations;
|
||||||
|
|
||||||
|
import com.hypixel.hytale.component.Archetype;
|
||||||
|
import com.hypixel.hytale.component.CommandBuffer;
|
||||||
|
import com.hypixel.hytale.component.Component;
|
||||||
|
import com.hypixel.hytale.protocol.Vector3i;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.World;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.chunk.BlockComponentChunk;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
||||||
|
import org.KaiFlo.SolarCell.Components.EnergySource.Implementations.EnergySourceComponent;
|
||||||
|
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
||||||
|
import org.KaiFlo.SolarCell.Systems.ITickingSystem;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.HyLogger;
|
||||||
|
import static org.KaiFlo.SolarCell.Helpers.ComponentHelper.getComponentOfType;
|
||||||
|
|
||||||
|
public class SolarCellSourceTicking implements ITickingSystem {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void accept(List<Component<ChunkStore>> foundComponents, Archetype<ChunkStore> archetype, Vector3i globalPosition, BlockComponentChunk blockComponentChunk, CommandBuffer<ChunkStore> commandBuffer, World world) {
|
||||||
|
var energyStorage = getComponentOfType(foundComponents, EnergyStorageComponent.class).orElse(null);
|
||||||
|
if (energyStorage == null) return;
|
||||||
|
var energySource = getComponentOfType(foundComponents, EnergySourceComponent.class).orElse(null);
|
||||||
|
if (energySource == null) return;
|
||||||
|
var received = energyStorage.receiveEnergy(energySource.getGeneratesPerTick());
|
||||||
|
if (received!= 0){
|
||||||
|
HyLogger.atInfo().log("Block at " + globalPosition.x+", "+ globalPosition.y+", " +globalPosition.z+" received " + received + " Energy, now at "+energyStorage.getCurrentEnergyAmount());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,31 @@
|
|||||||
|
package org.KaiFlo.SolarCell.Systems.EnergyStorage;
|
||||||
|
|
||||||
|
import com.hypixel.hytale.component.*;
|
||||||
|
import com.hypixel.hytale.component.query.Query;
|
||||||
|
import com.hypixel.hytale.component.system.RefSystem;
|
||||||
|
import com.hypixel.hytale.server.core.modules.block.BlockModule;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
||||||
|
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
||||||
|
import org.checkerframework.checker.nullness.compatqual.NonNullDecl;
|
||||||
|
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
||||||
|
|
||||||
|
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.setBlockRefTicking;
|
||||||
|
|
||||||
|
public class EnergyStorageInitializerSystem extends RefSystem<ChunkStore> {
|
||||||
|
@Override
|
||||||
|
public void onEntityAdded(@NonNullDecl Ref<ChunkStore> ref, @NonNullDecl AddReason addReason, @NonNullDecl Store<ChunkStore> store, @NonNullDecl CommandBuffer<ChunkStore> commandBuffer) {
|
||||||
|
setBlockRefTicking(ref, commandBuffer);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onEntityRemove(@NonNullDecl Ref ref, @NonNullDecl RemoveReason removeReason, @NonNullDecl Store store, @NonNullDecl CommandBuffer commandBuffer) {
|
||||||
|
//Nothing to do yet
|
||||||
|
}
|
||||||
|
|
||||||
|
@NullableDecl
|
||||||
|
@Override
|
||||||
|
public Query<ChunkStore> getQuery() {
|
||||||
|
return Query.and(EnergyStorageComponent.getComponentType(), BlockModule.BlockStateInfo.getComponentType());
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,54 @@
|
|||||||
|
package org.KaiFlo.SolarCell.Systems.EnergyStorage.TickingImplementations;
|
||||||
|
|
||||||
|
import com.hypixel.hytale.component.Archetype;
|
||||||
|
import com.hypixel.hytale.component.CommandBuffer;
|
||||||
|
import com.hypixel.hytale.component.Component;
|
||||||
|
import com.hypixel.hytale.protocol.Vector3i;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.World;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.chunk.BlockComponentChunk;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
||||||
|
import org.KaiFlo.SolarCell.Components.EnergySource.Implementations.EnergySourceComponent;
|
||||||
|
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
||||||
|
import org.KaiFlo.SolarCell.Systems.ITickingSystem;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.HyLogger;
|
||||||
|
import static org.KaiFlo.SolarCell.Helpers.BlockHelper.executeForCubeAroundChunkSafe;
|
||||||
|
import static org.KaiFlo.SolarCell.Helpers.ComponentHelper.getComponentOfType;
|
||||||
|
|
||||||
|
public class BatteryStorageTicking implements ITickingSystem {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void accept(List<Component<ChunkStore>> foundComponents, Archetype<ChunkStore> archetype, Vector3i globalPosition, BlockComponentChunk blockComponentChunk, CommandBuffer<ChunkStore> commandBuffer, World world) {
|
||||||
|
var energyStorage = getComponentOfType(foundComponents, EnergyStorageComponent.class).orElse(null);
|
||||||
|
if (energyStorage == null) return;
|
||||||
|
var energySourceComponent = getComponentOfType(foundComponents, EnergySourceComponent.class).orElse(null);
|
||||||
|
if (energySourceComponent != null) return;
|
||||||
|
if (energyStorage.getCurrentEnergyAmount() >= energyStorage.getMaxCapacity()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
executeForCubeAroundChunkSafe(globalPosition.x, globalPosition.y, globalPosition.z, 5, false, world, commandBuffer,
|
||||||
|
(x, y, z, targetRef, blockCompChunk, targetChunk) -> {
|
||||||
|
|
||||||
|
var targetEnergyStorage = commandBuffer.getComponent(targetRef, EnergyStorageComponent.getComponentType());
|
||||||
|
if (targetEnergyStorage == null) return;
|
||||||
|
if (targetEnergyStorage.getCurrentEnergyAmount() < energyStorage.getCurrentEnergyAmount()) return;
|
||||||
|
|
||||||
|
long energy = targetEnergyStorage.extractEnergy(Math.min(energyStorage.getMaxCapacity()-energyStorage.getCurrentEnergyAmount(),
|
||||||
|
Math.min(
|
||||||
|
targetEnergyStorage.getExtractEnergyPerTick(),
|
||||||
|
energyStorage.getReceiveEnergyPerTick()
|
||||||
|
)));
|
||||||
|
long inserted = energyStorage.receiveEnergy(energy);
|
||||||
|
|
||||||
|
if (inserted != 0 && energyStorage.getCurrentEnergyAmount() != energyStorage.getMaxCapacity()) {
|
||||||
|
HyLogger.atInfo().log("Inserted " + inserted + "/" + energy +
|
||||||
|
" |" + targetEnergyStorage.getCurrentEnergyAmount() + "| into storage" +
|
||||||
|
" at Block " + globalPosition.x + ", " + globalPosition.y + ", " + globalPosition.z + ", " +
|
||||||
|
energyStorage.getCurrentEnergyAmount() + "/" + energyStorage.getMaxCapacity());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,8 +1,6 @@
|
|||||||
package org.KaiFlo.SolarCell.Systems;
|
package org.KaiFlo.SolarCell.Systems;
|
||||||
|
|
||||||
import com.hypixel.hytale.component.ArchetypeChunk;
|
import com.hypixel.hytale.component.*;
|
||||||
import com.hypixel.hytale.component.CommandBuffer;
|
|
||||||
import com.hypixel.hytale.component.Store;
|
|
||||||
import com.hypixel.hytale.component.query.Query;
|
import com.hypixel.hytale.component.query.Query;
|
||||||
import com.hypixel.hytale.component.system.tick.EntityTickingSystem;
|
import com.hypixel.hytale.component.system.tick.EntityTickingSystem;
|
||||||
import com.hypixel.hytale.math.util.ChunkUtil;
|
import com.hypixel.hytale.math.util.ChunkUtil;
|
||||||
@@ -13,33 +11,34 @@ import com.hypixel.hytale.server.core.universe.world.chunk.WorldChunk;
|
|||||||
import com.hypixel.hytale.server.core.universe.world.chunk.section.BlockSection;
|
import com.hypixel.hytale.server.core.universe.world.chunk.section.BlockSection;
|
||||||
import com.hypixel.hytale.server.core.universe.world.chunk.section.ChunkSection;
|
import com.hypixel.hytale.server.core.universe.world.chunk.section.ChunkSection;
|
||||||
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
||||||
import org.KaiFlo.SolarCell.Components.EnergyConsumer.Implementations.EnergyConsumerComponent;
|
|
||||||
import org.KaiFlo.SolarCell.Components.EnergySource.Implementations.EnergySourceComponent;
|
|
||||||
import org.KaiFlo.SolarCell.Components.EnergyStorage.Implementations.EnergyStorageComponent;
|
|
||||||
import org.KaiFlo.SolarCell.Systems.EnergySource.IEnergySourceTicking;
|
|
||||||
import org.KaiFlo.SolarCell.Systems.EnergySource.SolarCellSourceTicking;
|
|
||||||
import org.checkerframework.checker.nullness.compatqual.NonNullDecl;
|
import org.checkerframework.checker.nullness.compatqual.NonNullDecl;
|
||||||
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
import org.checkerframework.checker.nullness.compatqual.NullableDecl;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.*;
|
||||||
|
import java.util.concurrent.atomic.AtomicBoolean;
|
||||||
|
|
||||||
public class EnergyTickingSystem extends EntityTickingSystem<ChunkStore> {
|
public class EnergyTickingSystem extends EntityTickingSystem<ChunkStore> {
|
||||||
private final List<IEnergySourceTicking> energySourceTicking = List.of(new SolarCellSourceTicking());
|
|
||||||
|
private final Map<List<ComponentType<ChunkStore, ?>>, ITickingSystem> componentsToTickingSystem = new HashMap<>();
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void tick(float v, int i, @NonNullDecl ArchetypeChunk<ChunkStore> archetypeChunk, @NonNullDecl Store<ChunkStore> store, @NonNullDecl CommandBuffer<ChunkStore> commandBuffer) {
|
public void tick(float v, int archetypeIndex, @NonNullDecl ArchetypeChunk<ChunkStore> archetypeChunk, @NonNullDecl Store<ChunkStore> store, @NonNullDecl CommandBuffer<ChunkStore> commandBuffer) {
|
||||||
var blockSection = archetypeChunk.getComponent(i, BlockSection.getComponentType());
|
|
||||||
|
var blockSection = archetypeChunk.getComponent(archetypeIndex, BlockSection.getComponentType());
|
||||||
if (blockSection == null || blockSection.getTickingBlocksCount() != 0) return;
|
if (blockSection == null || blockSection.getTickingBlocksCount() != 0) return;
|
||||||
|
|
||||||
var chunkSection = archetypeChunk.getComponent(i, ChunkSection.getComponentType());
|
var chunkSection = archetypeChunk.getComponent(archetypeIndex, ChunkSection.getComponentType());
|
||||||
if (chunkSection == null) return;
|
if (chunkSection == null) return;
|
||||||
|
|
||||||
var blockComponentChunk = commandBuffer.getComponent(chunkSection.getChunkColumnReference(), BlockComponentChunk.getComponentType());
|
var blockComponentChunk = commandBuffer.getComponent(chunkSection.getChunkColumnReference(), BlockComponentChunk.getComponentType());
|
||||||
var worldChunk = commandBuffer.getComponent(chunkSection.getChunkColumnReference(), WorldChunk.getComponentType());
|
var worldChunk = commandBuffer.getComponent(chunkSection.getChunkColumnReference(), WorldChunk.getComponentType());
|
||||||
if (blockComponentChunk == null || worldChunk == null) return;
|
if (blockComponentChunk == null || worldChunk == null) return;
|
||||||
|
|
||||||
blockSection.forEachTicking(blockComponentChunk, commandBuffer, chunkSection.getY(),
|
var entrySet = componentsToTickingSystem.entrySet();
|
||||||
(blockCompChunk, _, localX, localY, localZ, _) -> {
|
var foundComponentTypes = new ArrayList<ComponentType<ChunkStore, ?>>();
|
||||||
|
|
||||||
|
blockSection.forEachTicking(blockComponentChunk, commandBuffer, chunkSection.getY(), (blockCompChunk, _, localX, localY, localZ, _) -> {
|
||||||
var blockRef = blockCompChunk.getEntityReference(ChunkUtil.indexBlockInColumn(localX, localY, localZ));
|
var blockRef = blockCompChunk.getEntityReference(ChunkUtil.indexBlockInColumn(localX, localY, localZ));
|
||||||
if (blockRef == null) return BlockTickStrategy.IGNORED;
|
if (blockRef == null) return BlockTickStrategy.IGNORED;
|
||||||
|
|
||||||
@@ -47,17 +46,26 @@ public class EnergyTickingSystem extends EntityTickingSystem<ChunkStore> {
|
|||||||
int globalZ = localZ + (worldChunk.getZ() * 32);
|
int globalZ = localZ + (worldChunk.getZ() * 32);
|
||||||
var globalPosition = new Vector3i(globalX, localY, globalZ);
|
var globalPosition = new Vector3i(globalX, localY, globalZ);
|
||||||
|
|
||||||
var energySourceComponent = commandBuffer.getComponent(blockRef, EnergySourceComponent.getComponentType());
|
|
||||||
var energyConsumerComponent = commandBuffer.getComponent(blockRef, EnergyConsumerComponent.getComponentType());
|
|
||||||
var energyStorageComponent = commandBuffer.getComponent(blockRef, EnergyStorageComponent.getComponentType());
|
|
||||||
|
|
||||||
if (energySourceComponent != null && energyStorageComponent != null){
|
var archetype = commandBuffer.getArchetype(blockRef);
|
||||||
energySourceTicking.forEach(energySourceTicking -> energySourceTicking.accept(energySourceComponent, energyStorageComponent,globalPosition,blockCompChunk,commandBuffer));
|
|
||||||
return BlockTickStrategy.CONTINUE;
|
foundComponentTypes.clear();
|
||||||
|
var foundComponents = new ArrayList<Component<ChunkStore>>();
|
||||||
|
for (int i = 0; i < archetype.length(); i++) {
|
||||||
|
var type = archetype.get(i);
|
||||||
|
if (type == null) continue;
|
||||||
|
foundComponentTypes.add(type);
|
||||||
|
foundComponents.add(commandBuffer.getComponent(blockRef, type));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
AtomicBoolean hasAny = new AtomicBoolean(false);
|
||||||
return BlockTickStrategy.IGNORED;
|
entrySet.stream()
|
||||||
|
.filter(entry -> foundComponentTypes.containsAll(entry.getKey())).map(Map.Entry::getValue)
|
||||||
|
.forEach(tickingSystem -> {
|
||||||
|
hasAny.set(true);
|
||||||
|
tickingSystem.accept(foundComponents, archetype, globalPosition, blockCompChunk, commandBuffer, worldChunk.getWorld());
|
||||||
|
});
|
||||||
|
return hasAny.get() ? BlockTickStrategy.CONTINUE : BlockTickStrategy.IGNORED;
|
||||||
});
|
});
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -67,4 +75,9 @@ public class EnergyTickingSystem extends EntityTickingSystem<ChunkStore> {
|
|||||||
public Query<ChunkStore> getQuery() {
|
public Query<ChunkStore> getQuery() {
|
||||||
return Query.and(BlockSection.getComponentType(), ChunkSection.getComponentType());
|
return Query.and(BlockSection.getComponentType(), ChunkSection.getComponentType());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public EnergyTickingSystem withTickingSystemForComponentTypes(List<ComponentType<ChunkStore, ?>> componentTypes, ITickingSystem tickingSystem) {
|
||||||
|
componentsToTickingSystem.put(componentTypes, tickingSystem);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,16 @@
|
|||||||
|
package org.KaiFlo.SolarCell.Systems;
|
||||||
|
|
||||||
|
import com.hypixel.hytale.component.Archetype;
|
||||||
|
import com.hypixel.hytale.component.CommandBuffer;
|
||||||
|
import com.hypixel.hytale.component.Component;
|
||||||
|
import com.hypixel.hytale.protocol.Vector3i;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.World;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.chunk.BlockComponentChunk;
|
||||||
|
import com.hypixel.hytale.server.core.universe.world.storage.ChunkStore;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
public interface ITickingSystem {
|
||||||
|
|
||||||
|
void accept(List<Component<ChunkStore>> foundComponents, Archetype<ChunkStore> archetype, Vector3i globalPosition, BlockComponentChunk blockComponentChunk, CommandBuffer<ChunkStore> commandBuffer, World world);
|
||||||
|
}
|
||||||
@@ -18,11 +18,11 @@
|
|||||||
"BlockType": {
|
"BlockType": {
|
||||||
"BlockEntity": {
|
"BlockEntity": {
|
||||||
"Components": {
|
"Components": {
|
||||||
"EnergyStorageComponent": {
|
"EnergyStorage": {
|
||||||
"EnergyStored": 5,
|
"MaxCapacity": 10000,
|
||||||
"MaxEnergy": 80000,
|
"ExtractEnergyPerTick": 1000,
|
||||||
"MaxReceive": 1000,
|
"ReceiveEnergyPerTick": 1000,
|
||||||
"MaxExtract": 1000
|
"CurrentEnergyAmount": 100
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -18,12 +18,15 @@
|
|||||||
"BlockType": {
|
"BlockType": {
|
||||||
"BlockEntity": {
|
"BlockEntity": {
|
||||||
"Components": {
|
"Components": {
|
||||||
"SolarCell": {},
|
"EnergyStorage": {
|
||||||
"EnergyStorageComponent": {
|
"MaxCapacity": 10000,
|
||||||
"EnergyStored": 5,
|
"ExtractEnergyPerTick": 100,
|
||||||
"MaxEnergy": 80000,
|
"ReceiveEnergyPerTick": 1000,
|
||||||
"MaxReceive": 1000,
|
"CurrentEnergyAmount": 0
|
||||||
"MaxExtract": 1000
|
},
|
||||||
|
"EnergySource": {
|
||||||
|
"EnergyCapacity": -1,
|
||||||
|
"GeneratesPerTick": 1000
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|||||||
Reference in New Issue
Block a user