Files
EndlessIDs/src/main/java/com/falsepattern/endlessids/Hooks.java
T
2022-03-17 15:21:30 +01:00

145 lines
5.4 KiB
Java

package com.falsepattern.endlessids;
import com.falsepattern.endlessids.mixin.helpers.IExtendedBlockStorageMixin;
import net.minecraft.init.Blocks;
import net.minecraft.block.Block;
import net.minecraft.nbt.NBTTagCompound;
import java.nio.ShortBuffer;
import java.nio.ByteBuffer;
import net.minecraft.world.chunk.storage.ExtendedBlockStorage;
public class Hooks
{
public Hooks() {
super();
}
public static byte[] getBlockData(final IExtendedBlockStorageMixin ebs) {
final short[] data = ebs.get16B();
final byte[] ret = new byte[data.length * 2];
ByteBuffer.wrap(ret).asShortBuffer().put(data);
return ret;
}
public static void setBlockData(final IExtendedBlockStorageMixin ebs, final byte[] data, final int offset) {
ShortBuffer.wrap(ebs.get16B()).put(ByteBuffer.wrap(data, offset, 8192).asShortBuffer());
}
public static void writeChunkToNbt(final NBTTagCompound nbt, final IExtendedBlockStorageMixin ebs) {
nbt.setByteArray("Blocks16", getBlockData(ebs));
if (IEConfig.postNeidWorldsSupport) {
final short[] data = ebs.get16B();
final byte[] lsbData = new byte[data.length];
byte[] msbData = null;
for (int i = 0; i < data.length; ++i) {
final int id = data[i] & 0xFFFF;
if (id <= 255) {
lsbData[i] = (byte)id;
}
else if (id <= 4095) {
if (msbData == null) {
msbData = new byte[data.length / 2];
}
lsbData[i] = (byte)id;
if (i % 2 == 0) {
final byte[] array = msbData;
final int n = i / 2;
array[n] |= (byte)(id >>> 8 & 0xF);
}
else {
final byte[] array2 = msbData;
final int n2 = i / 2;
array2[n2] |= (byte)(id >>> 4 & 0xF0);
}
}
}
nbt.setByteArray("Blocks", lsbData);
if (msbData != null) {
nbt.setByteArray("Add", msbData);
}
}
}
public static void readChunkFromNbt(final IExtendedBlockStorageMixin ebs, final NBTTagCompound nbt) {
if (nbt.hasKey("Blocks16")) {
setBlockData(ebs, nbt.getByteArray("Blocks16"), 0);
}
else if (nbt.hasKey("Blocks")) {
final short[] out = ebs.get16B();
final byte[] lsbData = nbt.getByteArray("Blocks");
if (nbt.hasKey("Add")) {
final byte[] msbData = nbt.getByteArray("Add");
for (int i = 0; i < out.length; i += 2) {
final byte msPart = msbData[i / 2];
out[i] = (short)((lsbData[i] & 0xFF) | (msPart & 0xF) << 8);
out[i + 1] = (short)((lsbData[i + 1] & 0xFF) | (msPart & 0xF0) << 4);
}
}
else {
for (int j = 0; j < out.length; ++j) {
out[j] = (short)(lsbData[j] & 0xFF);
}
}
}
else {
assert false;
}
}
public static int getBlockId(final IExtendedBlockStorageMixin ebs, final int x, final int y, final int z) {
return ebs.get16B()[y << 8 | z << 4 | x] & 0xFFFF;
}
public static Block getBlock(final IExtendedBlockStorageMixin ebs, final int x, final int y, final int z) {
return Block.getBlockById(getBlockId(ebs, x, y, z));
}
public static void setBlockId(final IExtendedBlockStorageMixin ebs, final int x, final int y, final int z, final int id) {
ebs.get16B()[y << 8 | z << 4 | x] = (short)id;
}
public static short[] create16BArray() {
return new short[4096];
}
public static void removeInvalidBlocksHook(final IExtendedBlockStorageMixin ebs) {
final short[] blkIds = ebs.get16B();
int cntNonEmpty = 0;
int cntTicking = 0;
for (int off = 0; off < blkIds.length; ++off) {
final int id = blkIds[off] & 0xFFFF;
if (id > 0) {
final Block block = (Block)Block.blockRegistry.getObjectById(id);
if (block == null) {
if (IEConfig.removeInvalidBlocks) {
blkIds[off] = 0;
}
}
else if (block != Blocks.air) {
++cntNonEmpty;
if (block.getTickRandomly()) {
++cntTicking;
}
}
}
}
ebs.setBlockRefCount(cntNonEmpty);
ebs.setTickRefCount(cntTicking);
}
public static int getIdFromBlockWithCheck(final Block block, final Block oldBlock) {
final int id = Block.getIdFromBlock(block);
if (IEConfig.catchUnregisteredBlocks && id == -1) {
throw new IllegalArgumentException("Block " + block + " is not registered. <-- Say about this to the author of this mod, or you can try to enable \"RemoveInvalidBlocks\" option in NEID config.");
}
if (id >= 0 && id <= 32767) {
return id;
}
if (id == -1) {
return Block.getIdFromBlock(oldBlock);
}
throw new IllegalArgumentException("id out of range: " + id);
}
}