farewell AbstractGrid

This commit is contained in:
DBotThePony 2022-01-02 12:56:12 +07:00
parent 0ed841ab21
commit 162760c19c
Signed by: DBot
GPG Key ID: DCC23B5715498507

View File

@ -1,147 +0,0 @@
package ru.dbotthepony.mc.otm;
import net.minecraft.MethodsReturnNonnullByDefault;
import net.minecraft.core.BlockPos;
import net.minecraft.core.Direction;
import net.minecraft.core.SectionPos;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.block.entity.BlockEntity;
import net.minecraft.world.level.chunk.LevelChunk;
import net.minecraftforge.common.capabilities.Capability;
import net.minecraftforge.common.util.LazyOptional;
import javax.annotation.ParametersAreNonnullByDefault;
import java.util.HashSet;
import java.util.List;
import java.util.function.Function;
import java.util.function.Supplier;
@MethodsReturnNonnullByDefault
@ParametersAreNonnullByDefault
abstract public class AbstractGrid<T> {
protected final HashSet<T> cells = new HashSet<>();
public final Capability<T> capability;
protected AbstractGrid(Capability<T> capability) {
this.capability = capability;
}
public int size() {
return cells.size();
}
abstract protected void onAdded(T cell);
abstract protected void onRemoved(T cell);
public boolean add(LazyOptional<T> cell) {
if (!cell.isPresent())
return false;
var resolved = cell.resolve();
if (resolved.isPresent()) {
final var value = resolved.get();
if (add(value)) {
cell.addListener((lazy) -> remove(value));
return true;
}
}
return false;
}
public boolean add(T cell) {
if (cells.add(cell)) {
onAdded(cell);
return true;
}
return false;
}
public boolean remove(T cell) {
if (cells.remove(cell)) {
onRemoved(cell);
return true;
}
return false;
}
public void merge(AbstractGrid<T> other) {
if (other == this)
return;
if (size() < other.size()) {
var copy = List.copyOf(cells);
for (var cell : copy) {
remove(cell);
other.add(cell);
}
} else {
var copy = List.copyOf(other.cells);
for (var cell : copy) {
other.remove(cell);
add(cell);
}
}
}
public interface OnNeighbourFunction<T> {
void apply(Level level, BlockPos pos, Direction dir, T other, BlockEntity ent);
}
public static <T> boolean createOrConnectGrid(
T self,
Capability<T> capability,
Level level,
BlockPos pos,
boolean force,
Supplier<AbstractGrid<T>> factory,
Function<T, AbstractGrid<T>> getter,
OnNeighbourFunction<T> neighbour
) {
if (getter.apply(self) != null && !force)
return true;
boolean full_discovery = true;
for (Direction direction : Direction.values()) {
BlockPos offset = pos.offset(direction.getNormal());
// level.getBlockEntity can drink big cup of deadlocks
LevelChunk get_chunk = level.getChunkSource().getChunkNow(SectionPos.blockToSectionCoord(offset.getX()), SectionPos.blockToSectionCoord(offset.getZ()));
if (get_chunk == null) {
full_discovery = false;
continue;
}
BlockEntity get_entity = get_chunk.getBlockEntity(offset);
if (get_entity != null && get_entity.getCapability(capability, direction.getOpposite()).isPresent()) {
final var cell = get_entity.getCapability(capability, direction.getOpposite()).resolve().get();
final var grid = getter.apply(cell);
if (grid != null && grid != getter.apply(self)) {
if (getter.apply(self) == null) {
grid.add(self);
} else {
grid.merge(getter.apply(self));
}
}
neighbour.apply(level, pos, direction, cell, get_entity);
}
}
if (getter.apply(self) == null) {
factory.get().add(self);
}
return full_discovery;
}
}