diff --git a/worldedit-bukkit/build.gradle b/worldedit-bukkit/build.gradle
index f194b7fd5..be0cc651e 100644
--- a/worldedit-bukkit/build.gradle
+++ b/worldedit-bukkit/build.gradle
@@ -18,31 +18,39 @@ configurations.all { Configuration it ->
}
}
+task downloadJarsToLibs(){
+ def f = new File('lib/spigot-1.14.jar')
+ if (!f.exists()) {
+ new URL('https://ci.athion.net/job/BuildTools/lastSuccessfulBuild/artifact/spigot-1.14.jar').withInputStream{ i -> f.withOutputStream{ it << i }}
+ }
+}
+
dependencies {
api project(':worldedit-core')
api project(':worldedit-libs:bukkit')
- compile 'net.milkbowl.vault:VaultAPI:1.7'
- compile 'com.destroystokyo.paper:paper-api:1.14.3-R0.1-SNAPSHOT'
- implementation 'io.papermc:paperlib:1.0.2'
compileOnly 'com.sk89q:dummypermscompat:1.10'
+ testCompile 'org.mockito:mockito-core:1.9.0-rc1'
+ implementation('org.apache.logging.log4j:log4j-slf4j-impl:2.8.1'){transitive = false}
+ compile 'com.destroystokyo.paper:paper-api:1.14.3-R0.1-SNAPSHOT'
+ implementation('io.papermc:paperlib:1.0.2'){transitive = false}
compile 'org.spigotmc:spigot:1.13.2-R0.1-SNAPSHOT'
compile name: 'spigot-1.14.3'
- implementation 'org.apache.logging.log4j:log4j-slf4j-impl:2.8.1'
- testCompile 'org.mockito:mockito-core:1.9.0-rc1'
- compile 'com.massivecraft:factions:2.8.0'
- compile 'com.drtshock:factions:1.6.9.5'
- compile 'com.factionsone:FactionsOne:1.2.2'
- compile 'me.ryanhamshire:GriefPrevention:11.5.2'
- compile 'com.massivecraft:mcore:7.0.1'
- compile 'net.sacredlabyrinth.Phaed:PreciousStones:10.0.4-SNAPSHOT'
- compile 'net.jzx7:regios:5.9.9'
- compile 'com.bekvon.bukkit.residence:Residence:4.5._13.1'
- compile 'com.palmergames.bukkit:towny:0.84.0.9'
- compile 'com.thevoxelbox.voxelsniper:voxelsniper:5.171.0'
- compile 'com.comphenix.protocol:ProtocolLib-API:4.4.0-SNAPSHOT'
- compile 'com.wasteofplastic:askyblock:3.0.8.2'
- compileOnly 'com.sk89q.worldguard:worldguard-core:7.0.0-20190215.210421-39'
- compileOnly 'com.sk89q.worldguard:worldguard-legacy:7.0.0-20190215.210421-39'
+// compile([fileTree(dir: 'lib', include: ['*.jar']),'commons-validator:commons-validator:1.4.1'])
+ implementation('com.sk89q.worldguard:worldguard-core:7.0.0-20190215.210421-39'){transitive = false}
+ implementation('com.sk89q.worldguard:worldguard-legacy:7.0.0-20190215.210421-39'){transitive = false}
+ implementation('net.milkbowl.vault:VaultAPI:1.7'){transitive = false}
+ implementation('com.massivecraft:factions:2.8.0'){transitive = false}
+ implementation('com.drtshock:factions:1.6.9.5'){transitive = false}
+ implementation('com.factionsone:FactionsOne:1.2.2'){transitive = false}
+ implementation('me.ryanhamshire:GriefPrevention:11.5.2'){transitive = false}
+ implementation('com.massivecraft:mcore:7.0.1'){transitive = false}
+ implementation('net.sacredlabyrinth.Phaed:PreciousStones:10.0.4-SNAPSHOT'){transitive = false}
+ implementation('net.jzx7:regios:5.9.9'){transitive = false}
+ implementation('com.bekvon.bukkit.residence:Residence:4.5._13.1'){transitive = false}
+ implementation('com.palmergames.bukkit:towny:0.84.0.9'){transitive = false}
+ implementation('com.thevoxelbox.voxelsniper:voxelsniper:5.171.0'){transitive = false}
+ implementation('com.comphenix.protocol:ProtocolLib-API:4.4.0-SNAPSHOT'){transitive = false}
+ implementation('com.wasteofplastic:askyblock:3.0.8.2'){transitive = false}
}
processResources {
diff --git a/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/FaweBukkit.java b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/FaweBukkit.java
index 7a785843d..35acd8310 100644
--- a/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/FaweBukkit.java
+++ b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/FaweBukkit.java
@@ -2,6 +2,9 @@ package com.boydti.fawe.bukkit;
import com.boydti.fawe.Fawe;
import com.boydti.fawe.IFawe;
+import com.boydti.fawe.beta.implementation.QueueHandler;
+import com.boydti.fawe.bukkit.beta.BukkitQueue;
+import com.boydti.fawe.bukkit.beta.BukkitQueueHandler;
import com.boydti.fawe.bukkit.chat.BukkitChatManager;
import com.boydti.fawe.bukkit.listener.AsyncTabCompleteListener;
import com.boydti.fawe.bukkit.listener.BrushListener;
@@ -30,6 +33,7 @@ import com.boydti.fawe.bukkit.v0.BukkitQueue_All;
import com.boydti.fawe.bukkit.v0.ChunkListener_8;
import com.boydti.fawe.bukkit.v0.ChunkListener_9;
import com.boydti.fawe.bukkit.v1_13.BukkitQueue_1_13;
+import com.boydti.fawe.bukkit.v1_14.BukkitQueue_1_14;
import com.boydti.fawe.config.BBC;
import com.boydti.fawe.config.Settings;
import com.boydti.fawe.object.FaweCommand;
@@ -43,6 +47,7 @@ import com.boydti.fawe.util.image.ImageViewer;
import com.sk89q.worldedit.bukkit.WorldEditPlugin;
import com.sk89q.worldedit.world.World;
import org.bukkit.Bukkit;
+import org.bukkit.Chunk;
import org.bukkit.command.ConsoleCommandSender;
import org.bukkit.command.PluginCommand;
import org.bukkit.entity.Player;
@@ -50,9 +55,11 @@ import org.bukkit.event.EventHandler;
import org.bukkit.event.EventPriority;
import org.bukkit.event.Listener;
import org.bukkit.event.player.PlayerQuitEvent;
+import org.bukkit.event.world.ChunkUnloadEvent;
import org.bukkit.plugin.Plugin;
import org.bukkit.plugin.PluginManager;
import org.bukkit.plugin.java.JavaPlugin;
+import org.jetbrains.annotations.NotNull;
import java.io.File;
import java.io.FileOutputStream;
@@ -150,6 +157,11 @@ public class FaweBukkit implements IFawe, Listener {
// }
// }
+ @Override
+ public QueueHandler getQueueHandler() {
+ return new BukkitQueueHandler();
+ }
+
@Override
public synchronized ImageViewer getImageViewer(FawePlayer fp) {
if (listeningImages && imageListener == null) return null;
@@ -575,6 +587,7 @@ public class FaweBukkit implements IFawe, Listener {
}
public enum Version {
+ v1_14_R1,
v1_13_R2,
NONE,
}
@@ -583,6 +596,8 @@ public class FaweBukkit implements IFawe, Listener {
switch (getVersion()) {
case v1_13_R2:
return new BukkitQueue_1_13(world);
+ case v1_14_R1:
+ return new BukkitQueue_1_14(world);
default:
case NONE:
return new BukkitQueue_All(world);
@@ -593,6 +608,8 @@ public class FaweBukkit implements IFawe, Listener {
switch (getVersion()) {
case v1_13_R2:
return new BukkitQueue_1_13(world);
+ case v1_14_R1:
+ return new BukkitQueue_1_14(world);
default:
case NONE:
return new BukkitQueue_All(world);
diff --git a/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/adapter/v1_13_1/Spigot_v1_13_R2.java b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/adapter/v1_13_1/Spigot_v1_13_R2.java
index d16684bcd..076d57d6f 100644
--- a/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/adapter/v1_13_1/Spigot_v1_13_R2.java
+++ b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/adapter/v1_13_1/Spigot_v1_13_R2.java
@@ -102,16 +102,16 @@ public final class Spigot_v1_13_R2 extends CachedBukkitAdapter implements Bukkit
nbtCreateTagMethod.setAccessible(true);
}
- public int[] idbToStateOrdinal;
+ public char[] idbToStateOrdinal;
- private boolean init() {
+ private synchronized boolean init() {
if (idbToStateOrdinal != null) return false;
- idbToStateOrdinal = new int[Block.REGISTRY_ID.a()]; // size
+ idbToStateOrdinal = new char[Block.REGISTRY_ID.a()]; // size
for (int i = 0; i < idbToStateOrdinal.length; i++) {
BlockState state = BlockTypes.states[i];
BlockMaterial_1_13 material = (BlockMaterial_1_13) state.getMaterial();
int id = Block.REGISTRY_ID.getId(material.getState());
- idbToStateOrdinal[id] = state.getOrdinal();
+ idbToStateOrdinal[id] = state.getOrdinalChar();
}
return true;
}
@@ -533,8 +533,18 @@ public final class Spigot_v1_13_R2 extends CachedBukkitAdapter implements Bukkit
int id = Block.REGISTRY_ID.getId(ibd);
return idbToStateOrdinal[id];
} catch (NullPointerException e) {
- if (init()) return adaptToInt(ibd);
- throw e;
+ init();
+ return adaptToInt(ibd);
+ }
+ }
+
+ public char adaptToChar(IBlockData ibd) {
+ try {
+ int id = Block.REGISTRY_ID.getId(ibd);
+ return idbToStateOrdinal[id];
+ } catch (NullPointerException e) {
+ init();
+ return adaptToChar(ibd);
}
}
diff --git a/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitChunkHolder.java b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitChunkHolder.java
new file mode 100644
index 000000000..3987e02de
--- /dev/null
+++ b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitChunkHolder.java
@@ -0,0 +1,352 @@
+package com.boydti.fawe.bukkit.beta;
+
+import com.boydti.fawe.Fawe;
+import com.boydti.fawe.beta.IChunkGet;
+import com.boydti.fawe.beta.IQueueExtent;
+import com.boydti.fawe.beta.IChunkSet;
+import com.boydti.fawe.beta.implementation.QueueHandler;
+import com.boydti.fawe.beta.implementation.holder.ChunkHolder;
+import com.boydti.fawe.bukkit.v0.BukkitQueue_0;
+import com.boydti.fawe.bukkit.v1_13.BukkitQueue_1_13;
+import com.boydti.fawe.util.MemUtil;
+import com.boydti.fawe.util.ReflectionUtils;
+import com.sk89q.jnbt.CompoundTag;
+import com.sk89q.jnbt.ListTag;
+import com.sk89q.jnbt.LongTag;
+import com.sk89q.jnbt.StringTag;
+import com.sk89q.jnbt.Tag;
+import com.sk89q.worldedit.bukkit.BukkitAdapter;
+import com.sk89q.worldedit.internal.Constants;
+import com.sk89q.worldedit.world.biome.BiomeType;
+import net.minecraft.server.v1_14_R1.BiomeBase;
+import net.minecraft.server.v1_14_R1.BlockPosition;
+import net.minecraft.server.v1_14_R1.Chunk;
+import net.minecraft.server.v1_14_R1.ChunkSection;
+import net.minecraft.server.v1_14_R1.Entity;
+import net.minecraft.server.v1_14_R1.EntityTypes;
+import net.minecraft.server.v1_14_R1.MinecraftKey;
+import net.minecraft.server.v1_14_R1.NBTTagCompound;
+import net.minecraft.server.v1_14_R1.NBTTagInt;
+import net.minecraft.server.v1_14_R1.TileEntity;
+import org.bukkit.World;
+import org.bukkit.block.Biome;
+import org.bukkit.craftbukkit.v1_14_R1.block.CraftBlock;
+import org.bukkit.event.entity.CreatureSpawnEvent;
+
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.UUID;
+import java.util.concurrent.Callable;
+import java.util.concurrent.Future;
+
+public class BukkitChunkHolder> extends ChunkHolder {
+ @Override
+ public void init(final IQueueExtent extent, final int X, final int Z) {
+ super.init(extent, X, Z);
+ }
+
+ @Override
+ public IChunkGet get() {
+ BukkitQueue extent = (BukkitQueue) getExtent();
+ return new BukkitGetBlocks(extent.getNmsWorld(), getX(), getZ(), MemUtil.isMemoryFree());
+ }
+
+ private void updateGet(BukkitGetBlocks get, Chunk nmsChunk, ChunkSection[] sections, ChunkSection section, char[] arr, int layer) {
+ synchronized (get) {
+ if (get.nmsChunk != nmsChunk) {
+ get.nmsChunk = nmsChunk;
+ get.sections = sections.clone();
+ get.reset();
+ }
+ if (get.sections == null) {
+ get.sections = sections.clone();
+ }
+ if (get.sections[layer] != section) {
+ get.sections[layer] = section;
+ }
+ get.blocks[layer] = arr;
+ }
+ }
+
+ @Override
+ public synchronized T call() {
+ try {
+ int X = getX();
+ int Z = getZ();
+ BukkitQueue extent = (BukkitQueue) getExtent();
+ BukkitGetBlocks get = (BukkitGetBlocks) getOrCreateGet();
+ IChunkSet set = getOrCreateSet();
+
+ Chunk nmsChunk = extent.ensureLoaded(X, Z);
+
+ // Remove existing tiles
+ {
+ Map tiles = nmsChunk.getTileEntities();
+ if (!tiles.isEmpty()) {
+ final Iterator> iterator = tiles.entrySet().iterator();
+ while (iterator.hasNext()) {
+ final Map.Entry entry = iterator.next();
+ final BlockPosition pos = entry.getKey();
+ final int lx = pos.getX() & 15;
+ final int ly = pos.getY();
+ final int lz = pos.getZ() & 15;
+ final int layer = ly >> 4;
+ if (!set.hasSection(layer)) {
+ continue;
+ }
+ if (set.getBlock(lx, ly, lz).getOrdinal() != 0) {
+ TileEntity tile = entry.getValue();
+ tile.z();
+ tile.invalidateBlockCache();
+ }
+ }
+ }
+ }
+
+ int bitMask = 0;
+ synchronized (nmsChunk) {
+ ChunkSection[] sections = nmsChunk.getSections();
+ World world = extent.getBukkitWorld();
+ boolean hasSky = world.getEnvironment() == World.Environment.NORMAL;
+
+ for (int layer = 0; layer < 16; layer++) {
+ if (!set.hasSection(layer)) continue;
+
+ bitMask |= 1 << layer;
+
+ char[] setArr = set.getArray(layer);
+ ChunkSection newSection;
+ ChunkSection existingSection = sections[layer];
+ if (existingSection == null) {
+ newSection = extent.newChunkSection(layer, hasSky, setArr);
+ if (BukkitQueue.setSectionAtomic(sections, null, newSection, layer)) {
+ updateGet(get, nmsChunk, sections, newSection, setArr, layer);
+ continue;
+ } else {
+ existingSection = sections[layer];
+ if (existingSection == null) {
+ System.out.println("Skipping invalid null section. chunk:" + X + "," + Z + " layer: " + layer);
+ continue;
+ }
+ }
+ }
+ DelegateLock lock = BukkitQueue.applyLock(existingSection);
+ synchronized (get) {
+ synchronized (lock) {
+ lock.untilFree();
+
+ ChunkSection getSection;
+ if (get.nmsChunk != nmsChunk) {
+ get.nmsChunk = nmsChunk;
+ get.sections = null;
+ get.reset();
+ } else {
+ getSection = get.getSections()[layer];
+ if (getSection != existingSection) {
+ get.sections[layer] = existingSection;
+ get.reset();
+ } else if (lock.isModified()) {
+ get.reset(layer);
+ }
+ }
+ char[] getArr = get.load(layer);
+ for (int i = 0; i < 4096; i++) {
+ char value = setArr[i];
+ if (value != 0) {
+ getArr[i] = value;
+ }
+ }
+ newSection = extent.newChunkSection(layer, hasSky, getArr);
+ if (!BukkitQueue.setSectionAtomic(sections, existingSection, newSection, layer)) {
+ System.out.println("Failed to set chunk section:" + X + "," + Z + " layer: " + layer);
+ continue;
+ } else {
+ updateGet(get, nmsChunk, sections, newSection, setArr, layer);
+ }
+ }
+ }
+ }
+
+ // Biomes
+ BiomeType[] biomes = set.getBiomes();
+ if (biomes != null) {
+ // set biomes
+ final BiomeBase[] currentBiomes = nmsChunk.getBiomeIndex();
+ for (int i = 0; i < biomes.length; i++) {
+ final BiomeType biome = biomes[i];
+ if (biome != null) {
+ final Biome craftBiome = BukkitAdapter.adapt(biome);
+ currentBiomes[i] = CraftBlock.biomeToBiomeBase(craftBiome);
+ }
+ }
+ }
+
+ Runnable[] syncTasks = null;
+
+ net.minecraft.server.v1_14_R1.World nmsWorld = nmsChunk.getWorld();
+ int bx = X << 4;
+ int bz = Z << 4;
+
+ Set entityRemoves = set.getEntityRemoves();
+ if (entityRemoves != null && !entityRemoves.isEmpty()) {
+ if (syncTasks == null) syncTasks = new Runnable[3];
+
+ syncTasks[2] = new Runnable() {
+ @Override
+ public void run() {
+ final List[] entities = nmsChunk.getEntitySlices();
+
+ for (int i = 0; i < entities.length; i++) {
+ final Collection ents = entities[i];
+ if (!ents.isEmpty()) {
+ final Iterator iter = ents.iterator();
+ while (iter.hasNext()) {
+ final Entity entity = iter.next();
+ if (entityRemoves.contains(entity.getUniqueID())) {
+ iter.remove();
+ entity.b(false);
+ entity.die();
+ entity.valid = false;
+ }
+ }
+ }
+ }
+ }
+ };
+ }
+
+ Set entities = set.getEntities();
+ if (entities != null && !entities.isEmpty()) {
+ if (syncTasks == null) syncTasks = new Runnable[2];
+
+ syncTasks[1] = new Runnable() {
+ @Override
+ public void run() {
+ for (final CompoundTag nativeTag : entities) {
+ final Map entityTagMap = ReflectionUtils.getMap(nativeTag.getValue());
+ final StringTag idTag = (StringTag) entityTagMap.get("Id");
+ final ListTag posTag = (ListTag) entityTagMap.get("Pos");
+ final ListTag rotTag = (ListTag) entityTagMap.get("Rotation");
+ if (idTag == null || posTag == null || rotTag == null) {
+ Fawe.debug("Unknown entity tag: " + nativeTag);
+ continue;
+ }
+ final double x = posTag.getDouble(0);
+ final double y = posTag.getDouble(1);
+ final double z = posTag.getDouble(2);
+ final float yaw = rotTag.getFloat(0);
+ final float pitch = rotTag.getFloat(1);
+ final String id = idTag.getValue();
+ final Entity entity = EntityTypes.a(nmsWorld, new MinecraftKey(id));
+ if (entity != null) {
+ final UUID uuid = entity.getUniqueID();
+ entityTagMap.put("UUIDMost", new LongTag(uuid.getMostSignificantBits()));
+ entityTagMap.put("UUIDLeast", new LongTag(uuid.getLeastSignificantBits()));
+ if (nativeTag != null) {
+ final NBTTagCompound tag = (NBTTagCompound) BukkitQueue_1_13.fromNative(nativeTag);
+ for (final String name : Constants.NO_COPY_ENTITY_NBT_FIELDS) {
+ tag.remove(name);
+ }
+ entity.f(tag);
+ }
+ entity.setLocation(x, y, z, yaw, pitch);
+ nmsWorld.addEntity(entity, CreatureSpawnEvent.SpawnReason.CUSTOM);
+ }
+ }
+ }
+ };
+
+ }
+
+ // set tiles
+ Map tiles = set.getTiles();
+ if (tiles != null && !tiles.isEmpty()) {
+ if (syncTasks == null) syncTasks = new Runnable[1];
+
+ syncTasks[0] = new Runnable() {
+ @Override
+ public void run() {
+ for (final Map.Entry entry : tiles.entrySet()) {
+ final CompoundTag nativeTag = entry.getValue();
+ final short blockHash = entry.getKey();
+ final int x = (blockHash >> 12 & 0xF) + bx;
+ final int y = (blockHash & 0xFF);
+ final int z = (blockHash >> 8 & 0xF) + bz;
+ final BlockPosition pos = new BlockPosition(x, y, z);
+ synchronized (BukkitQueue_0.class) {
+ TileEntity tileEntity = nmsWorld.getTileEntity(pos);
+ if (tileEntity == null || tileEntity.x()) {
+ nmsWorld.n(pos);
+ tileEntity = nmsWorld.getTileEntity(pos);
+ }
+ if (tileEntity != null) {
+ final NBTTagCompound tag = (NBTTagCompound) BukkitQueue_1_13.fromNative(nativeTag);
+ tag.set("x", new NBTTagInt(x));
+ tag.set("y", new NBTTagInt(y));
+ tag.set("z", new NBTTagInt(z));
+ tileEntity.load(tag);
+ }
+ }
+ }
+ }
+ };
+ }
+
+ Runnable callback;
+ if (bitMask == 0) {
+ callback = null;
+ } else {
+ int finalMask = bitMask;
+ callback = () -> {
+ // Set Modified
+ nmsChunk.f(true);
+ nmsChunk.mustSave = true;
+ nmsChunk.markDirty();
+ // send to player
+ extent.sendChunk(X, Z, finalMask);
+
+ extent.returnToPool(BukkitChunkHolder.this);
+ };
+ }
+ if (syncTasks != null) {
+ QueueHandler queueHandler = Fawe.get().getQueueHandler();
+ Runnable[] finalSyncTasks = syncTasks;
+
+ // Chain the sync tasks and the callback
+ Callable chain = new Callable() {
+ @Override
+ public Future call() {
+ // Run the sync tasks
+ for (int i = 1; i < finalSyncTasks.length; i++) {
+ Runnable task = finalSyncTasks[i];
+ if (task != null) {
+ task.run();
+ }
+ }
+ if (callback == null) {
+ extent.returnToPool(BukkitChunkHolder.this);
+ return null;
+ } else {
+ return queueHandler.async(callback, null);
+ }
+ }
+ };
+ return (T) (Future) queueHandler.sync(chain);
+ } else {
+ if (callback == null) {
+ extent.returnToPool(BukkitChunkHolder.this);
+ } else {
+ callback.run();
+ }
+ }
+ }
+ return null;
+ } catch (Throwable e) {
+ e.printStackTrace();
+ return null;
+ }
+ }
+}
\ No newline at end of file
diff --git a/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitGetBlocks.java b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitGetBlocks.java
new file mode 100644
index 000000000..da1506fd7
--- /dev/null
+++ b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitGetBlocks.java
@@ -0,0 +1,208 @@
+package com.boydti.fawe.bukkit.beta;
+
+import com.boydti.fawe.FaweCache;
+import com.boydti.fawe.beta.implementation.blocks.CharGetBlocks;
+import com.boydti.fawe.bukkit.v1_14.BukkitQueue_1_14;
+import com.boydti.fawe.bukkit.v1_14.adapter.Spigot_v1_14_R1;
+import com.boydti.fawe.jnbt.anvil.BitArray4096;
+import com.boydti.fawe.util.MemUtil;
+import com.boydti.fawe.util.TaskManager;
+import com.sk89q.jnbt.CompoundTag;
+import com.sk89q.worldedit.bukkit.BukkitAdapter;
+import com.sk89q.worldedit.world.biome.BiomeType;
+import com.sk89q.worldedit.world.block.BlockTypes;
+import net.minecraft.server.v1_14_R1.BiomeBase;
+import net.minecraft.server.v1_14_R1.Chunk;
+import net.minecraft.server.v1_14_R1.ChunkCoordIntPair;
+import net.minecraft.server.v1_14_R1.ChunkProviderServer;
+import net.minecraft.server.v1_14_R1.ChunkSection;
+import net.minecraft.server.v1_14_R1.DataBits;
+import net.minecraft.server.v1_14_R1.DataPalette;
+import net.minecraft.server.v1_14_R1.DataPaletteBlock;
+import net.minecraft.server.v1_14_R1.DataPaletteHash;
+import net.minecraft.server.v1_14_R1.DataPaletteLinear;
+import net.minecraft.server.v1_14_R1.IBlockData;
+import net.minecraft.server.v1_14_R1.World;
+import net.minecraft.server.v1_14_R1.WorldServer;
+import org.bukkit.craftbukkit.v1_14_R1.block.CraftBlock;
+
+import java.util.Arrays;
+
+public class BukkitGetBlocks extends CharGetBlocks {
+ public ChunkSection[] sections;
+ public Chunk nmsChunk;
+ public World nmsWorld;
+ public int X, Z;
+ private boolean forceLoad;
+
+ public BukkitGetBlocks(World nmsWorld, int X, int Z, boolean forceLoad) {
+ this.nmsWorld = nmsWorld;
+ this.X = X;
+ this.Z = Z;
+ if (forceLoad) {
+ ((WorldServer) nmsWorld).setForceLoaded(X, Z, this.forceLoad = true);
+ }
+ }
+
+ @Override
+ protected void finalize() {
+ if (forceLoad) {
+ ((WorldServer) nmsWorld).setForceLoaded(X, Z, forceLoad = false);
+ }
+ }
+
+ @Override
+ public BiomeType getBiomeType(int x, int z) {
+ BiomeBase base = getChunk().getBiomeIndex()[(z << 4) + x];
+ return BukkitAdapter.adapt(CraftBlock.biomeBaseToBiome(base));
+ }
+
+ @Override
+ public CompoundTag getTag(int x, int y, int z) {
+ // TODO
+ return null;
+ }
+
+ @Override
+ public char[] load(int layer) {
+ return load(layer, null);
+ }
+
+ @Override
+ public synchronized char[] load(int layer, char[] data) {
+ ChunkSection section = getSections()[layer];
+ // Section is null, return empty array
+ if (section == null) {
+ return FaweCache.EMPTY_CHAR_4096;
+ }
+ if (data == null || data == FaweCache.EMPTY_CHAR_4096) {
+ data = new char[4096];
+ }
+ DelegateLock lock = BukkitQueue.applyLock(section);
+ synchronized (lock) {
+ lock.untilFree();
+ lock.setModified(false);
+ // Efficiently convert ChunkSection to raw data
+ try {
+ final DataPaletteBlock blocks = section.getBlocks();
+ final DataBits bits = (DataBits) BukkitQueue_1_14.fieldBits.get(blocks);
+ final DataPalette palette = (DataPalette) BukkitQueue_1_14.fieldPalette.get(blocks);
+
+ final int bitsPerEntry = bits.c();
+ final long[] blockStates = bits.a();
+
+ new BitArray4096(blockStates, bitsPerEntry).toRaw(data);
+
+ int num_palette;
+ if (palette instanceof DataPaletteLinear) {
+ num_palette = ((DataPaletteLinear) palette).b();
+ } else if (palette instanceof DataPaletteHash) {
+ num_palette = ((DataPaletteHash) palette).b();
+ } else {
+ num_palette = 0;
+ int[] paletteToBlockInts = FaweCache.PALETTE_TO_BLOCK.get();
+ char[] paletteToBlockChars = FaweCache.PALETTE_TO_BLOCK_CHAR.get();
+ try {
+ for (int i = 0; i < 4096; i++) {
+ char paletteVal = data[i];
+ char ordinal = paletteToBlockChars[paletteVal];
+ if (ordinal == Character.MAX_VALUE) {
+ paletteToBlockInts[num_palette++] = paletteVal;
+ IBlockData ibd = palette.a(data[i]);
+ if (ibd == null) {
+ ordinal = BlockTypes.AIR.getDefaultState().getOrdinalChar();
+ } else {
+ ordinal = ((Spigot_v1_14_R1) getAdapter()).adaptToChar(ibd);
+ }
+ paletteToBlockChars[paletteVal] = ordinal;
+ }
+ data[i] = ordinal;
+ }
+ } finally {
+ for (int i = 0; i < num_palette; i++) {
+ int paletteVal = paletteToBlockInts[i];
+ paletteToBlockChars[paletteVal] = Character.MAX_VALUE;
+ }
+ }
+ return data;
+ }
+
+ char[] paletteToBlockChars = FaweCache.PALETTE_TO_BLOCK_CHAR.get();
+ try {
+ final int size = num_palette;
+ if (size != 1) {
+ for (int i = 0; i < size; i++) {
+ char ordinal = ordinal(palette.a(i));
+ paletteToBlockChars[i] = ordinal;
+ }
+ for (int i = 0; i < 4096; i++) {
+ char paletteVal = data[i];
+ char val = paletteToBlockChars[paletteVal];
+ data[i] = val;
+ }
+ } else {
+ char ordinal = ordinal(palette.a(0));
+ Arrays.fill(data, ordinal);
+ }
+ } finally {
+ for (int i = 0; i < num_palette; i++) {
+ paletteToBlockChars[i] = Character.MAX_VALUE;
+ }
+ }
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ throw new RuntimeException(e);
+ }
+ return data;
+ }
+ }
+
+ private final char ordinal(IBlockData ibd) {
+ if (ibd == null) {
+ return BlockTypes.AIR.getDefaultState().getOrdinalChar();
+ } else {
+ return ((Spigot_v1_14_R1) getAdapter()).adaptToChar(ibd);
+ }
+ }
+
+ public ChunkSection[] getSections() {
+ ChunkSection[] tmp = sections;
+ if (tmp == null) {
+ synchronized (this) {
+ tmp = sections;
+ if (tmp == null) {
+ Chunk chunk = getChunk();
+ sections = tmp = chunk.getSections().clone();
+ }
+ }
+ }
+ return tmp;
+ }
+
+ public Chunk getChunk() {
+ Chunk tmp = nmsChunk;
+ if (tmp == null) {
+ synchronized (this) {
+ tmp = nmsChunk;
+ if (tmp == null) {
+ nmsChunk = tmp = BukkitQueue.ensureLoaded(nmsWorld, X, Z);
+ }
+ }
+ }
+ return tmp;
+ }
+
+ @Override
+ public boolean hasSection(int layer) {
+ return getSections()[layer] != null;
+ }
+
+ @Override
+ public boolean trim(boolean aggressive) {
+ if (aggressive) {
+ sections = null;
+ nmsChunk = null;
+ }
+ return super.trim(aggressive);
+ }
+}
diff --git a/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitQueue.java b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitQueue.java
new file mode 100644
index 000000000..79b37e1eb
--- /dev/null
+++ b/worldedit-bukkit/src/main/java/com/boydti/fawe/bukkit/beta/BukkitQueue.java
@@ -0,0 +1,369 @@
+package com.boydti.fawe.bukkit.beta;
+
+import com.boydti.fawe.Fawe;
+import com.boydti.fawe.FaweCache;
+import com.boydti.fawe.beta.IChunk;
+import com.boydti.fawe.beta.implementation.SimpleCharQueueExtent;
+import com.boydti.fawe.beta.implementation.SingleThreadQueueExtent;
+import com.boydti.fawe.beta.implementation.WorldChunkCache;
+import com.boydti.fawe.bukkit.adapter.v1_13_1.BlockMaterial_1_13;
+import com.boydti.fawe.config.Settings;
+import com.boydti.fawe.jnbt.anvil.BitArray4096;
+import com.boydti.fawe.object.collection.IterableThreadLocal;
+import com.boydti.fawe.util.MathMan;
+import com.boydti.fawe.util.TaskManager;
+import com.sk89q.worldedit.bukkit.BukkitWorld;
+import com.sk89q.worldedit.math.BlockVector3;
+import com.sk89q.worldedit.world.World;
+import com.sk89q.worldedit.world.block.BaseBlock;
+import com.sk89q.worldedit.world.block.BlockID;
+import com.sk89q.worldedit.world.block.BlockState;
+import com.sk89q.worldedit.world.block.BlockTypes;
+import net.jpountz.util.UnsafeUtils;
+import net.minecraft.server.v1_14_R1.Block;
+import net.minecraft.server.v1_14_R1.Chunk;
+import net.minecraft.server.v1_14_R1.ChunkCoordIntPair;
+import net.minecraft.server.v1_14_R1.ChunkProviderServer;
+import net.minecraft.server.v1_14_R1.ChunkSection;
+import net.minecraft.server.v1_14_R1.ChunkStatus;
+import net.minecraft.server.v1_14_R1.DataBits;
+import net.minecraft.server.v1_14_R1.DataPalette;
+import net.minecraft.server.v1_14_R1.DataPaletteBlock;
+import net.minecraft.server.v1_14_R1.DataPaletteLinear;
+import net.minecraft.server.v1_14_R1.GameProfileSerializer;
+import net.minecraft.server.v1_14_R1.IBlockData;
+import net.minecraft.server.v1_14_R1.PlayerChunk;
+import net.minecraft.server.v1_14_R1.PlayerChunkMap;
+import net.minecraft.server.v1_14_R1.WorldServer;
+import org.bukkit.Bukkit;
+import org.bukkit.craftbukkit.v1_14_R1.CraftChunk;
+import org.bukkit.craftbukkit.v1_14_R1.CraftWorld;
+
+import java.lang.reflect.Field;
+import java.lang.reflect.Modifier;
+import java.util.Arrays;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReentrantLock;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+import java.util.function.Supplier;
+
+import sun.misc.Unsafe;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+public class BukkitQueue extends SimpleCharQueueExtent {
+
+ private org.bukkit.World bukkitWorld;
+ private WorldServer nmsWorld;
+
+ @Override
+ public synchronized void init(WorldChunkCache cache) {
+ World world = cache.getWorld();
+ if (world instanceof BukkitWorld) {
+ this.bukkitWorld = ((BukkitWorld) world).getWorld();
+ } else {
+ this.bukkitWorld = Bukkit.getWorld(world.getName());
+ }
+ checkNotNull(this.bukkitWorld);
+ CraftWorld craftWorld = ((CraftWorld) bukkitWorld);
+ this.nmsWorld = craftWorld.getHandle();
+ super.init(cache);
+ }
+
+ public WorldServer getNmsWorld() {
+ return nmsWorld;
+ }
+
+ public org.bukkit.World getBukkitWorld() {
+ return bukkitWorld;
+ }
+
+ @Override
+ protected synchronized void reset() {
+ super.reset();
+ }
+
+// private static final IterableThreadLocal FULL_CHUNKS = new IterableThreadLocal() {
+// @Override
+// public BukkitFullChunk init() {
+// return new BukkitFullChunk();
+// }
+// };
+
+ @Override
+ public IChunk create(boolean full) {
+// if (full) {
+// //TODO implement
+// return FULL_CHUNKS.get();
+// }
+ return new BukkitChunkHolder();
+ }
+
+ /*
+ NMS fields
+ */
+ public final static Field fieldBits;
+ public final static Field fieldPalette;
+ public final static Field fieldSize;
+
+ public final static Field fieldFluidCount;
+ public final static Field fieldTickingBlockCount;
+ public final static Field fieldNonEmptyBlockCount;
+
+ private final static Field fieldDirtyCount;
+ private final static Field fieldDirtyBits;
+
+ private static final int CHUNKSECTION_BASE;
+ private static final int CHUNKSECTION_SHIFT;
+
+ private static final Field fieldLock;
+
+ static {
+ try {
+ fieldSize = DataPaletteBlock.class.getDeclaredField("i");
+ fieldSize.setAccessible(true);
+ fieldBits = DataPaletteBlock.class.getDeclaredField("a");
+ fieldBits.setAccessible(true);
+ fieldPalette = DataPaletteBlock.class.getDeclaredField("h");
+ fieldPalette.setAccessible(true);
+
+ fieldFluidCount = ChunkSection.class.getDeclaredField("e");
+ fieldFluidCount.setAccessible(true);
+ fieldTickingBlockCount = ChunkSection.class.getDeclaredField("tickingBlockCount");
+ fieldTickingBlockCount.setAccessible(true);
+ fieldNonEmptyBlockCount = ChunkSection.class.getDeclaredField("nonEmptyBlockCount");
+ fieldNonEmptyBlockCount.setAccessible(true);
+
+ fieldDirtyCount = PlayerChunk.class.getDeclaredField("dirtyCount");
+ fieldDirtyCount.setAccessible(true);
+ fieldDirtyBits = PlayerChunk.class.getDeclaredField("h");
+ fieldDirtyBits.setAccessible(true);
+
+ {
+ Field tmp = null;
+ try {
+ tmp = DataPaletteBlock.class.getDeclaredField("j");
+ } catch (NoSuchFieldException paper) {
+ tmp = DataPaletteBlock.class.getDeclaredField("writeLock");
+ }
+ fieldLock = tmp;
+ fieldLock.setAccessible(true);
+ Field modifiersField = Field.class.getDeclaredField("modifiers");
+ modifiersField.setAccessible(true);
+ int modifiers = modifiersField.getInt(fieldLock);
+ int newModifiers = modifiers & (~Modifier.FINAL);
+ if (newModifiers != modifiers) modifiersField.setInt(fieldLock, newModifiers);
+ }
+
+ Unsafe unsafe = UnsafeUtils.getUNSAFE();
+ CHUNKSECTION_BASE = unsafe.arrayBaseOffset(ChunkSection[].class);
+ int scale = unsafe.arrayIndexScale(ChunkSection[].class);
+ if ((scale & (scale - 1)) != 0)
+ throw new Error("data type scale not a power of two");
+ CHUNKSECTION_SHIFT = 31 - Integer.numberOfLeadingZeros(scale);
+ } catch (RuntimeException e) {
+ throw e;
+ } catch (Throwable rethrow) {
+ rethrow.printStackTrace();
+ throw new RuntimeException(rethrow);
+ }
+ }
+
+ protected static boolean setSectionAtomic(ChunkSection[] sections, ChunkSection expected, ChunkSection value, int layer) {
+ long offset = ((long) layer << CHUNKSECTION_SHIFT) + CHUNKSECTION_BASE;
+ if (layer >= 0 && layer < sections.length) {
+ return UnsafeUtils.getUNSAFE().compareAndSwapObject(sections, offset, expected, value);
+ }
+ return false;
+ }
+
+ protected static DelegateLock applyLock(ChunkSection section) {
+ try {
+ synchronized (section) {
+ DataPaletteBlock blocks = section.getBlocks();
+ Lock currentLock = (Lock) fieldLock.get(blocks);
+ if (currentLock instanceof DelegateLock) {
+ return (DelegateLock) currentLock;
+ }
+ DelegateLock newLock = new DelegateLock(currentLock);
+ fieldLock.set(blocks, newLock);
+ return newLock;
+ }
+ } catch (IllegalAccessException e) {
+ e.printStackTrace();
+ throw new RuntimeException(e);
+ }
+ }
+
+ private static boolean PAPER = true;
+
+ public Chunk ensureLoaded(int X, int Z) {
+ return ensureLoaded(nmsWorld, X, Z);
+ }
+
+ public static Chunk ensureLoaded(net.minecraft.server.v1_14_R1.World nmsWorld, int X, int Z) {
+ ChunkProviderServer provider = (ChunkProviderServer) nmsWorld.getChunkProvider();
+
+
+ Chunk nmsChunk = (Chunk) provider.getChunkAt(X, Z, ChunkStatus.FEATURES, false);;
+ if (nmsChunk != null) {
+ return nmsChunk;
+ }
+ if (Fawe.isMainThread()) {
+ return nmsWorld.getChunkAt(X, Z);
+ }
+ if (PAPER) {
+ CraftWorld craftWorld = nmsWorld.getWorld();
+ CompletableFuture future = craftWorld.getChunkAtAsync(X, Z, true);
+ try {
+ CraftChunk chunk = (CraftChunk) future.get();
+ return chunk.getHandle();
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ } catch (ExecutionException e) {
+ e.printStackTrace();
+ } catch (Throwable e) {
+ System.out.println("Error, cannot load chunk async (paper not installed?)");
+ PAPER = false;
+ }
+ }
+ // TODO optimize
+ return TaskManager.IMP.sync(() -> nmsWorld.getChunkAt(X, Z));
+ }
+
+ private PlayerChunk getPlayerChunk(final int cx, final int cz) {
+ final PlayerChunkMap chunkMap = nmsWorld.getPlayerChunkMap();
+ final PlayerChunk playerChunk = chunkMap.getChunk(cx, cz);
+ if (playerChunk == null) {
+ return null;
+ }
+ if (playerChunk.players.isEmpty()) {
+ return null;
+ }
+ return playerChunk;
+ }
+
+ public boolean sendChunk(final int X, final int Z, final int mask) {
+ PlayerChunk playerChunk = getPlayerChunk(X, Z);
+ if (playerChunk == null) {
+ return false;
+ }
+ if (playerChunk.e()) {
+ TaskManager.IMP.sync(new Supplier
*
- *
The list of directions can be cleared.
- *
* @return the list of directions
*/
- protected Collection getDirections() {
- return directions;
+ public Collection getDirections() {
+ return Arrays.asList(directions);
}
/**
* Add the directions along the axes as directions to visit.
*/
- protected void addAxes() {
- directions.add(BlockVector3.UNIT_MINUS_Y);
- directions.add(BlockVector3.UNIT_Y);
- directions.add(BlockVector3.UNIT_MINUS_X);
- directions.add(BlockVector3.UNIT_X);
- directions.add(BlockVector3.UNIT_MINUS_Z);
- directions.add(BlockVector3.UNIT_Z);
+ public void addAxes() {
+ HashSet set = new HashSet<>(Arrays.asList(directions));
+ set.add(BlockVector3.UNIT_MINUS_Y);
+ set.add(BlockVector3.UNIT_Y);
+ set.add(BlockVector3.UNIT_MINUS_X);
+ set.add(BlockVector3.UNIT_X);
+ set.add(BlockVector3.UNIT_MINUS_Z);
+ set.add(BlockVector3.UNIT_Z);
+ setDirections(set);
}
/**
* Add the diagonal directions as directions to visit.
*/
- protected void addDiagonal() {
- directions.add(Direction.NORTHEAST.toBlockVector());
- directions.add(Direction.SOUTHEAST.toBlockVector());
- directions.add(Direction.SOUTHWEST.toBlockVector());
- directions.add(Direction.NORTHWEST.toBlockVector());
+ public void addDiagonal() {
+ HashSet set = new HashSet<>(Arrays.asList(directions));
+ set.add(Direction.NORTHEAST.toBlockVector());
+ set.add(Direction.SOUTHEAST.toBlockVector());
+ set.add(Direction.SOUTHWEST.toBlockVector());
+ set.add(Direction.NORTHWEST.toBlockVector());
+ setDirections(set);
}
/**
@@ -207,21 +207,6 @@ public abstract class BreadthFirstSearch implements Operation {
public void setMaxBranch(int maxBranch) {
this.maxBranch = maxBranch;
}
- /**
- * Try to visit the given 'to' location.
- *
- * @param from the origin block
- * @param to the block under question
- */
- private void visit(BlockVector3 from, BlockVector3 to) {
- BlockVector3 blockVector = to;
- if (!visited.contains(blockVector)) {
- visited.add(blockVector);
- if (isVisitable(from, to)) {
- queue.add(blockVector);
- }
- }
- }
/**
* Return whether the given 'to' block should be visited, starting from the
@@ -245,7 +230,9 @@ public abstract class BreadthFirstSearch implements Operation {
@Override
public Operation resume(RunContext run) throws WorldEditException {
MutableBlockVector3 mutable = new MutableBlockVector3();
- IntegerTrio[] dirs = getIntDirections();
+// MutableBlockVector3 mutable2 = new MutableBlockVector3();
+ boolean shouldTrim = false;
+ BlockVector3[] dirs = directions;
BlockVectorSet tempQueue = new BlockVectorSet();
BlockVectorSet chunkLoadSet = new BlockVectorSet();
for (currentDepth = 0; !queue.isEmpty() && currentDepth <= maxDepth; currentDepth++) {
@@ -253,11 +240,11 @@ public abstract class BreadthFirstSearch implements Operation {
int cx = Integer.MIN_VALUE;
int cz = Integer.MIN_VALUE;
for (BlockVector3 from : queue) {
- for (IntegerTrio direction : dirs) {
- int x = from.getBlockX() + direction.x;
- int z = from.getBlockZ() + direction.z;
+ for (BlockVector3 direction : dirs) {
+ int x = from.getBlockX() + direction.getX();
+ int z = from.getBlockZ() + direction.getZ();
if (cx != (cx = x >> 4) || cz != (cz = z >> 4)) {
- int y = from.getBlockY() + direction.y;
+ int y = from.getBlockY() + direction.getY();
if (y < 0 || y >= 256) {
continue;
}
@@ -274,13 +261,13 @@ public abstract class BreadthFirstSearch implements Operation {
for (BlockVector3 from : queue) {
if (function.apply(from)) affected++;
for (int i = 0, j = 0; i < dirs.length && j < maxBranch; i++) {
- IntegerTrio direction = dirs[i];
- int y = from.getBlockY() + direction.y;
+ BlockVector3 direction = dirs[i];
+ int y = from.getBlockY() + direction.getY();
if (y < 0 || y >= 256) {
continue;
}
- int x = from.getBlockX() + direction.x;
- int z = from.getBlockZ() + direction.z;
+ int x = from.getBlockX() + direction.getX();
+ int z = from.getBlockZ() + direction.getZ();
if (!visited.contains(x, y, z)) {
if (isVisitable(from, mutable.setComponents(x, y, z))) {
j++;
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DirectionalVisitor.java b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DirectionalVisitor.java
index 8a9542e32..9a0b8c912 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DirectionalVisitor.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DirectionalVisitor.java
@@ -51,14 +51,15 @@ public class DirectionalVisitor extends RecursiveVisitor {
checkNotNull(mask);
this.origin = origin;
this.dirVec = direction;
- final Collection directions = this.getDirections();
- directions.clear();
- directions.add(BlockVector3.at(1, 0, 0));
- directions.add(BlockVector3.at(-1, 0, 0));
- directions.add(BlockVector3.at(0, 0, 1));
- directions.add(BlockVector3.at(0, 0, -1));
- directions.add(BlockVector3.at(0, -1, 0));
- directions.add(BlockVector3.at(0, 1, 0));
+
+ setDirections(
+ BlockVector3.at(1, 0, 0),
+ BlockVector3.at(-1, 0, 0),
+ BlockVector3.at(0, 0, 1),
+ BlockVector3.at(0, 0, -1),
+ BlockVector3.at(0, -1, 0),
+ BlockVector3.at(0, 1, 0)
+ );
}
@Override
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DownwardVisitor.java b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DownwardVisitor.java
index e20007841..33a1dde10 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DownwardVisitor.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/DownwardVisitor.java
@@ -57,13 +57,13 @@ public class DownwardVisitor extends RecursiveVisitor {
this.baseY = baseY;
- Collection directions = getDirections();
- directions.clear();
- directions.add(BlockVector3.UNIT_X);
- directions.add(BlockVector3.UNIT_MINUS_X);
- directions.add(BlockVector3.UNIT_Z);
- directions.add(BlockVector3.UNIT_MINUS_Z);
- directions.add(BlockVector3.UNIT_MINUS_Y);
+ setDirections(
+ BlockVector3.UNIT_X,
+ BlockVector3.UNIT_MINUS_X,
+ BlockVector3.UNIT_Z,
+ BlockVector3.UNIT_MINUS_Z,
+ BlockVector3.UNIT_MINUS_Y
+ );
}
@Override
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/NonRisingVisitor.java b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/NonRisingVisitor.java
index cc74ffce7..e932d8c2d 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/NonRisingVisitor.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/NonRisingVisitor.java
@@ -44,13 +44,13 @@ public class NonRisingVisitor extends RecursiveVisitor {
public NonRisingVisitor(Mask mask, RegionFunction function, int depth, HasFaweQueue hasFaweQueue) {
super(mask, function, depth, hasFaweQueue);
- Collection directions = getDirections();
- directions.clear();
- directions.add(BlockVector3.UNIT_X);
- directions.add(BlockVector3.UNIT_MINUS_X);
- directions.add(BlockVector3.UNIT_Z);
- directions.add(BlockVector3.UNIT_MINUS_Z);
- directions.add(BlockVector3.UNIT_MINUS_Y);
+ setDirections(
+ BlockVector3.UNIT_X,
+ BlockVector3.UNIT_MINUS_X,
+ BlockVector3.UNIT_Z,
+ BlockVector3.UNIT_MINUS_Z,
+ BlockVector3.UNIT_MINUS_Y
+ );
}
}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/ScanChunk.java b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/ScanChunk.java
new file mode 100644
index 000000000..96ce3ca37
--- /dev/null
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/function/visitor/ScanChunk.java
@@ -0,0 +1,342 @@
+package com.sk89q.worldedit.function.visitor;
+
+import com.boydti.fawe.beta.IChunk;
+import com.boydti.fawe.util.MathMan;
+import com.sk89q.worldedit.function.RegionFunction;
+import com.sk89q.worldedit.math.BlockVector3;
+import it.unimi.dsi.fastutil.longs.Long2ObjectMap;
+import it.unimi.dsi.fastutil.longs.Long2ObjectOpenHashMap;
+import it.unimi.dsi.fastutil.longs.LongArraySet;
+import it.unimi.dsi.fastutil.objects.ObjectIterator;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.List;
+import java.util.concurrent.ConcurrentLinkedQueue;
+
+/**
+ * A chunk based search algorithm
+ */
+public class ScanChunk {
+ private static final int MAX_QUEUE = 34816;
+ public static final BlockVector3[] DEFAULT_DIRECTIONS = new BlockVector3[6];
+ public static final BlockVector3[] DIAGONAL_DIRECTIONS;
+
+ static {
+ DEFAULT_DIRECTIONS[0] = (BlockVector3.at(0, -1, 0));
+ DEFAULT_DIRECTIONS[1] = (BlockVector3.at(0, 1, 0));
+ DEFAULT_DIRECTIONS[2] = (BlockVector3.at(-1, 0, 0));
+ DEFAULT_DIRECTIONS[3] = (BlockVector3.at(1, 0, 0));
+ DEFAULT_DIRECTIONS[4] = (BlockVector3.at(0, 0, -1));
+ DEFAULT_DIRECTIONS[5] = (BlockVector3.at(0, 0, 1));
+ List list = new ArrayList<>();
+ for (int x = -1; x <= 1; x++) {
+ for (int y = -1; y <= 1; y++) {
+ for (int z = -1; z <= 1; z++) {
+ if (x != 0 || y != 0 || z != 0) {
+ BlockVector3 pos = BlockVector3.at(x, y, z);
+ if (!list.contains(pos)) {
+ list.add(pos);
+ }
+ }
+ }
+ }
+ }
+ Collections.sort(list, new Comparator() {
+ @Override
+ public int compare(BlockVector3 o1, BlockVector3 o2) {
+ return (int) Math.signum(o1.lengthSq() - o2.lengthSq());
+ }
+ });
+ DIAGONAL_DIRECTIONS = list.toArray(new BlockVector3[list.size()]);
+ }
+
+ private final RegionFunction function;
+ private final BlockVector3[] directions;
+ private final Long2ObjectOpenHashMap visits;
+ private final Long2ObjectOpenHashMap queues;
+
+ public ScanChunk(final RegionFunction function) {
+ this.function = function;
+ this.directions = DEFAULT_DIRECTIONS;
+
+ this.queues = new Long2ObjectOpenHashMap<>();
+ this.visits = new Long2ObjectOpenHashMap<>();
+ }
+
+ public static final long pairInt(int x, int y) {
+ return (((long) x) << 32) | (y & 0xffffffffL);
+ }
+
+ public boolean isVisited(int x, int y, int z) {
+ int X = x >> 4;
+ int Z = z >> 4;
+ long pair = pairInt(X, Z);
+ long[][] chunk = visits.get(pair);
+ if (chunk == null) return false;
+ int layer = y >> 4;
+ long[] section = chunk[layer];
+ if (section == null) return false;
+ return get(section, getLocalIndex(x & 15, y & 15, z & 15));
+ }
+
+ public void start(int x, int y, int z) {
+ if (!isVisited(x, y, z)) {
+ push(x, y, z);
+ visit(x, y, z);
+ }
+ }
+
+ public void visit(int x, int y, int z) {
+ int X = x >> 4;
+ int Z = z >> 4;
+ long pair = pairInt(X, Z);
+ long[][] arrs = visits.get(pair);
+ if (arrs == null) {
+ visits.put(pair, arrs = new long[16][]);
+ }
+ int layer = y >> 4;
+ long[] section = arrs[layer];
+ if (section == null) {
+ arrs[layer] = section = new long[64];
+ }
+ set(section, getLocalIndex(x & 15, y & 15, z & 15));
+ }
+
+ private char[] getOrCreateQueue(long pair, int layer) {
+ char[][] arrs = queues.get(pair);
+ if (arrs == null) {
+ queues.put(pair, arrs = new char[16][]);
+ }
+
+ char[] section = arrs[layer];
+ if (section == null) {
+ arrs[layer] = section = newQueue();
+ }
+ return section;
+ }
+
+ private void push(int x, int y, int z) {
+ int X = x >> 4;
+ int Z = z >> 4;
+ long pair = pairInt(X, Z);
+ int layer = y >> 4;
+ char[] section = getOrCreateQueue(pair, layer);
+ push(section, x & 15, y & 15, z & 15);
+ }
+
+ private void push(char[] queue, int x, int y, int z) {
+ char indexStart = queue[0];
+ char indexEnd = queue[1];
+ push(indexStart, indexEnd, queue, x, y, z);
+ }
+
+ private void push(char indexStart, char indexEnd, char[] queue, int x, int y, int z) {
+ char index = getLocalIndex(x, y, z);
+ if (indexStart > 2) {
+ queue[0] = --indexStart;
+ queue[indexStart] = index;
+ } else {
+ queue[indexEnd] = index;
+ queue[0] = ++indexEnd;
+ }
+ }
+
+ public void process() {
+ LongArraySet set = new LongArraySet();
+ while (!queues.isEmpty()) {
+// ObjectIterator> iter = queues.long2ObjectEntrySet().fastIterator();
+// Long2ObjectMap.Entry entry = iter.next();
+// long index = entry.getLongKey();
+// int X = MathMan.unpairIntX(index);
+// int Z = MathMan.unpairIntY(index);
+// // check that adjacent chunks aren;t being processed
+//
+// char[] queue = entry.getValue();
+// long[][] visit = visits.get(index);
+// if (visit == null) {
+// visits.put(index, visit = new long[16][]);
+// }
+ }
+ }
+
+ private ConcurrentLinkedQueue queuePool = new ConcurrentLinkedQueue<>();
+
+ private char[] newQueue() {
+ char[] arr = queuePool.poll();
+ if (arr != null) {
+ arr[0] = 2;
+ arr[1] = 2;
+ return arr;
+ }
+ return new char[4096];
+ }
+
+ public void process4(int xx, int yy, int zz, char[] queue, long[] visit) {
+ char index;
+ while ((index = queue[0]) != queue[1]) {
+ queue[0]++;
+
+ char triple = queue[index];
+ int x = index & 15;
+ int z = (index >> 4) & 15;
+ int y = index >> 8;
+
+ int absX = xx + x;
+ int absY = yy + y;
+ int absZ = zz + z;
+
+ apply(xx + x, yy + y, zz + z);
+
+ int x1 = x, x2 = x;
+
+ // find start of scan-line
+ int i1 = index;
+ while (true) {
+ if (x1 < 0) {
+ // queue in west chunk
+ break;
+ }
+ if (get(visit, i1)) break;
+ // visit
+ set(visit, i1);
+
+ i1--;
+ x1--;
+ }
+ i1++;
+ x1++;
+
+ // find end of scan-line
+ int i2 = index;
+ while (true) {
+ if (x2 > 15) {
+ // queue in east chunk
+ break;
+ }
+ if (get(visit, i2)) break;
+ set(visit, i2);
+ i2++;
+ x2++;
+ }
+ i2--;
+ x2--;
+
+ // find start
+ }
+ }
+
+ public void apply(int x, int y, int z) {
+
+ }
+
+ public void process4(int X, int Z, char[][] queues, long[][] visit) {
+ int xx = X << 4;
+ int zz = Z << 4;
+
+ // TODO fetch instead of create
+ final BlockVector3[] dirs = directions;
+ char[][] dirQueues = new char[directions.length][];
+ while (true) {
+ boolean empty = true;
+ for (int layer = 0; layer < 16; layer++) {
+ char[] queue = queues[layer];
+ if (queue == null) continue;
+ char index;
+ while ((index = queue[0]) != queue[1]) {
+ queue[0]++;
+
+ char triple = queue[index];
+ int x = index & 15;
+ int z = (index >> 4) & 15;
+ int y = index >> 8;
+ }
+ queuePool.add(queue);
+ queues[layer] = null;
+ continue;
+ }
+
+ if (empty) break;
+ }
+ // empty queues
+
+// while (indexStart != indexEnd) {
+// char index = queue[indexStart++];
+// byte dirs = 0xF;
+// int x = index & 15;
+// int z = (index >> 4) & 15;
+// int y = index >> 8;
+//
+// int layer = y >> 4;
+// long[] visitBits = visit[layer];
+//
+// int x1 = x;
+// int x2 = x;
+//
+// // find start of scan-line
+// int i1 = index;
+// while (true) {
+// if (x1 < 0) {
+// // queue in adjacent chunk
+// break;
+// }
+// if (get(visitBits, i1--)) break;
+// x1--;
+// }
+// i1++;
+// x1++;
+//
+// // find end of scan-line
+// int i2 = index;
+// while (true) {
+// if (x2 > 15) {
+// // queue in adjacent chunk
+// break;
+// }
+// if (get(visitBits, i2++)) break;
+// x2++;
+// }
+// i2--;
+// x2--;
+//
+// boolean scanUp = false;
+// boolean scanDown = false;
+// boolean scanLeft = false;
+// boolean scanRight = false;
+//
+// for (int i = i1; i <= i2; i++) {
+// if (!scanDown && y > 0 && )
+// }
+//
+// for (int i=x1; i<=x2; i++) { // find scan-lines above this one
+// if (!inScanLine && y>0 && ip.getPixel(i,y-1)==color)
+// {push(i, y-1); inScanLine = true;}
+// else if (inScanLine && y>0 && ip.getPixel(i,y-1)!=color)
+// inScanLine = false;
+// }
+//
+// inScanLine = false;
+// for (int i=x1; i<=x2; i++) { // find scan-lines below this one
+// if (!inScanLine && y> 6] |= (1L << (i & 0x3F));
+ }
+
+ public boolean get(long[] bits, final int i) {
+ return (bits[i >> 6] & (1L << (i & 0x3F))) != 0;
+ }
+
+ public char getLocalIndex(int x, int y, int z) {
+ return (char) (x + (z << 4) + (y << 8));
+ }
+
+
+}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/math/BlockVector3.java b/worldedit-core/src/main/java/com/sk89q/worldedit/math/BlockVector3.java
index 8fb8da940..68ac4d813 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/math/BlockVector3.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/math/BlockVector3.java
@@ -22,43 +22,43 @@ package com.sk89q.worldedit.math;
import static com.google.common.base.Preconditions.checkArgument;
import com.google.common.collect.ComparisonChain;
+import com.sk89q.jnbt.CompoundTag;
+import com.sk89q.worldedit.extent.Extent;
import com.sk89q.worldedit.math.transform.AffineTransform;
+import com.sk89q.worldedit.world.biome.BiomeType;
+import com.sk89q.worldedit.world.block.BaseBlock;
+import com.sk89q.worldedit.world.block.BlockState;
+import javax.annotation.Nullable;
import java.util.Comparator;
/**
* An immutable 3-dimensional vector.
*/
-public class BlockVector3 {
+public abstract class BlockVector3 {
- public static final BlockVector3 ZERO = new BlockVector3(0, 0, 0);
- public static final BlockVector3 UNIT_X = new BlockVector3(1, 0, 0);
- public static final BlockVector3 UNIT_Y = new BlockVector3(0, 1, 0);
- public static final BlockVector3 UNIT_Z = new BlockVector3(0, 0, 1);
- public static final BlockVector3 UNIT_MINUS_X = new BlockVector3(-1, 0, 0);
- public static final BlockVector3 UNIT_MINUS_Y = new BlockVector3(0, -1, 0);
- public static final BlockVector3 UNIT_MINUS_Z = new BlockVector3(0, 0, -1);
- public static final BlockVector3 ONE = new BlockVector3(1, 1, 1);
+ public static final BlockVector3 ZERO = BlockVector3.at(0, 0, 0);
+ public static final BlockVector3 UNIT_X = BlockVector3.at(1, 0, 0);
+ public static final BlockVector3 UNIT_Y = BlockVector3.at(0, 1, 0);
+ public static final BlockVector3 UNIT_Z = BlockVector3.at(0, 0, 1);
+ public static final BlockVector3 UNIT_MINUS_X = BlockVector3.at(-1, 0, 0);
+ public static final BlockVector3 UNIT_MINUS_Y = BlockVector3.at(0, -1, 0);
+ public static final BlockVector3 UNIT_MINUS_Z = BlockVector3.at(0, 0, -1);
+ public static final BlockVector3 ONE = BlockVector3.at(1, 1, 1);
public static BlockVector3 at(double x, double y, double z) {
return at((int) Math.floor(x), (int) Math.floor(y), (int) Math.floor(z));
}
public static BlockVector3 at(int x, int y, int z) {
- return new BlockVector3(x, y, z);
+ return new BlockVector3Imp(x, y, z);
}
- // thread-safe initialization idiom
- private static final class YzxOrderComparator {
- private static final Comparator YZX_ORDER = (a, b) -> {
- //noinspection SuspiciousNameCombination
- return ComparisonChain.start()
- .compare(a.y, b.y)
- .compare(a.z, b.z)
- .compare(a.x, b.x)
- .result();
- };
- }
+ static final Comparator YZX_ORDER = (a, b) -> ComparisonChain.start()
+ .compare(a.getY(), b.getY())
+ .compare(a.getZ(), b.getZ())
+ .compare(a.getX(), b.getX())
+ .result();
/**
* Returns a comparator that sorts vectors first by Y, then Z, then X.
@@ -67,24 +67,7 @@ public class BlockVector3 {
* Useful for sorting by chunk block storage order.
*/
public static Comparator sortByCoordsYzx() {
- return YzxOrderComparator.YZX_ORDER;
- }
-
- protected int x, y, z;
-
- protected BlockVector3(){}
-
- /**
- * Construct an instance.
- *
- * @param x the X coordinate
- * @param y the Y coordinate
- * @param z the Z coordinate
- */
- protected BlockVector3(int x, int y, int z) {
- this.x = x;
- this.y = y;
- this.z = z;
+ return YZX_ORDER;
}
public MutableBlockVector3 setComponents(double x, double y, double z) {
@@ -96,37 +79,71 @@ public class BlockVector3 {
}
public MutableBlockVector3 mutX(double x) {
- return new MutableBlockVector3((int) x, y, z);
+ return new MutableBlockVector3((int) x, getY(), getZ());
}
public MutableBlockVector3 mutY(double y) {
- return new MutableBlockVector3(x, (int) y, z);
+ return new MutableBlockVector3(getX(), (int) y, getZ());
}
public MutableBlockVector3 mutZ(double z) {
- return new MutableBlockVector3(x, y, (int) z);
+ return new MutableBlockVector3(getX(), getY(), (int) z);
}
public MutableBlockVector3 mutX(int x) {
- return new MutableBlockVector3(x, y, z);
+ return new MutableBlockVector3(x, getY(), getZ());
}
public MutableBlockVector3 mutY(int y) {
- return new MutableBlockVector3(x, y, z);
+ return new MutableBlockVector3(getX(), y, getZ());
}
public MutableBlockVector3 mutZ(int z) {
- return new MutableBlockVector3(x, y, z);
+ return new MutableBlockVector3(getX(), getY(), z);
}
+ public BlockVector3 toImmutable() {
+ return BlockVector3.at(getX(), getY(), getZ());
+ }
+
+// /**
+// * Get the BlockVector3 to the north
+// * Normal use you would use north(this),
+// * To avoid constructing a new Vector, pass e.g. north(some MutableBlockVector3)
+// * There is no gaurantee it will use this provided vector
+// * @param orDefault the vector to use as the result
+// * @return BlockVector3
+// */
+// public BlockVector3 north(BlockVector3 orDefault) {
+// return orDefault.setComponents(getX(), getY(), getZ() - 1);
+// }
+//
+// public BlockVector3 east(BlockVector3 orDefault) {
+// return orDefault.setComponents(getX() + 1, getY(), getZ());
+// }
+//
+// public BlockVector3 south(BlockVector3 orDefault) {
+// return orDefault.setComponents(getX(), getY(), getZ() + 1);
+// }
+//
+// public BlockVector3 west(BlockVector3 orDefault) {
+// return orDefault.setComponents(getX() - 1, getY(), getZ());
+// }
+//
+// public BlockVector3 up(BlockVector3 orDefault) {
+// return orDefault.setComponents(getX(), getY() + 1, getZ());
+// }
+//
+// public BlockVector3 down(BlockVector3 orDefault) {
+// return orDefault.setComponents(getX(), getY() - 1, getZ());
+// }
+
/**
* Get the X coordinate.
*
* @return the x coordinate
*/
- public int getX() {
- return x;
- }
+ public abstract int getX();
/**
* Get the X coordinate.
@@ -134,7 +151,7 @@ public class BlockVector3 {
* @return the x coordinate
*/
public int getBlockX() {
- return x;
+ return getX();
}
/**
@@ -144,7 +161,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 withX(int x) {
- return BlockVector3.at(x, y, z);
+ return BlockVector3.at(x, getY(), getZ());
}
/**
@@ -152,9 +169,7 @@ public class BlockVector3 {
*
* @return the y coordinate
*/
- public int getY() {
- return y;
- }
+ public abstract int getY();
/**
* Get the Y coordinate.
@@ -162,7 +177,7 @@ public class BlockVector3 {
* @return the y coordinate
*/
public int getBlockY() {
- return y;
+ return getY();
}
/**
@@ -172,7 +187,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 withY(int y) {
- return BlockVector3.at(x, y, z);
+ return BlockVector3.at(getX(), y, getZ());
}
/**
@@ -180,9 +195,7 @@ public class BlockVector3 {
*
* @return the z coordinate
*/
- public int getZ() {
- return z;
- }
+ public abstract int getZ();
/**
* Get the Z coordinate.
@@ -190,7 +203,7 @@ public class BlockVector3 {
* @return the z coordinate
*/
public int getBlockZ() {
- return z;
+ return getZ();
}
/**
@@ -200,7 +213,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 withZ(int z) {
- return BlockVector3.at(x, y, z);
+ return BlockVector3.at(getX(), getY(), z);
}
/**
@@ -210,7 +223,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 add(BlockVector3 other) {
- return add(other.x, other.y, other.z);
+ return add(other.getX(), other.getY(), other.getZ());
}
/**
@@ -222,7 +235,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 add(int x, int y, int z) {
- return BlockVector3.at(this.x + x, this.y + y, this.z + z);
+ return BlockVector3.at(this.getX() + x, this.getY() + y, this.getZ() + z);
}
/**
@@ -233,12 +246,12 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 add(BlockVector3... others) {
- int newX = x, newY = y, newZ = z;
+ int newX = getX(), newY = getY(), newZ = getZ();
for (BlockVector3 other : others) {
- newX += other.x;
- newY += other.y;
- newZ += other.z;
+ newX += other.getX();
+ newY += other.getY();
+ newZ += other.getZ();
}
return BlockVector3.at(newX, newY, newZ);
@@ -252,7 +265,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 subtract(BlockVector3 other) {
- return subtract(other.x, other.y, other.z);
+ return subtract(other.getX(), other.getY(), other.getZ());
}
/**
@@ -265,7 +278,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 subtract(int x, int y, int z) {
- return BlockVector3.at(this.x - x, this.y - y, this.z - z);
+ return BlockVector3.at(this.getX() - x, this.getY() - y, this.getZ() - z);
}
/**
@@ -276,12 +289,12 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 subtract(BlockVector3... others) {
- int newX = x, newY = y, newZ = z;
+ int newX = getX(), newY = getY(), newZ = getZ();
for (BlockVector3 other : others) {
- newX -= other.x;
- newY -= other.y;
- newZ -= other.z;
+ newX -= other.getX();
+ newY -= other.getY();
+ newZ -= other.getZ();
}
return BlockVector3.at(newX, newY, newZ);
@@ -294,7 +307,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 multiply(BlockVector3 other) {
- return multiply(other.x, other.y, other.z);
+ return multiply(other.getX(), other.getY(), other.getZ());
}
/**
@@ -306,7 +319,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 multiply(int x, int y, int z) {
- return BlockVector3.at(this.x * x, this.y * y, this.z * z);
+ return BlockVector3.at(this.getX() * x, this.getY() * y, this.getZ() * z);
}
/**
@@ -316,12 +329,12 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 multiply(BlockVector3... others) {
- int newX = x, newY = y, newZ = z;
+ int newX = getX(), newY = getY(), newZ = getZ();
for (BlockVector3 other : others) {
- newX *= other.x;
- newY *= other.y;
- newZ *= other.z;
+ newX *= other.getX();
+ newY *= other.getY();
+ newZ *= other.getZ();
}
return BlockVector3.at(newX, newY, newZ);
@@ -344,7 +357,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 divide(BlockVector3 other) {
- return divide(other.x, other.y, other.z);
+ return divide(other.getX(), other.getY(), other.getZ());
}
/**
@@ -356,7 +369,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 divide(int x, int y, int z) {
- return BlockVector3.at(this.x / x, this.y / y, this.z / z);
+ return BlockVector3.at(this.getX() / x, this.getY() / y, this.getZ() / z);
}
/**
@@ -384,7 +397,7 @@ public class BlockVector3 {
* @return length, squared
*/
public int lengthSq() {
- return x * x + y * y + z * z;
+ return getX() * getX() + getY() * getY() + getZ() * getZ();
}
/**
@@ -404,9 +417,9 @@ public class BlockVector3 {
* @return distance
*/
public int distanceSq(BlockVector3 other) {
- int dx = other.x - x;
- int dy = other.y - y;
- int dz = other.z - z;
+ int dx = other.getX() - getX();
+ int dy = other.getY() - getY();
+ int dz = other.getZ() - getZ();
return dx * dx + dy * dy + dz * dz;
}
@@ -418,9 +431,9 @@ public class BlockVector3 {
*/
public BlockVector3 normalize() {
double len = length();
- double x = this.x / len;
- double y = this.y / len;
- double z = this.z / len;
+ double x = this.getX() / len;
+ double y = this.getY() / len;
+ double z = this.getZ() / len;
return BlockVector3.at(x, y, z);
}
@@ -431,7 +444,7 @@ public class BlockVector3 {
* @return the dot product of this and the other vector
*/
public double dot(BlockVector3 other) {
- return x * other.x + y * other.y + z * other.z;
+ return getX() * other.getX() + getY() * other.getY() + getZ() * other.getZ();
}
/**
@@ -441,10 +454,10 @@ public class BlockVector3 {
* @return the cross product of this and the other vector
*/
public BlockVector3 cross(BlockVector3 other) {
- return new BlockVector3(
- y * other.z - z * other.y,
- z * other.x - x * other.z,
- x * other.y - y * other.x
+ return new BlockVector3Imp(
+ getY() * other.getZ() - getZ() * other.getY(),
+ getZ() * other.getX() - getX() * other.getZ(),
+ getX() * other.getY() - getY() * other.getX()
);
}
@@ -456,7 +469,7 @@ public class BlockVector3 {
* @return true if the vector is contained
*/
public boolean containedWithin(BlockVector3 min, BlockVector3 max) {
- return x >= min.x && x <= max.x && y >= min.y && y <= max.y && z >= min.z && z <= max.z;
+ return getX() >= min.getX() && getX() <= max.getX() && getY() >= min.getY() && getY() <= max.getY() && getZ() >= min.getZ() && getZ() <= max.getZ();
}
/**
@@ -468,11 +481,11 @@ public class BlockVector3 {
*/
public BlockVector3 clampY(int min, int max) {
checkArgument(min <= max, "minimum cannot be greater than maximum");
- if (y < min) {
- return BlockVector3.at(x, min, z);
+ if (getY() < min) {
+ return BlockVector3.at(getX(), min, getZ());
}
- if (y > max) {
- return BlockVector3.at(x, max, z);
+ if (getY() > max) {
+ return BlockVector3.at(getX(), max, getZ());
}
return this;
}
@@ -516,7 +529,7 @@ public class BlockVector3 {
* @return a new vector
*/
public BlockVector3 abs() {
- return BlockVector3.at(Math.abs(x), Math.abs(y), Math.abs(z));
+ return BlockVector3.at(Math.abs(getX()), Math.abs(getY()), Math.abs(getZ()));
}
/**
@@ -532,8 +545,8 @@ public class BlockVector3 {
*/
public BlockVector3 transform2D(double angle, double aboutX, double aboutZ, double translateX, double translateZ) {
angle = Math.toRadians(angle);
- double x = this.x - aboutX;
- double z = this.z - aboutZ;
+ double x = this.getX() - aboutX;
+ double z = this.getZ() - aboutZ;
double cos = Math.cos(angle);
double sin = Math.sin(angle);
double x2 = x * cos - z * sin;
@@ -541,7 +554,7 @@ public class BlockVector3 {
return BlockVector3.at(
x2 + aboutX + translateX,
- y,
+ getY(),
z2 + aboutZ + translateZ
);
}
@@ -587,10 +600,10 @@ public class BlockVector3 {
* @return minimum
*/
public BlockVector3 getMinimum(BlockVector3 v2) {
- return new BlockVector3(
- Math.min(x, v2.x),
- Math.min(y, v2.y),
- Math.min(z, v2.z)
+ return new BlockVector3Imp(
+ Math.min(getX(), v2.getX()),
+ Math.min(getY(), v2.getY()),
+ Math.min(getZ(), v2.getZ())
);
}
@@ -601,44 +614,110 @@ public class BlockVector3 {
* @return maximum
*/
public BlockVector3 getMaximum(BlockVector3 v2) {
- return new BlockVector3(
- Math.max(x, v2.x),
- Math.max(y, v2.y),
- Math.max(z, v2.z)
+ return new BlockVector3Imp(
+ Math.max(getX(), v2.getX()),
+ Math.max(getY(), v2.getY()),
+ Math.max(getZ(), v2.getZ())
);
}
+ /*
+ Methods for getting/setting blocks
+
+ Why are these methods here?
+ - Getting a block at a position requires various operations
+ (bounds checks, cache checks, ensuring loaded chunk, get ChunkSection, etc.)
+ - When iterating over a region, it will provide custom BlockVector3 positions
+ - These override the below set/get and avoid lookups (as the iterator shifts it to the chunk level)
+ */
+
+ public boolean setOrdinal(Extent orDefault, int ordinal) {
+ return orDefault.setBlock(this, BlockState.getFromOrdinal(ordinal));
+ }
+
+ public boolean setBlock(Extent orDefault, BlockState state) {
+ return orDefault.setBlock(this, state);
+ }
+
+ public boolean setFullBlock(Extent orDefault, BaseBlock block) {
+ return orDefault.setBlock(this, block);
+ }
+
+ public boolean setBiome(Extent orDefault, BiomeType biome) {
+ return orDefault.setBiome(getX(), getY(), getZ(), biome);
+ }
+
+ public int getOrdinal(Extent orDefault) {
+ return getBlock(orDefault).getOrdinal();
+ }
+
+ public char getOrdinalChar(Extent orDefault) {
+ return (char) getOrdinal(orDefault);
+ }
+
+ public BlockState getBlock(Extent orDefault) {
+ return orDefault.getBlock(this);
+ }
+
+ public BaseBlock getFullBlock(Extent orDefault) {
+ return orDefault.getFullBlock(this);
+ }
+
+ public CompoundTag getNbtData(Extent orDefault) {
+ return orDefault.getFullBlock(getX(), getY(), getZ()).getNbtData();
+ }
+
+ public BlockState getOrdinalBelow(Extent orDefault) {
+ return orDefault.getBlock(getX(), getY() - 1, getZ());
+ }
+
+ public BlockState getStateAbove(Extent orDefault) {
+ return orDefault.getBlock(getX(), getY() + 1, getZ());
+ }
+
+ public BlockState getStateRelativeY(Extent orDefault, final int y) {
+ return orDefault.getBlock(getX(), getY() + y, getZ());
+ }
+
+
+ /*
+ Adapt
+ */
+
/**
* Creates a 2D vector by dropping the Y component from this vector.
*
* @return a new {@link BlockVector2}
*/
public BlockVector2 toBlockVector2() {
- return BlockVector2.at(x, z);
+ return BlockVector2.at(getX(), getZ());
}
public Vector3 toVector3() {
- return Vector3.at(x, y, z);
+ return Vector3.at(getX(), getY(), getZ());
}
@Override
- public boolean equals(Object obj) {
+ public final boolean equals(Object obj) {
if (!(obj instanceof BlockVector3)) {
return false;
}
- BlockVector3 other = (BlockVector3) obj;
- return other.x == this.x && other.y == this.y && other.z == this.z;
+ return equals((BlockVector3) obj);
+ }
+
+ public final boolean equals(BlockVector3 other) {
+ return other.getX() == this.getX() && other.getY() == this.getY() && other.getZ() == this.getZ();
}
@Override
public int hashCode() {
- return (x ^ (z << 12)) ^ (y << 24);
+ return (getX() ^ (getZ() << 12)) ^ (getY() << 24);
}
@Override
public String toString() {
- return "(" + x + ", " + y + ", " + z + ")";
+ return "(" + getX() + ", " + getY() + ", " + getZ() + ")";
}
}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/math/BlockVector3Imp.java b/worldedit-core/src/main/java/com/sk89q/worldedit/math/BlockVector3Imp.java
new file mode 100644
index 000000000..dd7399c64
--- /dev/null
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/math/BlockVector3Imp.java
@@ -0,0 +1,92 @@
+/*
+ * WorldEdit, a Minecraft world manipulation toolkit
+ * Copyright (C) sk89q
+ * Copyright (C) WorldEdit team and contributors
+ *
+ * This program is free software: you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as published by the
+ * Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
+ * for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program. If not, see .
+ */
+
+package com.sk89q.worldedit.math;
+
+import static com.google.common.base.Preconditions.checkArgument;
+
+import com.google.common.collect.ComparisonChain;
+import com.sk89q.worldedit.math.transform.AffineTransform;
+
+import java.util.Comparator;
+
+/**
+ * An immutable 3-dimensional vector.
+ */
+public final class BlockVector3Imp extends BlockVector3 {
+
+ public static final BlockVector3Imp ZERO = new BlockVector3Imp(0, 0, 0);
+ public static final BlockVector3Imp UNIT_X = new BlockVector3Imp(1, 0, 0);
+ public static final BlockVector3Imp UNIT_Y = new BlockVector3Imp(0, 1, 0);
+ public static final BlockVector3Imp UNIT_Z = new BlockVector3Imp(0, 0, 1);
+ public static final BlockVector3Imp ONE = new BlockVector3Imp(1, 1, 1);
+
+ public static BlockVector3Imp at(double x, double y, double z) {
+ return at((int) Math.floor(x), (int) Math.floor(y), (int) Math.floor(z));
+ }
+
+ public static BlockVector3Imp at(int x, int y, int z) {
+ return new BlockVector3Imp(x, y, z);
+ }
+
+ private final int x, y, z;
+
+ /**
+ * Construct an instance.
+ *
+ * @param x the X coordinate
+ * @param y the Y coordinate
+ * @param z the Z coordinate
+ */
+ protected BlockVector3Imp(int x, int y, int z) {
+ this.x = x;
+ this.y = y;
+ this.z = z;
+ }
+
+ @Override
+ public final int getX() {
+ return x;
+ }
+
+ @Override
+ public final int getY() {
+ return y;
+ }
+
+ @Override
+ public final int getZ() {
+ return z;
+ }
+
+ @Override
+ public int hashCode() {
+ return (getX() ^ (getZ() << 12)) ^ (getY() << 24);
+ }
+
+ @Override
+ public final BlockVector3 toImmutable() {
+ return this;
+ }
+
+ @Override
+ public String toString() {
+ return "(" + getX() + ", " + getY() + ", " + getZ() + ")";
+ }
+}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableBlockVector3.java b/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableBlockVector3.java
index 88eb28a71..48296a3a6 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableBlockVector3.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableBlockVector3.java
@@ -1,25 +1,37 @@
package com.sk89q.worldedit.math;
+import com.boydti.fawe.FaweCache;
+
public class MutableBlockVector3 extends BlockVector3 {
- private static ThreadLocal MUTABLE_CACHE = ThreadLocal.withInitial(() -> new MutableBlockVector3());
+ public static MutableBlockVector3 at(double x, double y, double z) {
+ return at((int) Math.floor(x), (int) Math.floor(y), (int) Math.floor(z));
+ }
+
+ public static MutableBlockVector3 at(int x, int y, int z) {
+ return new MutableBlockVector3(x, y, z);
+ }
public static MutableBlockVector3 get(int x, int y, int z) {
- return MUTABLE_CACHE.get().setComponents(x, y, z);
+ return FaweCache.MUTABLE_BLOCKVECTOR3.get().setComponents(x, y, z);
}
public MutableBlockVector3() {}
public MutableBlockVector3(BlockVector3 other) {
- super(other.getX(), other.getY(), other.getZ());
+ this(other.getX(), other.getY(), other.getZ());
}
public MutableBlockVector3 setComponents(BlockVector3 other) {
return setComponents(other.getBlockX(), other.getBlockY(), other.getBlockZ());
}
+ private int x,y,z;
+
public MutableBlockVector3(int x, int y, int z) {
- super(x, y, z);
+ this.x = x;
+ this.y = y;
+ this.z = z;
}
@Override
@@ -30,6 +42,21 @@ public class MutableBlockVector3 extends BlockVector3 {
return this;
}
+ @Override
+ public final int getX() {
+ return x;
+ }
+
+ @Override
+ public final int getY() {
+ return y;
+ }
+
+ @Override
+ public final int getZ() {
+ return z;
+ }
+
@Override
public MutableBlockVector3 mutX(double x) {
this.x = (int) x;
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableVector3.java b/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableVector3.java
index 27edc3437..27c9fd75f 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableVector3.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/math/MutableVector3.java
@@ -1,7 +1,17 @@
package com.sk89q.worldedit.math;
+import com.boydti.fawe.FaweCache;
+
public class MutableVector3 extends Vector3 {
+ public static MutableVector3 get(int x, int y, int z) {
+ return FaweCache.MUTABLE_VECTOR3.get().setComponents(x, y, z);
+ }
+
+ public static MutableVector3 get(double x, double y, double z) {
+ return FaweCache.MUTABLE_VECTOR3.get().setComponents(x, y, z);
+ }
+
public MutableVector3() {}
public MutableVector3(double x, double y, double z) {
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CuboidRegion.java b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CuboidRegion.java
index e78422cd8..8e3840772 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CuboidRegion.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CuboidRegion.java
@@ -19,6 +19,11 @@
package com.sk89q.worldedit.regions;
+import com.boydti.fawe.beta.ChunkFilterBlock;
+import com.boydti.fawe.beta.Filter;
+import com.boydti.fawe.beta.IChunk;
+import com.boydti.fawe.beta.IChunkGet;
+import com.boydti.fawe.beta.IChunkSet;
import com.boydti.fawe.config.Settings;
import com.boydti.fawe.object.collection.BlockVectorSet;
import com.sk89q.worldedit.math.BlockVector2;
@@ -394,14 +399,8 @@ public class CuboidRegion extends AbstractRegion implements FlatRegion {
public boolean contains(int x, int z) {
return x >= this.minX && x <= this.maxX && z >= this.minZ && z <= this.maxZ;
}
- @Override
- public boolean contains(BlockVector3 position) {
- BlockVector3 min = getMinimumPoint();
- BlockVector3 max = getMaximumPoint();
- return position.containedWithin(min, max);
- }
- @NotNull @Override
+ @Override
public Iterator iterator() {
if (Settings.IMP.HISTORY.COMPRESSION_LEVEL >= 9 || useOldIterator) {
return iterator_old();
@@ -612,5 +611,50 @@ public class CuboidRegion extends AbstractRegion implements FlatRegion {
return new CuboidRegion(origin.subtract(size), origin.add(size));
}
+ @Override
+ public int getMinY() {
+ return minY;
+ }
+ @Override
+ public int getMaxY() {
+ return maxY;
+ }
+
+ @Override
+ public void filter(final IChunk chunk, final Filter filter, ChunkFilterBlock block, final IChunkGet get, final IChunkSet set) {
+ int X = chunk.getX();
+ int Z = chunk.getZ();
+ block = block.init(X, Z, get);
+
+ if ((minX + 15) >> 4 <= X && (maxX - 15) >> 4 >= X && (minZ + 15) >> 4 <= Z && (maxZ - 15) >> 4 >= Z) {
+ filter(chunk, filter, block, get, set, minY, maxY);
+ return;
+ }
+ int localMinX = Math.max(minX, X << 4) & 15;
+ int localMaxX = Math.min(maxX, 15 + X << 4) & 15;
+ int localMinZ = Math.max(minZ, Z << 4) & 15;
+ int localMaxZ = Math.min(maxZ, 15 + Z << 4) & 15;
+
+ int yStart = (minY & 15);
+ int yEnd = (maxY & 15);
+
+ int minSection = minY >> 4;
+ int maxSection = maxY >> 4;
+ if (minSection == maxSection) {
+ filter(chunk, filter, block, get, set, minSection, localMinX, yStart, localMinZ, localMaxX, yEnd, localMaxZ);
+ return;
+ }
+ if (yStart != 0) {
+ filter(chunk, filter, block, get, set, minSection, localMinX, yStart, localMinZ, localMaxX, 15, localMaxZ);
+ minSection++;
+ }
+ if (yEnd != 15) {
+ filter(chunk, filter, block, get, set, minSection, localMinX, 0, localMinZ, localMaxX, 15, localMaxZ);
+ maxSection--;
+ }
+ for (int layer = minSection; layer < maxSection; layer++) {
+ filter(chunk, filter, block, get, set, layer, localMinX, yStart, localMinZ, localMaxX, yEnd, localMaxZ);
+ }
+ }
}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CylinderRegion.java b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CylinderRegion.java
index 263c2b2a1..ae33ef8c8 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CylinderRegion.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/CylinderRegion.java
@@ -20,6 +20,12 @@
package com.sk89q.worldedit.regions;
import static com.google.common.base.Preconditions.checkNotNull;
+
+import com.boydti.fawe.beta.ChunkFilterBlock;
+import com.boydti.fawe.beta.Filter;
+import com.boydti.fawe.beta.IChunk;
+import com.boydti.fawe.beta.IChunkGet;
+import com.boydti.fawe.beta.IChunkSet;
import com.sk89q.worldedit.extent.Extent;
import com.sk89q.worldedit.math.BlockVector2;
import com.sk89q.worldedit.math.BlockVector3;
@@ -287,26 +293,22 @@ public class CylinderRegion extends AbstractRegion implements FlatRegion {
minY += changeY;
}
- /**
- * Checks to see if a point is inside this region.
- */
@Override
- public boolean contains(BlockVector3 position) {
- final int blockY = position.getBlockY();
- if (blockY < minY || blockY > maxY) {
+ public boolean contains(int x, int y, int z) {
+ if (y < minY || y > maxY) {
return false;
}
- //todo the following lines can possibly be removed and replaced with upstream
- int px = position.getBlockX();
- int pz = position.getBlockZ();
+ return contains(x, z);
+ }
- double dx = Math.abs(px - center.getBlockX()) * radiusInverse.getX();
- double dz = Math.abs(pz - center.getBlockZ()) * radiusInverse.getZ();
+ @Override
+ public boolean contains(int x, int z) {
+ double dx = Math.abs(x - center.getBlockX()) * radiusInverse.getX();
+ double dz = Math.abs(z - center.getBlockZ()) * radiusInverse.getZ();
return dx * dx + dz * dz <= 1;
}
-
/**
* Sets the height of the cylinder to fit the specified Y.
*
@@ -361,6 +363,16 @@ public class CylinderRegion extends AbstractRegion implements FlatRegion {
return Polygons.polygonizeCylinder(center, radius, maxPoints);
}
+ @Override
+ public int getMinY() {
+ return minY;
+ }
+
+ @Override
+ public int getMaxY() {
+ return maxY;
+ }
+
/**
* Return a new instance with the given center and radius in the X and Z
* axes with a Y that extends from the bottom of the extent to the top
@@ -380,4 +392,16 @@ public class CylinderRegion extends AbstractRegion implements FlatRegion {
return new CylinderRegion(center, radiusVec, minY, maxY);
}
+ @Override
+ public void filter(final IChunk chunk, final Filter filter, final ChunkFilterBlock block, final IChunkGet get, final IChunkSet set) {
+ int bcx = chunk.getX() >> 4;
+ int bcz = chunk.getZ() >> 4;
+ int tcx = bcx + 15;
+ int tcz = bcz + 15;
+ if (contains(bcx, bcz) && contains(tcx, tcz)) {
+ filter(chunk, filter, block, get, set, minY, maxY);
+ return;
+ }
+ super.filter(chunk, filter, block, get, set);
+ }
}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/EllipsoidRegion.java b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/EllipsoidRegion.java
index c1184afb9..a84a1aa62 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/EllipsoidRegion.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/EllipsoidRegion.java
@@ -19,6 +19,13 @@
package com.sk89q.worldedit.regions;
+
+import com.boydti.fawe.beta.ChunkFilterBlock;
+import com.boydti.fawe.beta.Filter;
+import com.boydti.fawe.beta.IChunk;
+import com.boydti.fawe.beta.IChunkGet;
+import com.boydti.fawe.beta.IChunkSet;
+import com.boydti.fawe.util.MathMan;
import com.sk89q.worldedit.math.BlockVector2;
import com.sk89q.worldedit.math.BlockVector3;
import com.sk89q.worldedit.math.Vector3;
@@ -44,6 +51,7 @@ public class EllipsoidRegion extends AbstractRegion {
private Vector3 radius;
private Vector3 radiusSqr;
+ private Vector3 inverseRadius;
private int radiusLengthSqr;
private boolean sphere;
@@ -184,6 +192,7 @@ public class EllipsoidRegion extends AbstractRegion {
} else {
this.sphere = false;
}
+ inverseRadius = Vector3.ONE.divide(radius);
}
@Override
@@ -210,30 +219,50 @@ public class EllipsoidRegion extends AbstractRegion {
return chunks;
}
+ @Override
+ public boolean contains(int x, int y, int z) {
+ int cx = x - center.getBlockX();
+ int cx2 = cx * cx;
+ if (cx2 > radiusSqr.getBlockX()) {
+ return false;
+ }
+ int cz = z - center.getBlockZ();
+ int cz2 = cz * cz;
+ if (cz2 > radiusSqr.getBlockZ()) {
+ return false;
+ }
+ int cy = y - center.getBlockY();
+ int cy2 = cy * cy;
+ if (radiusSqr.getBlockY() < 255 && cy2 > radiusSqr.getBlockY()) {
+ return false;
+ }
+ if (sphere) {
+ return cx2 + cy2 + cz2 <= radiusLengthSqr;
+ }
+ double cxd = cx2 * inverseRadius.getX();
+ double cyd = cy2 * inverseRadius.getY();
+ double czd = cz2 * inverseRadius.getZ();
+ return cxd + cyd + czd <= 1;
+ }
+
@Override
- public boolean contains(BlockVector3 position) {
- int cx = position.getBlockX() - center.getBlockX();
+ public boolean contains(int x, int z) {
+ int cx = x - center.getBlockX();
int cx2 = cx * cx;
if (cx2 > radiusSqr.getBlockX()) {
return false;
}
- int cz = position.getBlockZ() - center.getBlockZ();
+ int cz = z - center.getBlockZ();
int cz2 = cz * cz;
if (cz2 > radiusSqr.getBlockZ()) {
return false;
}
- int cy = position.getBlockY() - center.getBlockY();
- int cy2 = cy * cy;
- if (radiusSqr.getBlockY() < 255 && cy2 > radiusSqr.getBlockY()) {
- return false;
- }
if (sphere) {
- return cx2 + cy2 + cz2 <= radiusLengthSqr;
+ return cx2 + cz2 <= radiusLengthSqr;
}
- double cxd = (double) cx / radius.getBlockX();
- double cyd = (double) cy / radius.getBlockY();
- double czd = (double) cz / radius.getBlockZ();
- return cxd * cxd + cyd * cyd + czd * czd <= 1;
+ double cxd = cx2 * inverseRadius.getX();
+ double czd = cz2 * inverseRadius.getZ();
+ return cxd + czd <= 1;
}
/**
@@ -256,4 +285,113 @@ public class EllipsoidRegion extends AbstractRegion {
return (EllipsoidRegion) super.clone();
}
+ private void filterSpherePartial(int y1, int y2, int bx, int bz, Filter filter, ChunkFilterBlock block, IChunkGet get, IChunkSet set) {
+ int sectionStart = y1 >> 4;
+ int sectionEnd = y2 >> 4;
+
+ }
+
+ private void filterSpherePartial(int layer, int y1, int y2, int bx, int bz, Filter filter, ChunkFilterBlock block, IChunkGet get, IChunkSet set) {
+ int cx = center.getBlockX();
+ int cy = center.getBlockY();
+ int cz = center.getBlockZ();
+
+ block.init(get, set, layer);
+
+ int by = layer << 4;
+ int diffY;
+ for (int y = y1, yy = by + y1; y <= y2; y++, yy++) {
+ diffY = cy - yy;
+ int remainderY = radiusLengthSqr - (diffY * diffY);
+ if (remainderY >= 0) {
+ for (int z = 0; z < 16; z++) {
+ int zz = z + bz;
+ int diffZ = cz - zz;
+ int remainderZ = remainderY - (diffZ * diffZ);
+ if (remainderZ >= 0) {
+ int diffX = MathMan.usqrt(remainderZ);
+ int minX = Math.max(0, cx - diffX - bx);
+ int maxX = Math.min(15, cx + diffX - bx);
+ if (minX != maxX) {
+ block.filter(filter, minX, y, z, maxX, y, z);
+ }
+ }
+ }
+ }
+ }
+ }
+
+ @Override
+ public void filter(IChunk chunk, Filter filter, ChunkFilterBlock block, IChunkGet get, IChunkSet set) {
+ // Check bounds
+ // This needs to be able to perform 50M blocks/sec otherwise it becomes a bottleneck
+ int cx = center.getBlockX();
+ int cz = center.getBlockZ();
+ int bx = chunk.getX() << 4;
+ int bz = chunk.getZ() << 4;
+ int tx = bx + 15;
+ int tz = bz + 15;
+ int cx1 = bx - cx;
+ int cx2 = tx - cx;
+ int cxMax, cxMin;
+ if (cx1 < cx2) {
+ cxMin = cx1;
+ cxMax = cx2;
+ } else {
+ cxMin = cx2;
+ cxMax = cx1;
+ }
+ int cxMin2 = cxMin * cxMin;
+ int cxMax2 = cxMax * cxMax;
+ int cz1 = bz - cz;
+ int cz2 = tz - cz;
+ int czMax, czMin;
+ if (cz1 < cz2) {
+ czMin = cz1;
+ czMax = cz2;
+ } else {
+ czMin = cz2;
+ czMax = cz1;
+ }
+ int czMin2 = czMin * czMin;
+ int czMax2 = czMax * czMax;
+
+
+ if (sphere) {
+ // Does not contain chunk
+ if (cxMin2 + czMin2 >= radiusLengthSqr) {
+ return;
+ }
+ int diffY2 = radiusLengthSqr - cxMax2 - czMax2;
+ // (shortcut) Contains all of certain layers
+ if (diffY2 >= 0) {
+ // Get the solid layers
+ int cy = center.getBlockY();
+ int diffYFull = MathMan.usqrt(diffY2);
+ int yBotFull = Math.max(0, cy - diffYFull);
+ int yTopFull = Math.min(255, cy + diffYFull);
+ // Set those layers
+ filter(chunk, filter, block, get, set, yBotFull, yTopFull);
+
+ // Fill the remaining layers
+ if (yBotFull != 0 || yTopFull != 255) {
+ int diffYPartial = MathMan.usqrt(radiusLengthSqr - cxMin * cxMin - czMin * czMin);
+
+ if (yBotFull != 0) {
+ int yBotPartial = Math.max(0, cy - diffYPartial);
+ filterSpherePartial(yBotPartial, yBotFull - 1, bx, bz, filter, block, get, set);
+ }
+
+ if (yTopFull != 255) {
+ int yTopPartial = Math.min(255, cy + diffYPartial);
+ filterSpherePartial(yTopFull + 1, yTopPartial - 1, bx, bz, filter, block, get, set);
+ }
+ }
+ }
+
+
+ } else {
+ super.filter(chunk, filter, block, get, set); // TODO optimize non spheres
+ }
+ }
}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/Region.java b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/Region.java
index 4076c6cd0..c3dc4d55a 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/Region.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/Region.java
@@ -19,12 +19,20 @@
package com.sk89q.worldedit.regions;
+import com.boydti.fawe.beta.ChunkFilterBlock;
+import com.boydti.fawe.beta.Filter;
+import com.boydti.fawe.beta.IChunk;
+import com.boydti.fawe.beta.IChunkGet;
+import com.boydti.fawe.beta.IChunkSet;
+import com.sk89q.worldedit.function.RegionFunction;
import com.sk89q.worldedit.math.BlockVector2;
import com.sk89q.worldedit.math.BlockVector3;
+import com.sk89q.worldedit.math.MutableBlockVector3;
import com.sk89q.worldedit.math.Vector3;
import com.sk89q.worldedit.world.World;
import javax.annotation.Nullable;
+import java.util.Iterator;
import java.util.List;
import java.util.Set;
@@ -128,7 +136,9 @@ public interface Region extends Iterable, Cloneable {
* @param position the position
* @return true if contained
*/
- boolean contains(BlockVector3 position);
+ default boolean contains(BlockVector3 position) {
+ return contains(position.getX(), position.getY(), position.getZ());
+ }
/**
* Get a list of chunks.
@@ -172,4 +182,63 @@ public interface Region extends Iterable, Cloneable {
* @return the points.
*/
List polygonize(int maxPoints);
+
+ default int getMinY() {
+ return getMinimumPoint().getY();
+ }
+
+ default int getMaxY() {
+ return getMaximumPoint().getY();
+ }
+
+ default void filter(final IChunk chunk, final Filter filter, ChunkFilterBlock block, final IChunkGet get, final IChunkSet set) {
+ int minSection = Math.max(0, getMinY() >> 4);
+ int maxSection = Math.min(15, getMaxY() >> 4);
+ for (int layer = minSection; layer <= maxSection; layer++) {
+ if (!get.hasSection(layer) || !filter.appliesLayer(chunk, layer)) return;
+ block = block.init(get, set, layer);
+ block.filter(filter, this);
+ }
+ }
+
+ default void filter(final IChunk chunk, final Filter filter, ChunkFilterBlock block, final IChunkGet get, final IChunkSet set, final int minY, final int maxY) {
+ int minSection = minY >> 4;
+ int maxSection = maxY >> 4;
+ int yStart = (minY & 15);
+ int yEnd = (maxY & 15);
+ if (minSection == maxSection) {
+ filter(chunk, filter, block, get, set, minSection, yStart, yEnd);
+ return;
+ }
+ if (yStart != 0) {
+ filter(chunk, filter, block, get, set, minSection, yStart, 15);
+ minSection++;
+ }
+ if (yEnd != 15) {
+ filter(chunk, filter, block, get, set, minSection, 0, yEnd);
+ maxSection--;
+ }
+ for (int layer = minSection; layer < maxSection; layer++) {
+ filter(chunk, filter, block, get, set, layer);
+ }
+ return;
+ }
+
+ default void filter(final IChunk chunk, final Filter filter, ChunkFilterBlock block, final IChunkGet get, final IChunkSet set, int layer) {
+ if (!get.hasSection(layer) || !filter.appliesLayer(chunk, layer)) return;
+ block = block.init(get, set, layer);
+ block.filter(filter);
+ }
+
+ default void filter(final IChunk chunk, final Filter filter, ChunkFilterBlock block, final IChunkGet get, final IChunkSet set, int layer, int minX, int minY, int minZ, int maxX, int maxY, int maxZ) {
+ if (!get.hasSection(layer) || !filter.appliesLayer(chunk, layer)) return;
+ block = block.init(get, set, layer);
+ block.filter(filter, minX, minY, minZ, maxX, maxY, maxZ);
+ }
+
+ default void filter(final IChunk chunk, final Filter filter, ChunkFilterBlock block, final IChunkGet get, final IChunkSet set, int layer, int yStart, int yEnd) {
+ if (!get.hasSection(layer) || !filter.appliesLayer(chunk, layer)) return;
+ block = block.init(get, set, layer);
+ block.filter(filter, yStart, yEnd);
+ }
}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/RegionIntersection.java b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/RegionIntersection.java
index 9442deaca..cc1dbd954 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/RegionIntersection.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/RegionIntersection.java
@@ -19,9 +19,6 @@
package com.sk89q.worldedit.regions;
-import static com.google.common.base.Preconditions.checkArgument;
-import static com.google.common.base.Preconditions.checkNotNull;
-
import com.google.common.collect.Iterators;
import com.sk89q.worldedit.math.BlockVector3;
import com.sk89q.worldedit.world.World;
@@ -31,6 +28,9 @@ import java.util.Collections;
import java.util.Iterator;
import java.util.List;
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.base.Preconditions.checkNotNull;
+
/**
* An intersection of several other regions. Any location that is contained in one
* of the child regions is considered as contained by this region.
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/TransformRegion.java b/worldedit-core/src/main/java/com/sk89q/worldedit/regions/TransformRegion.java
deleted file mode 100644
index 911e40b8b..000000000
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/regions/TransformRegion.java
+++ /dev/null
@@ -1,191 +0,0 @@
-/*
- * WorldEdit, a Minecraft world manipulation toolkit
- * Copyright (C) sk89q
- * Copyright (C) WorldEdit team and contributors
- *
- * This program is free software: you can redistribute it and/or modify it
- * under the terms of the GNU Lesser General Public License as published by the
- * Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
- * for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program. If not, see .
- */
-
-package com.sk89q.worldedit.regions;
-
-import static com.google.common.base.Preconditions.checkNotNull;
-
-import com.sk89q.worldedit.math.BlockVector2;
-import com.sk89q.worldedit.math.BlockVector3;
-import com.sk89q.worldedit.math.Vector3;
-import com.sk89q.worldedit.math.transform.Identity;
-import com.sk89q.worldedit.math.transform.Transform;
-import com.sk89q.worldedit.world.World;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-
-import javax.annotation.Nullable;
-
-/**
- * Transforms another region according to a provided vector {@code Transform}.
- *
- * @see Transform
- */
-public class TransformRegion extends AbstractRegion {
-
- private final Region region;
- private Transform transform = new Identity();
-
- /**
- * Create a new instance.
- *
- * @param region the region
- * @param transform the transform
- */
- public TransformRegion(Region region, Transform transform) {
- this(null, region, transform);
- }
-
- /**
- * Create a new instance.
- *
- * @param world the world, which may be null
- * @param region the region
- * @param transform the transform
- */
- public TransformRegion(@Nullable World world, Region region, Transform transform) {
- super(world);
- checkNotNull(region);
- checkNotNull(transform);
- this.region = region;
- this.transform = transform;
- }
-
- /**
- * Get the untransformed, base region.
- *
- * @return the base region
- */
- public Region getRegion() {
- return region;
- }
-
- /**
- * Get the transform that is applied.
- *
- * @return the transform
- */
- public Transform getTransform() {
- return transform;
- }
-
- /**
- * Set the transform that is applied.
- *
- * @param transform the transform
- */
- public void setTransform(Transform transform) {
- checkNotNull(transform);
- this.transform = transform;
- }
-
- @Override
- public BlockVector3 getMinimumPoint() {
- return transform.apply(region.getMinimumPoint().toVector3()).toBlockPoint();
- }
-
- @Override
- public BlockVector3 getMaximumPoint() {
- return transform.apply(region.getMaximumPoint().toVector3()).toBlockPoint();
- }
-
- @Override
- public Vector3 getCenter() {
- return transform.apply(region.getCenter());
- }
-
- @Override
- public int getArea() {
- return region.getArea(); // Cannot transform this
- }
-
- @Override
- public int getWidth() {
- return getMaximumPoint().subtract(getMinimumPoint()).getBlockX() + 1;
- }
-
- @Override
- public int getHeight() {
- return getMaximumPoint().subtract(getMinimumPoint()).getBlockY() + 1;
- }
-
- @Override
- public int getLength() {
- return getMaximumPoint().subtract(getMinimumPoint()).getBlockZ() + 1;
- }
-
- @Override
- public void expand(BlockVector3... changes) throws RegionOperationException {
- throw new RegionOperationException("Can't expand a TransformedRegion");
- }
-
- @Override
- public void contract(BlockVector3... changes) throws RegionOperationException {
- throw new RegionOperationException("Can't contract a TransformedRegion");
- }
-
- @Override
- public void shift(BlockVector3 change) throws RegionOperationException {
- throw new RegionOperationException("Can't change a TransformedRegion");
- }
-
- @Override
- public boolean contains(BlockVector3 position) {
- return region.contains(transform.inverse().apply(position.toVector3()).toBlockPoint());
- }
-
- @Override
- public List polygonize(int maxPoints) {
- List origPoints = region.polygonize(maxPoints);
- List transformedPoints = new ArrayList<>();
- for (BlockVector2 vector : origPoints) {
- transformedPoints.add(transform.apply(vector.toVector3(0)).toVector2().toBlockPoint());
- }
- return transformedPoints;
- }
-
- @Override
- public Iterator iterator() {
- final Iterator it = region.iterator();
-
- return new Iterator() {
- @Override
- public boolean hasNext() {
- return it.hasNext();
- }
-
- @Override
- public BlockVector3 next() {
- BlockVector3 next = it.next();
- if (next != null) {
- return transform.apply(next.toVector3()).toBlockPoint();
- } else {
- return null;
- }
- }
-
- @Override
- public void remove() {
- it.remove();
- }
- };
- }
-}
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/session/request/RequestSelection.java b/worldedit-core/src/main/java/com/sk89q/worldedit/session/request/RequestSelection.java
index 9e37e4da0..7645154f8 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/session/request/RequestSelection.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/session/request/RequestSelection.java
@@ -23,6 +23,7 @@ import com.sk89q.worldedit.IncompleteRegionException;
import com.sk89q.worldedit.LocalSession;
import com.sk89q.worldedit.math.BlockVector2;
import com.sk89q.worldedit.math.BlockVector3;
+import com.sk89q.worldedit.math.MutableBlockVector3;
import com.sk89q.worldedit.math.Vector3;
import com.sk89q.worldedit.regions.NullRegion;
import com.sk89q.worldedit.regions.Region;
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/AbstractWorld.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/AbstractWorld.java
index 271c356ed..066bc7ea9 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/AbstractWorld.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/AbstractWorld.java
@@ -20,17 +20,16 @@
package com.sk89q.worldedit.world;
import com.sk89q.worldedit.WorldEditException;
+import com.sk89q.worldedit.function.mask.BlockMask;
import com.sk89q.worldedit.blocks.BaseItem;
import com.sk89q.worldedit.blocks.BaseItemStack;
import com.sk89q.worldedit.extension.platform.Platform;
-import com.sk89q.worldedit.function.mask.BlockTypeMask;
import com.sk89q.worldedit.function.mask.Mask;
import com.sk89q.worldedit.function.operation.Operation;
import com.sk89q.worldedit.math.BlockVector2;
import com.sk89q.worldedit.math.BlockVector3;
import com.sk89q.worldedit.math.Vector3;
import com.sk89q.worldedit.util.Direction;
-import com.sk89q.worldedit.world.block.BlockState;
import com.sk89q.worldedit.world.block.BlockStateHolder;
import com.sk89q.worldedit.world.block.BlockType;
import com.sk89q.worldedit.world.block.BlockTypes;
@@ -63,7 +62,7 @@ public abstract class AbstractWorld implements World {
@Override
public Mask createLiquidMask() {
- return new BlockTypeMask(this, BlockTypes.LAVA, BlockTypes.WATER);
+ return new BlockMask(this).add(BlockTypes.LAVA, BlockTypes.WATER);
}
@Override
@@ -90,11 +89,6 @@ public abstract class AbstractWorld implements World {
return false;
}
- @Override
- public BlockState getLazyBlock(BlockVector3 position) {
- return getBlock(position);
- }
-
@Override
public boolean queueBlockBreakEffect(Platform server, BlockVector3 position, BlockType blockType, double priority) {
if (taskId == -1) {
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/NullWorld.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/NullWorld.java
index c3ef611d8..ff1ac5edc 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/NullWorld.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/NullWorld.java
@@ -81,12 +81,12 @@ public class NullWorld extends AbstractWorld {
}
@Override
- public BiomeType getBiome(BlockVector2 position) {
+ public BiomeType getBiomeType(int x, int z) {
return BiomeTypes.THE_VOID;
}
@Override
- public boolean setBiome(BlockVector2 position, BiomeType biome) {
+ public boolean setBiome(int x, int y, int z, BiomeType biome) {
return false;
}
@@ -132,13 +132,18 @@ public class NullWorld extends AbstractWorld {
}
@Override
- public BlockState getBlock(BlockVector3 position) {
+ public BlockState getBlock(int x, int y, int z) {
return BlockTypes.AIR.getDefaultState();
}
@Override
- public BlockState getLazyBlock(BlockVector3 position) {
- return getBlock(position);
+ public BaseBlock getFullBlock(int x, int y, int z) {
+ return BlockTypes.AIR.getDefaultState().toBaseBlock();
+ }
+
+ @Override
+ public > boolean setBlock(int x, int y, int z, T block) throws WorldEditException {
+ return false;
}
@Override
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/SimpleWorld.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/SimpleWorld.java
index c6040cd60..04e7d05c1 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/SimpleWorld.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/SimpleWorld.java
@@ -61,7 +61,7 @@ public interface SimpleWorld extends World {
@Override
default BaseBlock getFullBlock(BlockVector3 position) {
- return getLazyBlock(position).toBaseBlock();
+ return getBlock(position).toBaseBlock();
}
@Override
@@ -74,7 +74,7 @@ public interface SimpleWorld extends World {
@Override
default Mask createLiquidMask() {
- return new BlockTypeMask(this, BlockTypes.LAVA, BlockTypes.WATER);
+ return new BlockMask(this).add(BlockTypes.LAVA, BlockTypes.WATER);
}
@Override
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/World.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/World.java
index cad0be0f5..c7dfcaa91 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/World.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/World.java
@@ -94,7 +94,9 @@ public interface World extends Extent {
* @param notifyAndLight true to to notify and light
* @return true if the block was successfully set (return value may not be accurate)
*/
- > boolean setBlock(BlockVector3 position, B block, boolean notifyAndLight) throws WorldEditException;
+ default > boolean setBlock(BlockVector3 position, B block, boolean notifyAndLight) throws WorldEditException {
+ return setBlock(position, block);
+ }
/**
* Notifies the simulation that the block at the given location has
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BaseBlock.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BaseBlock.java
index 0b0997992..c6d7b82e5 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BaseBlock.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BaseBlock.java
@@ -45,9 +45,8 @@ import java.util.Objects;
* may be missing.
*/
public class BaseBlock implements BlockStateHolder {
-
- private BlockState blockState;
- @Nullable protected CompoundTag nbtData;
+ private final BlockState blockState;
+ private final CompoundTag nbtData;
@Deprecated
public BaseBlock() {
@@ -70,6 +69,7 @@ public class BaseBlock implements BlockStateHolder {
*/
public BaseBlock(BlockState blockState) {
this.blockState = blockState;
+ nbtData = null;
}
/**
@@ -180,7 +180,7 @@ public class BaseBlock implements BlockStateHolder {
@Override
public void setNbtData(@Nullable CompoundTag nbtData) {
- this.nbtData = nbtData;
+ throw new UnsupportedOperationException("Immutable");
}
/**
@@ -232,7 +232,12 @@ public class BaseBlock implements BlockStateHolder {
}
@Override
- public BaseBlock toBaseBlock() {
+ public final char getOrdinalChar() {
+ return blockState.getOrdinalChar();
+ }
+
+ @Override
+ public final BaseBlock toBaseBlock() {
return this;
}
@@ -247,6 +252,10 @@ public class BaseBlock implements BlockStateHolder {
}
}
+ public BlockState toBlockState() {
+ return blockState;
+ }
+
@Override
public int hashCode() {
return getOrdinal();
@@ -254,7 +263,8 @@ public class BaseBlock implements BlockStateHolder {
@Override
public boolean apply(Extent extent, BlockVector3 get, BlockVector3 set) throws WorldEditException {
- return extent.setBlock(set, this);
+ set.setFullBlock(extent, this);
+ return true;
}
@Override
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockID.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockID.java
index 82f5c2979..1e9c5afa4 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockID.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockID.java
@@ -3,570 +3,570 @@ package com.sk89q.worldedit.world.block;
public class BlockID {
// Used for switch statements on blocks
public static final int __RESERVED__ = 0;
- public static final int ACACIA_BUTTON = 1;
- public static final int ACACIA_DOOR = 2;
- public static final int ACACIA_FENCE = 3;
- public static final int ACACIA_FENCE_GATE = 4;
- public static final int ACACIA_LEAVES = 5;
- public static final int ACACIA_LOG = 6;
- public static final int ACACIA_PLANKS = 7;
- public static final int ACACIA_PRESSURE_PLATE = 8;
- public static final int ACACIA_SAPLING = 9;
- public static final int ACACIA_SLAB = 10;
- public static final int ACACIA_STAIRS = 11;
- public static final int ACACIA_TRAPDOOR = 12;
- public static final int ACACIA_WOOD = 13;
- public static final int ACTIVATOR_RAIL = 14;
- public static final int AIR = 15;
- public static final int ALLIUM = 16;
- public static final int ANDESITE = 17;
- public static final int ANVIL = 18;
- public static final int ATTACHED_MELON_STEM = 19;
- public static final int ATTACHED_PUMPKIN_STEM = 20;
- public static final int AZURE_BLUET = 21;
- public static final int BARRIER = 22;
- public static final int BEACON = 23;
- public static final int BEDROCK = 24;
- public static final int BEETROOTS = 25;
- public static final int BIRCH_BUTTON = 26;
- public static final int BIRCH_DOOR = 27;
- public static final int BIRCH_FENCE = 28;
- public static final int BIRCH_FENCE_GATE = 29;
- public static final int BIRCH_LEAVES = 30;
- public static final int BIRCH_LOG = 31;
- public static final int BIRCH_PLANKS = 32;
- public static final int BIRCH_PRESSURE_PLATE = 33;
- public static final int BIRCH_SAPLING = 34;
- public static final int BIRCH_SLAB = 35;
- public static final int BIRCH_STAIRS = 36;
- public static final int BIRCH_TRAPDOOR = 37;
- public static final int BIRCH_WOOD = 38;
- public static final int BLACK_BANNER = 39;
- public static final int BLACK_BED = 40;
- public static final int BLACK_CARPET = 41;
- public static final int BLACK_CONCRETE = 42;
- public static final int BLACK_CONCRETE_POWDER = 43;
- public static final int BLACK_GLAZED_TERRACOTTA = 44;
- public static final int BLACK_SHULKER_BOX = 45;
- public static final int BLACK_STAINED_GLASS = 46;
- public static final int BLACK_STAINED_GLASS_PANE = 47;
- public static final int BLACK_TERRACOTTA = 48;
- public static final int BLACK_WALL_BANNER = 49;
- public static final int BLACK_WOOL = 50;
- public static final int BLUE_BANNER = 51;
- public static final int BLUE_BED = 52;
- public static final int BLUE_CARPET = 53;
- public static final int BLUE_CONCRETE = 54;
- public static final int BLUE_CONCRETE_POWDER = 55;
- public static final int BLUE_GLAZED_TERRACOTTA = 56;
- public static final int BLUE_ICE = 57;
- public static final int BLUE_ORCHID = 58;
- public static final int BLUE_SHULKER_BOX = 59;
- public static final int BLUE_STAINED_GLASS = 60;
- public static final int BLUE_STAINED_GLASS_PANE = 61;
- public static final int BLUE_TERRACOTTA = 62;
- public static final int BLUE_WALL_BANNER = 63;
- public static final int BLUE_WOOL = 64;
- public static final int BONE_BLOCK = 65;
- public static final int BOOKSHELF = 66;
- public static final int BRAIN_CORAL = 67;
- public static final int BRAIN_CORAL_BLOCK = 68;
- public static final int BRAIN_CORAL_FAN = 69;
- public static final int BRAIN_CORAL_WALL_FAN = 70;
- public static final int BREWING_STAND = 71;
- public static final int BRICK_SLAB = 72;
- public static final int BRICK_STAIRS = 73;
- public static final int BRICKS = 74;
- public static final int BROWN_BANNER = 75;
- public static final int BROWN_BED = 76;
- public static final int BROWN_CARPET = 77;
- public static final int BROWN_CONCRETE = 78;
- public static final int BROWN_CONCRETE_POWDER = 79;
- public static final int BROWN_GLAZED_TERRACOTTA = 80;
- public static final int BROWN_MUSHROOM = 81;
- public static final int BROWN_MUSHROOM_BLOCK = 82;
- public static final int BROWN_SHULKER_BOX = 83;
- public static final int BROWN_STAINED_GLASS = 84;
- public static final int BROWN_STAINED_GLASS_PANE = 85;
- public static final int BROWN_TERRACOTTA = 86;
- public static final int BROWN_WALL_BANNER = 87;
- public static final int BROWN_WOOL = 88;
- public static final int BUBBLE_COLUMN = 89;
- public static final int BUBBLE_CORAL = 90;
- public static final int BUBBLE_CORAL_BLOCK = 91;
- public static final int BUBBLE_CORAL_FAN = 92;
- public static final int BUBBLE_CORAL_WALL_FAN = 93;
- public static final int CACTUS = 94;
- public static final int CAKE = 95;
- public static final int CARROTS = 96;
- public static final int CARVED_PUMPKIN = 97;
- public static final int CAULDRON = 98;
- public static final int CAVE_AIR = 99;
- public static final int CHAIN_COMMAND_BLOCK = 100;
- public static final int CHEST = 101;
- public static final int CHIPPED_ANVIL = 102;
- public static final int CHISELED_QUARTZ_BLOCK = 103;
- public static final int CHISELED_RED_SANDSTONE = 104;
- public static final int CHISELED_SANDSTONE = 105;
- public static final int CHISELED_STONE_BRICKS = 106;
- public static final int CHORUS_FLOWER = 107;
- public static final int CHORUS_PLANT = 108;
- public static final int CLAY = 109;
- public static final int COAL_BLOCK = 110;
- public static final int COAL_ORE = 111;
- public static final int COARSE_DIRT = 112;
- public static final int COBBLESTONE = 113;
- public static final int COBBLESTONE_SLAB = 114;
- public static final int COBBLESTONE_STAIRS = 115;
- public static final int COBBLESTONE_WALL = 116;
- public static final int COBWEB = 117;
- public static final int COCOA = 118;
- public static final int COMMAND_BLOCK = 119;
- public static final int COMPARATOR = 120;
- public static final int CONDUIT = 121;
- public static final int CRACKED_STONE_BRICKS = 122;
- public static final int CRAFTING_TABLE = 123;
- public static final int CREEPER_HEAD = 124;
- public static final int CREEPER_WALL_HEAD = 125;
- public static final int CUT_RED_SANDSTONE = 126;
- public static final int CUT_SANDSTONE = 127;
- public static final int CYAN_BANNER = 128;
- public static final int CYAN_BED = 129;
- public static final int CYAN_CARPET = 130;
- public static final int CYAN_CONCRETE = 131;
- public static final int CYAN_CONCRETE_POWDER = 132;
- public static final int CYAN_GLAZED_TERRACOTTA = 133;
- public static final int CYAN_SHULKER_BOX = 134;
- public static final int CYAN_STAINED_GLASS = 135;
- public static final int CYAN_STAINED_GLASS_PANE = 136;
- public static final int CYAN_TERRACOTTA = 137;
- public static final int CYAN_WALL_BANNER = 138;
- public static final int CYAN_WOOL = 139;
- public static final int DAMAGED_ANVIL = 140;
- public static final int DANDELION = 141;
- public static final int DARK_OAK_BUTTON = 142;
- public static final int DARK_OAK_DOOR = 143;
- public static final int DARK_OAK_FENCE = 144;
- public static final int DARK_OAK_FENCE_GATE = 145;
- public static final int DARK_OAK_LEAVES = 146;
- public static final int DARK_OAK_LOG = 147;
- public static final int DARK_OAK_PLANKS = 148;
- public static final int DARK_OAK_PRESSURE_PLATE = 149;
- public static final int DARK_OAK_SAPLING = 150;
- public static final int DARK_OAK_SLAB = 151;
- public static final int DARK_OAK_STAIRS = 152;
- public static final int DARK_OAK_TRAPDOOR = 153;
- public static final int DARK_OAK_WOOD = 154;
- public static final int DARK_PRISMARINE = 155;
- public static final int DARK_PRISMARINE_SLAB = 156;
- public static final int DARK_PRISMARINE_STAIRS = 157;
- public static final int DAYLIGHT_DETECTOR = 158;
- public static final int DEAD_BRAIN_CORAL = 159;
- public static final int DEAD_BRAIN_CORAL_BLOCK = 160;
- public static final int DEAD_BRAIN_CORAL_FAN = 161;
- public static final int DEAD_BRAIN_CORAL_WALL_FAN = 162;
- public static final int DEAD_BUBBLE_CORAL = 163;
- public static final int DEAD_BUBBLE_CORAL_BLOCK = 164;
- public static final int DEAD_BUBBLE_CORAL_FAN = 165;
- public static final int DEAD_BUBBLE_CORAL_WALL_FAN = 166;
- public static final int DEAD_BUSH = 167;
- public static final int DEAD_FIRE_CORAL = 168;
- public static final int DEAD_FIRE_CORAL_BLOCK = 169;
- public static final int DEAD_FIRE_CORAL_FAN = 170;
- public static final int DEAD_FIRE_CORAL_WALL_FAN = 171;
- public static final int DEAD_HORN_CORAL = 172;
- public static final int DEAD_HORN_CORAL_BLOCK = 173;
- public static final int DEAD_HORN_CORAL_FAN = 174;
- public static final int DEAD_HORN_CORAL_WALL_FAN = 175;
- public static final int DEAD_TUBE_CORAL = 176;
- public static final int DEAD_TUBE_CORAL_BLOCK = 177;
- public static final int DEAD_TUBE_CORAL_FAN = 178;
- public static final int DEAD_TUBE_CORAL_WALL_FAN = 179;
- public static final int DETECTOR_RAIL = 180;
- public static final int DIAMOND_BLOCK = 181;
- public static final int DIAMOND_ORE = 182;
- public static final int DIORITE = 183;
- public static final int DIRT = 184;
- public static final int DISPENSER = 185;
- public static final int DRAGON_EGG = 186;
- public static final int DRAGON_HEAD = 187;
- public static final int DRAGON_WALL_HEAD = 188;
- public static final int DRIED_KELP_BLOCK = 189;
- public static final int DROPPER = 190;
- public static final int EMERALD_BLOCK = 191;
- public static final int EMERALD_ORE = 192;
- public static final int ENCHANTING_TABLE = 193;
- public static final int END_GATEWAY = 194;
- public static final int END_PORTAL = 195;
- public static final int END_PORTAL_FRAME = 196;
- public static final int END_ROD = 197;
- public static final int END_STONE = 198;
- public static final int END_STONE_BRICKS = 199;
- public static final int ENDER_CHEST = 200;
- public static final int FARMLAND = 201;
- public static final int FERN = 202;
- public static final int FIRE = 203;
- public static final int FIRE_CORAL = 204;
- public static final int FIRE_CORAL_BLOCK = 205;
- public static final int FIRE_CORAL_FAN = 206;
- public static final int FIRE_CORAL_WALL_FAN = 207;
- public static final int FLOWER_POT = 208;
- public static final int FROSTED_ICE = 209;
- public static final int FURNACE = 210;
- public static final int GLASS = 211;
- public static final int GLASS_PANE = 212;
- public static final int GLOWSTONE = 213;
- public static final int GOLD_BLOCK = 214;
- public static final int GOLD_ORE = 215;
- public static final int GRANITE = 216;
- public static final int GRASS = 217;
- public static final int GRASS_BLOCK = 218;
- public static final int GRASS_PATH = 219;
- public static final int GRAVEL = 220;
- public static final int GRAY_BANNER = 221;
- public static final int GRAY_BED = 222;
- public static final int GRAY_CARPET = 223;
- public static final int GRAY_CONCRETE = 224;
- public static final int GRAY_CONCRETE_POWDER = 225;
- public static final int GRAY_GLAZED_TERRACOTTA = 226;
- public static final int GRAY_SHULKER_BOX = 227;
- public static final int GRAY_STAINED_GLASS = 228;
- public static final int GRAY_STAINED_GLASS_PANE = 229;
- public static final int GRAY_TERRACOTTA = 230;
- public static final int GRAY_WALL_BANNER = 231;
- public static final int GRAY_WOOL = 232;
- public static final int GREEN_BANNER = 233;
- public static final int GREEN_BED = 234;
- public static final int GREEN_CARPET = 235;
- public static final int GREEN_CONCRETE = 236;
- public static final int GREEN_CONCRETE_POWDER = 237;
- public static final int GREEN_GLAZED_TERRACOTTA = 238;
- public static final int GREEN_SHULKER_BOX = 239;
- public static final int GREEN_STAINED_GLASS = 240;
- public static final int GREEN_STAINED_GLASS_PANE = 241;
- public static final int GREEN_TERRACOTTA = 242;
- public static final int GREEN_WALL_BANNER = 243;
- public static final int GREEN_WOOL = 244;
- public static final int HAY_BLOCK = 245;
- public static final int HEAVY_WEIGHTED_PRESSURE_PLATE = 246;
- public static final int HOPPER = 247;
- public static final int HORN_CORAL = 248;
- public static final int HORN_CORAL_BLOCK = 249;
- public static final int HORN_CORAL_FAN = 250;
- public static final int HORN_CORAL_WALL_FAN = 251;
- public static final int ICE = 252;
- public static final int INFESTED_CHISELED_STONE_BRICKS = 253;
- public static final int INFESTED_COBBLESTONE = 254;
- public static final int INFESTED_CRACKED_STONE_BRICKS = 255;
- public static final int INFESTED_MOSSY_STONE_BRICKS = 256;
- public static final int INFESTED_STONE = 257;
- public static final int INFESTED_STONE_BRICKS = 258;
- public static final int IRON_BARS = 259;
- public static final int IRON_BLOCK = 260;
- public static final int IRON_DOOR = 261;
- public static final int IRON_ORE = 262;
- public static final int IRON_TRAPDOOR = 263;
- public static final int JACK_O_LANTERN = 264;
- public static final int JUKEBOX = 265;
- public static final int JUNGLE_BUTTON = 266;
- public static final int JUNGLE_DOOR = 267;
- public static final int JUNGLE_FENCE = 268;
- public static final int JUNGLE_FENCE_GATE = 269;
- public static final int JUNGLE_LEAVES = 270;
- public static final int JUNGLE_LOG = 271;
- public static final int JUNGLE_PLANKS = 272;
- public static final int JUNGLE_PRESSURE_PLATE = 273;
- public static final int JUNGLE_SAPLING = 274;
- public static final int JUNGLE_SLAB = 275;
- public static final int JUNGLE_STAIRS = 276;
- public static final int JUNGLE_TRAPDOOR = 277;
- public static final int JUNGLE_WOOD = 278;
- public static final int KELP = 279;
- public static final int KELP_PLANT = 280;
- public static final int LADDER = 281;
- public static final int LAPIS_BLOCK = 282;
- public static final int LAPIS_ORE = 283;
- public static final int LARGE_FERN = 284;
- public static final int LAVA = 285;
- public static final int LEVER = 286;
- public static final int LIGHT_BLUE_BANNER = 287;
- public static final int LIGHT_BLUE_BED = 288;
- public static final int LIGHT_BLUE_CARPET = 289;
- public static final int LIGHT_BLUE_CONCRETE = 290;
- public static final int LIGHT_BLUE_CONCRETE_POWDER = 291;
- public static final int LIGHT_BLUE_GLAZED_TERRACOTTA = 292;
- public static final int LIGHT_BLUE_SHULKER_BOX = 293;
- public static final int LIGHT_BLUE_STAINED_GLASS = 294;
- public static final int LIGHT_BLUE_STAINED_GLASS_PANE = 295;
- public static final int LIGHT_BLUE_TERRACOTTA = 296;
- public static final int LIGHT_BLUE_WALL_BANNER = 297;
- public static final int LIGHT_BLUE_WOOL = 298;
- public static final int LIGHT_GRAY_BANNER = 299;
- public static final int LIGHT_GRAY_BED = 300;
- public static final int LIGHT_GRAY_CARPET = 301;
- public static final int LIGHT_GRAY_CONCRETE = 302;
- public static final int LIGHT_GRAY_CONCRETE_POWDER = 303;
- public static final int LIGHT_GRAY_GLAZED_TERRACOTTA = 304;
- public static final int LIGHT_GRAY_SHULKER_BOX = 305;
- public static final int LIGHT_GRAY_STAINED_GLASS = 306;
- public static final int LIGHT_GRAY_STAINED_GLASS_PANE = 307;
- public static final int LIGHT_GRAY_TERRACOTTA = 308;
- public static final int LIGHT_GRAY_WALL_BANNER = 309;
- public static final int LIGHT_GRAY_WOOL = 310;
- public static final int LIGHT_WEIGHTED_PRESSURE_PLATE = 311;
- public static final int LILAC = 312;
- public static final int LILY_PAD = 313;
- public static final int LIME_BANNER = 314;
- public static final int LIME_BED = 315;
- public static final int LIME_CARPET = 316;
- public static final int LIME_CONCRETE = 317;
- public static final int LIME_CONCRETE_POWDER = 318;
- public static final int LIME_GLAZED_TERRACOTTA = 319;
- public static final int LIME_SHULKER_BOX = 320;
- public static final int LIME_STAINED_GLASS = 321;
- public static final int LIME_STAINED_GLASS_PANE = 322;
- public static final int LIME_TERRACOTTA = 323;
- public static final int LIME_WALL_BANNER = 324;
- public static final int LIME_WOOL = 325;
- public static final int MAGENTA_BANNER = 326;
- public static final int MAGENTA_BED = 327;
- public static final int MAGENTA_CARPET = 328;
- public static final int MAGENTA_CONCRETE = 329;
- public static final int MAGENTA_CONCRETE_POWDER = 330;
- public static final int MAGENTA_GLAZED_TERRACOTTA = 331;
- public static final int MAGENTA_SHULKER_BOX = 332;
- public static final int MAGENTA_STAINED_GLASS = 333;
- public static final int MAGENTA_STAINED_GLASS_PANE = 334;
- public static final int MAGENTA_TERRACOTTA = 335;
- public static final int MAGENTA_WALL_BANNER = 336;
- public static final int MAGENTA_WOOL = 337;
- public static final int MAGMA_BLOCK = 338;
- public static final int MELON = 339;
- public static final int MELON_STEM = 340;
- public static final int MOSSY_COBBLESTONE = 341;
- public static final int MOSSY_COBBLESTONE_WALL = 342;
- public static final int MOSSY_STONE_BRICKS = 343;
- public static final int MOVING_PISTON = 344;
- public static final int MUSHROOM_STEM = 345;
- public static final int MYCELIUM = 346;
- public static final int NETHER_BRICK_FENCE = 347;
- public static final int NETHER_BRICK_SLAB = 348;
- public static final int NETHER_BRICK_STAIRS = 349;
- public static final int NETHER_BRICKS = 350;
- public static final int NETHER_PORTAL = 351;
- public static final int NETHER_QUARTZ_ORE = 352;
- public static final int NETHER_WART = 353;
- public static final int NETHER_WART_BLOCK = 354;
- public static final int NETHERRACK = 355;
- public static final int NOTE_BLOCK = 356;
- public static final int OAK_BUTTON = 357;
- public static final int OAK_DOOR = 358;
- public static final int OAK_FENCE = 359;
- public static final int OAK_FENCE_GATE = 360;
- public static final int OAK_LEAVES = 361;
- public static final int OAK_LOG = 362;
- public static final int OAK_PLANKS = 363;
- public static final int OAK_PRESSURE_PLATE = 364;
- public static final int OAK_SAPLING = 365;
- public static final int OAK_SLAB = 366;
- public static final int OAK_STAIRS = 367;
- public static final int OAK_TRAPDOOR = 368;
- public static final int OAK_WOOD = 369;
- public static final int OBSERVER = 370;
- public static final int OBSIDIAN = 371;
- public static final int ORANGE_BANNER = 372;
- public static final int ORANGE_BED = 373;
- public static final int ORANGE_CARPET = 374;
- public static final int ORANGE_CONCRETE = 375;
- public static final int ORANGE_CONCRETE_POWDER = 376;
- public static final int ORANGE_GLAZED_TERRACOTTA = 377;
- public static final int ORANGE_SHULKER_BOX = 378;
- public static final int ORANGE_STAINED_GLASS = 379;
- public static final int ORANGE_STAINED_GLASS_PANE = 380;
- public static final int ORANGE_TERRACOTTA = 381;
- public static final int ORANGE_TULIP = 382;
- public static final int ORANGE_WALL_BANNER = 383;
- public static final int ORANGE_WOOL = 384;
- public static final int OXEYE_DAISY = 385;
- public static final int PACKED_ICE = 386;
- public static final int PEONY = 387;
- public static final int PETRIFIED_OAK_SLAB = 388;
- public static final int PINK_BANNER = 389;
- public static final int PINK_BED = 390;
- public static final int PINK_CARPET = 391;
- public static final int PINK_CONCRETE = 392;
- public static final int PINK_CONCRETE_POWDER = 393;
- public static final int PINK_GLAZED_TERRACOTTA = 394;
- public static final int PINK_SHULKER_BOX = 395;
- public static final int PINK_STAINED_GLASS = 396;
- public static final int PINK_STAINED_GLASS_PANE = 397;
- public static final int PINK_TERRACOTTA = 398;
- public static final int PINK_TULIP = 399;
- public static final int PINK_WALL_BANNER = 400;
- public static final int PINK_WOOL = 401;
- public static final int PISTON = 402;
- public static final int PISTON_HEAD = 403;
- public static final int PLAYER_HEAD = 404;
- public static final int PLAYER_WALL_HEAD = 405;
- public static final int PODZOL = 406;
- public static final int POLISHED_ANDESITE = 407;
- public static final int POLISHED_DIORITE = 408;
- public static final int POLISHED_GRANITE = 409;
- public static final int POPPY = 410;
- public static final int POTATOES = 411;
- public static final int POTTED_ACACIA_SAPLING = 412;
- public static final int POTTED_ALLIUM = 413;
- public static final int POTTED_AZURE_BLUET = 414;
- public static final int POTTED_BIRCH_SAPLING = 415;
- public static final int POTTED_BLUE_ORCHID = 416;
- public static final int POTTED_BROWN_MUSHROOM = 417;
- public static final int POTTED_CACTUS = 418;
- public static final int POTTED_DANDELION = 419;
- public static final int POTTED_DARK_OAK_SAPLING = 420;
- public static final int POTTED_DEAD_BUSH = 421;
- public static final int POTTED_FERN = 422;
- public static final int POTTED_JUNGLE_SAPLING = 423;
- public static final int POTTED_OAK_SAPLING = 424;
- public static final int POTTED_ORANGE_TULIP = 425;
- public static final int POTTED_OXEYE_DAISY = 426;
- public static final int POTTED_PINK_TULIP = 427;
- public static final int POTTED_POPPY = 428;
- public static final int POTTED_RED_MUSHROOM = 429;
- public static final int POTTED_RED_TULIP = 430;
- public static final int POTTED_SPRUCE_SAPLING = 431;
- public static final int POTTED_WHITE_TULIP = 432;
- public static final int POWERED_RAIL = 433;
- public static final int PRISMARINE = 434;
- public static final int PRISMARINE_BRICK_SLAB = 435;
- public static final int PRISMARINE_BRICK_STAIRS = 436;
- public static final int PRISMARINE_BRICKS = 437;
- public static final int PRISMARINE_SLAB = 438;
- public static final int PRISMARINE_STAIRS = 439;
- public static final int PUMPKIN = 440;
- public static final int PUMPKIN_STEM = 441;
- public static final int PURPLE_BANNER = 442;
- public static final int PURPLE_BED = 443;
- public static final int PURPLE_CARPET = 444;
- public static final int PURPLE_CONCRETE = 445;
- public static final int PURPLE_CONCRETE_POWDER = 446;
- public static final int PURPLE_GLAZED_TERRACOTTA = 447;
- public static final int PURPLE_SHULKER_BOX = 448;
- public static final int PURPLE_STAINED_GLASS = 449;
- public static final int PURPLE_STAINED_GLASS_PANE = 450;
- public static final int PURPLE_TERRACOTTA = 451;
- public static final int PURPLE_WALL_BANNER = 452;
- public static final int PURPLE_WOOL = 453;
- public static final int PURPUR_BLOCK = 454;
- public static final int PURPUR_PILLAR = 455;
- public static final int PURPUR_SLAB = 456;
- public static final int PURPUR_STAIRS = 457;
- public static final int QUARTZ_BLOCK = 458;
- public static final int QUARTZ_PILLAR = 459;
- public static final int QUARTZ_SLAB = 460;
- public static final int QUARTZ_STAIRS = 461;
- public static final int RAIL = 462;
- public static final int RED_BANNER = 463;
- public static final int RED_BED = 464;
- public static final int RED_CARPET = 465;
- public static final int RED_CONCRETE = 466;
- public static final int RED_CONCRETE_POWDER = 467;
- public static final int RED_GLAZED_TERRACOTTA = 468;
- public static final int RED_MUSHROOM = 469;
- public static final int RED_MUSHROOM_BLOCK = 470;
- public static final int RED_NETHER_BRICKS = 471;
- public static final int RED_SAND = 472;
- public static final int RED_SANDSTONE = 473;
- public static final int RED_SANDSTONE_SLAB = 474;
- public static final int RED_SANDSTONE_STAIRS = 475;
- public static final int RED_SHULKER_BOX = 476;
- public static final int RED_STAINED_GLASS = 477;
- public static final int RED_STAINED_GLASS_PANE = 478;
- public static final int RED_TERRACOTTA = 479;
- public static final int RED_TULIP = 480;
- public static final int RED_WALL_BANNER = 481;
- public static final int RED_WOOL = 482;
- public static final int REDSTONE_BLOCK = 483;
- public static final int REDSTONE_LAMP = 484;
- public static final int REDSTONE_ORE = 485;
- public static final int REDSTONE_TORCH = 486;
- public static final int REDSTONE_WALL_TORCH = 487;
- public static final int REDSTONE_WIRE = 488;
- public static final int REPEATER = 489;
- public static final int REPEATING_COMMAND_BLOCK = 490;
- public static final int ROSE_BUSH = 491;
- public static final int SAND = 492;
- public static final int SANDSTONE = 493;
- public static final int SANDSTONE_SLAB = 494;
- public static final int SANDSTONE_STAIRS = 495;
- public static final int SEA_LANTERN = 496;
- public static final int SEA_PICKLE = 497;
- public static final int SEAGRASS = 498;
- public static final int SHULKER_BOX = 499;
- public static final int SIGN = 500;
- public static final int SKELETON_SKULL = 501;
- public static final int SKELETON_WALL_SKULL = 502;
- public static final int SLIME_BLOCK = 503;
- public static final int SMOOTH_QUARTZ = 504;
- public static final int SMOOTH_RED_SANDSTONE = 505;
- public static final int SMOOTH_SANDSTONE = 506;
- public static final int SMOOTH_STONE = 507;
- public static final int SNOW = 508;
- public static final int SNOW_BLOCK = 509;
- public static final int SOUL_SAND = 510;
- public static final int SPAWNER = 511;
- public static final int SPONGE = 512;
- public static final int SPRUCE_BUTTON = 513;
- public static final int SPRUCE_DOOR = 514;
- public static final int SPRUCE_FENCE = 515;
- public static final int SPRUCE_FENCE_GATE = 516;
- public static final int SPRUCE_LEAVES = 517;
- public static final int SPRUCE_LOG = 518;
- public static final int SPRUCE_PLANKS = 519;
- public static final int SPRUCE_PRESSURE_PLATE = 520;
- public static final int SPRUCE_SAPLING = 521;
- public static final int SPRUCE_SLAB = 522;
- public static final int SPRUCE_STAIRS = 523;
- public static final int SPRUCE_TRAPDOOR = 524;
- public static final int SPRUCE_WOOD = 525;
- public static final int STICKY_PISTON = 526;
- public static final int STONE = 527;
- public static final int STONE_BRICK_SLAB = 528;
- public static final int STONE_BRICK_STAIRS = 529;
- public static final int STONE_BRICKS = 530;
- public static final int STONE_BUTTON = 531;
- public static final int STONE_PRESSURE_PLATE = 532;
- public static final int STONE_SLAB = 533;
- public static final int STRIPPED_ACACIA_LOG = 534;
- public static final int STRIPPED_ACACIA_WOOD = 535;
- public static final int STRIPPED_BIRCH_LOG = 536;
- public static final int STRIPPED_BIRCH_WOOD = 537;
- public static final int STRIPPED_DARK_OAK_LOG = 538;
- public static final int STRIPPED_DARK_OAK_WOOD = 539;
- public static final int STRIPPED_JUNGLE_LOG = 540;
- public static final int STRIPPED_JUNGLE_WOOD = 541;
- public static final int STRIPPED_OAK_LOG = 542;
- public static final int STRIPPED_OAK_WOOD = 543;
- public static final int STRIPPED_SPRUCE_LOG = 544;
- public static final int STRIPPED_SPRUCE_WOOD = 545;
- public static final int STRUCTURE_BLOCK = 546;
- public static final int STRUCTURE_VOID = 547;
- public static final int SUGAR_CANE = 548;
- public static final int SUNFLOWER = 549;
- public static final int TALL_GRASS = 550;
- public static final int TALL_SEAGRASS = 551;
- public static final int TERRACOTTA = 552;
- public static final int TNT = 553;
- public static final int TORCH = 554;
- public static final int TRAPPED_CHEST = 555;
- public static final int TRIPWIRE = 556;
- public static final int TRIPWIRE_HOOK = 557;
- public static final int TUBE_CORAL = 558;
- public static final int TUBE_CORAL_BLOCK = 559;
- public static final int TUBE_CORAL_FAN = 560;
- public static final int TUBE_CORAL_WALL_FAN = 561;
- public static final int TURTLE_EGG = 562;
- public static final int VINE = 563;
- public static final int VOID_AIR = 564;
+ public static final int AIR = 1;
+ public static final int CAVE_AIR = 2;
+ public static final int VOID_AIR = 3;
+ public static final int ACACIA_BUTTON = 4;
+ public static final int ACACIA_DOOR = 5;
+ public static final int ACACIA_FENCE = 6;
+ public static final int ACACIA_FENCE_GATE = 7;
+ public static final int ACACIA_LEAVES = 8;
+ public static final int ACACIA_LOG = 9;
+ public static final int ACACIA_PLANKS = 10;
+ public static final int ACACIA_PRESSURE_PLATE = 11;
+ public static final int ACACIA_SAPLING = 12;
+ public static final int ACACIA_SLAB = 13;
+ public static final int ACACIA_STAIRS = 14;
+ public static final int ACACIA_TRAPDOOR = 15;
+ public static final int ACACIA_WOOD = 16;
+ public static final int ACTIVATOR_RAIL = 17;
+ public static final int ALLIUM = 18;
+ public static final int ANDESITE = 19;
+ public static final int ANVIL = 20;
+ public static final int ATTACHED_MELON_STEM = 21;
+ public static final int ATTACHED_PUMPKIN_STEM = 22;
+ public static final int AZURE_BLUET = 23;
+ public static final int BARRIER = 24;
+ public static final int BEACON = 25;
+ public static final int BEDROCK = 26;
+ public static final int BEETROOTS = 27;
+ public static final int BIRCH_BUTTON = 28;
+ public static final int BIRCH_DOOR = 29;
+ public static final int BIRCH_FENCE = 30;
+ public static final int BIRCH_FENCE_GATE = 31;
+ public static final int BIRCH_LEAVES = 32;
+ public static final int BIRCH_LOG = 33;
+ public static final int BIRCH_PLANKS = 34;
+ public static final int BIRCH_PRESSURE_PLATE = 35;
+ public static final int BIRCH_SAPLING = 36;
+ public static final int BIRCH_SLAB = 37;
+ public static final int BIRCH_STAIRS = 38;
+ public static final int BIRCH_TRAPDOOR = 39;
+ public static final int BIRCH_WOOD = 40;
+ public static final int BLACK_BANNER = 41;
+ public static final int BLACK_BED = 42;
+ public static final int BLACK_CARPET = 43;
+ public static final int BLACK_CONCRETE = 44;
+ public static final int BLACK_CONCRETE_POWDER = 45;
+ public static final int BLACK_GLAZED_TERRACOTTA = 46;
+ public static final int BLACK_SHULKER_BOX = 47;
+ public static final int BLACK_STAINED_GLASS = 48;
+ public static final int BLACK_STAINED_GLASS_PANE = 49;
+ public static final int BLACK_TERRACOTTA = 50;
+ public static final int BLACK_WALL_BANNER = 51;
+ public static final int BLACK_WOOL = 52;
+ public static final int BLUE_BANNER = 53;
+ public static final int BLUE_BED = 54;
+ public static final int BLUE_CARPET = 55;
+ public static final int BLUE_CONCRETE = 56;
+ public static final int BLUE_CONCRETE_POWDER = 57;
+ public static final int BLUE_GLAZED_TERRACOTTA = 58;
+ public static final int BLUE_ICE = 59;
+ public static final int BLUE_ORCHID = 60;
+ public static final int BLUE_SHULKER_BOX = 61;
+ public static final int BLUE_STAINED_GLASS = 62;
+ public static final int BLUE_STAINED_GLASS_PANE = 63;
+ public static final int BLUE_TERRACOTTA = 64;
+ public static final int BLUE_WALL_BANNER = 65;
+ public static final int BLUE_WOOL = 66;
+ public static final int BONE_BLOCK = 67;
+ public static final int BOOKSHELF = 68;
+ public static final int BRAIN_CORAL = 69;
+ public static final int BRAIN_CORAL_BLOCK = 70;
+ public static final int BRAIN_CORAL_FAN = 71;
+ public static final int BRAIN_CORAL_WALL_FAN = 72;
+ public static final int BREWING_STAND = 73;
+ public static final int BRICK_SLAB = 74;
+ public static final int BRICK_STAIRS = 75;
+ public static final int BRICKS = 76;
+ public static final int BROWN_BANNER = 77;
+ public static final int BROWN_BED = 78;
+ public static final int BROWN_CARPET = 79;
+ public static final int BROWN_CONCRETE = 80;
+ public static final int BROWN_CONCRETE_POWDER = 81;
+ public static final int BROWN_GLAZED_TERRACOTTA = 82;
+ public static final int BROWN_MUSHROOM = 83;
+ public static final int BROWN_MUSHROOM_BLOCK = 84;
+ public static final int BROWN_SHULKER_BOX = 85;
+ public static final int BROWN_STAINED_GLASS = 86;
+ public static final int BROWN_STAINED_GLASS_PANE = 87;
+ public static final int BROWN_TERRACOTTA = 88;
+ public static final int BROWN_WALL_BANNER = 89;
+ public static final int BROWN_WOOL = 90;
+ public static final int BUBBLE_COLUMN = 91;
+ public static final int BUBBLE_CORAL = 92;
+ public static final int BUBBLE_CORAL_BLOCK = 93;
+ public static final int BUBBLE_CORAL_FAN = 94;
+ public static final int BUBBLE_CORAL_WALL_FAN = 95;
+ public static final int CACTUS = 96;
+ public static final int CAKE = 97;
+ public static final int CARROTS = 98;
+ public static final int CARVED_PUMPKIN = 99;
+ public static final int CAULDRON = 100;
+ public static final int CHAIN_COMMAND_BLOCK = 101;
+ public static final int CHEST = 102;
+ public static final int CHIPPED_ANVIL = 103;
+ public static final int CHISELED_QUARTZ_BLOCK = 104;
+ public static final int CHISELED_RED_SANDSTONE = 105;
+ public static final int CHISELED_SANDSTONE = 106;
+ public static final int CHISELED_STONE_BRICKS = 107;
+ public static final int CHORUS_FLOWER = 108;
+ public static final int CHORUS_PLANT = 109;
+ public static final int CLAY = 110;
+ public static final int COAL_BLOCK = 111;
+ public static final int COAL_ORE = 112;
+ public static final int COARSE_DIRT = 113;
+ public static final int COBBLESTONE = 114;
+ public static final int COBBLESTONE_SLAB = 115;
+ public static final int COBBLESTONE_STAIRS = 116;
+ public static final int COBBLESTONE_WALL = 117;
+ public static final int COBWEB = 118;
+ public static final int COCOA = 119;
+ public static final int COMMAND_BLOCK = 120;
+ public static final int COMPARATOR = 121;
+ public static final int CONDUIT = 122;
+ public static final int CRACKED_STONE_BRICKS = 123;
+ public static final int CRAFTING_TABLE = 124;
+ public static final int CREEPER_HEAD = 125;
+ public static final int CREEPER_WALL_HEAD = 126;
+ public static final int CUT_RED_SANDSTONE = 127;
+ public static final int CUT_SANDSTONE = 128;
+ public static final int CYAN_BANNER = 129;
+ public static final int CYAN_BED = 130;
+ public static final int CYAN_CARPET = 131;
+ public static final int CYAN_CONCRETE = 132;
+ public static final int CYAN_CONCRETE_POWDER = 133;
+ public static final int CYAN_GLAZED_TERRACOTTA = 134;
+ public static final int CYAN_SHULKER_BOX = 135;
+ public static final int CYAN_STAINED_GLASS = 136;
+ public static final int CYAN_STAINED_GLASS_PANE = 137;
+ public static final int CYAN_TERRACOTTA = 138;
+ public static final int CYAN_WALL_BANNER = 139;
+ public static final int CYAN_WOOL = 140;
+ public static final int DAMAGED_ANVIL = 141;
+ public static final int DANDELION = 142;
+ public static final int DARK_OAK_BUTTON = 143;
+ public static final int DARK_OAK_DOOR = 144;
+ public static final int DARK_OAK_FENCE = 145;
+ public static final int DARK_OAK_FENCE_GATE = 146;
+ public static final int DARK_OAK_LEAVES = 147;
+ public static final int DARK_OAK_LOG = 148;
+ public static final int DARK_OAK_PLANKS = 149;
+ public static final int DARK_OAK_PRESSURE_PLATE = 150;
+ public static final int DARK_OAK_SAPLING = 151;
+ public static final int DARK_OAK_SLAB = 152;
+ public static final int DARK_OAK_STAIRS = 153;
+ public static final int DARK_OAK_TRAPDOOR = 154;
+ public static final int DARK_OAK_WOOD = 155;
+ public static final int DARK_PRISMARINE = 156;
+ public static final int DARK_PRISMARINE_SLAB = 157;
+ public static final int DARK_PRISMARINE_STAIRS = 158;
+ public static final int DAYLIGHT_DETECTOR = 159;
+ public static final int DEAD_BRAIN_CORAL = 160;
+ public static final int DEAD_BRAIN_CORAL_BLOCK = 161;
+ public static final int DEAD_BRAIN_CORAL_FAN = 162;
+ public static final int DEAD_BRAIN_CORAL_WALL_FAN = 163;
+ public static final int DEAD_BUBBLE_CORAL = 164;
+ public static final int DEAD_BUBBLE_CORAL_BLOCK = 165;
+ public static final int DEAD_BUBBLE_CORAL_FAN = 166;
+ public static final int DEAD_BUBBLE_CORAL_WALL_FAN = 167;
+ public static final int DEAD_BUSH = 168;
+ public static final int DEAD_FIRE_CORAL = 169;
+ public static final int DEAD_FIRE_CORAL_BLOCK = 170;
+ public static final int DEAD_FIRE_CORAL_FAN = 171;
+ public static final int DEAD_FIRE_CORAL_WALL_FAN = 172;
+ public static final int DEAD_HORN_CORAL = 173;
+ public static final int DEAD_HORN_CORAL_BLOCK = 174;
+ public static final int DEAD_HORN_CORAL_FAN = 175;
+ public static final int DEAD_HORN_CORAL_WALL_FAN = 176;
+ public static final int DEAD_TUBE_CORAL = 177;
+ public static final int DEAD_TUBE_CORAL_BLOCK = 178;
+ public static final int DEAD_TUBE_CORAL_FAN = 179;
+ public static final int DEAD_TUBE_CORAL_WALL_FAN = 180;
+ public static final int DETECTOR_RAIL = 181;
+ public static final int DIAMOND_BLOCK = 182;
+ public static final int DIAMOND_ORE = 183;
+ public static final int DIORITE = 184;
+ public static final int DIRT = 185;
+ public static final int DISPENSER = 186;
+ public static final int DRAGON_EGG = 187;
+ public static final int DRAGON_HEAD = 188;
+ public static final int DRAGON_WALL_HEAD = 189;
+ public static final int DRIED_KELP_BLOCK = 190;
+ public static final int DROPPER = 191;
+ public static final int EMERALD_BLOCK = 192;
+ public static final int EMERALD_ORE = 193;
+ public static final int ENCHANTING_TABLE = 194;
+ public static final int END_GATEWAY = 195;
+ public static final int END_PORTAL = 196;
+ public static final int END_PORTAL_FRAME = 197;
+ public static final int END_ROD = 198;
+ public static final int END_STONE = 199;
+ public static final int END_STONE_BRICKS = 200;
+ public static final int ENDER_CHEST = 201;
+ public static final int FARMLAND = 202;
+ public static final int FERN = 203;
+ public static final int FIRE = 204;
+ public static final int FIRE_CORAL = 205;
+ public static final int FIRE_CORAL_BLOCK = 206;
+ public static final int FIRE_CORAL_FAN = 207;
+ public static final int FIRE_CORAL_WALL_FAN = 208;
+ public static final int FLOWER_POT = 209;
+ public static final int FROSTED_ICE = 210;
+ public static final int FURNACE = 211;
+ public static final int GLASS = 212;
+ public static final int GLASS_PANE = 213;
+ public static final int GLOWSTONE = 214;
+ public static final int GOLD_BLOCK = 215;
+ public static final int GOLD_ORE = 216;
+ public static final int GRANITE = 217;
+ public static final int GRASS = 218;
+ public static final int GRASS_BLOCK = 219;
+ public static final int GRASS_PATH = 220;
+ public static final int GRAVEL = 221;
+ public static final int GRAY_BANNER = 222;
+ public static final int GRAY_BED = 223;
+ public static final int GRAY_CARPET = 224;
+ public static final int GRAY_CONCRETE = 225;
+ public static final int GRAY_CONCRETE_POWDER = 226;
+ public static final int GRAY_GLAZED_TERRACOTTA = 227;
+ public static final int GRAY_SHULKER_BOX = 228;
+ public static final int GRAY_STAINED_GLASS = 229;
+ public static final int GRAY_STAINED_GLASS_PANE = 230;
+ public static final int GRAY_TERRACOTTA = 231;
+ public static final int GRAY_WALL_BANNER = 232;
+ public static final int GRAY_WOOL = 233;
+ public static final int GREEN_BANNER = 234;
+ public static final int GREEN_BED = 235;
+ public static final int GREEN_CARPET = 236;
+ public static final int GREEN_CONCRETE = 237;
+ public static final int GREEN_CONCRETE_POWDER = 238;
+ public static final int GREEN_GLAZED_TERRACOTTA = 239;
+ public static final int GREEN_SHULKER_BOX = 240;
+ public static final int GREEN_STAINED_GLASS = 241;
+ public static final int GREEN_STAINED_GLASS_PANE = 242;
+ public static final int GREEN_TERRACOTTA = 243;
+ public static final int GREEN_WALL_BANNER = 244;
+ public static final int GREEN_WOOL = 245;
+ public static final int HAY_BLOCK = 246;
+ public static final int HEAVY_WEIGHTED_PRESSURE_PLATE = 247;
+ public static final int HOPPER = 248;
+ public static final int HORN_CORAL = 249;
+ public static final int HORN_CORAL_BLOCK = 250;
+ public static final int HORN_CORAL_FAN = 251;
+ public static final int HORN_CORAL_WALL_FAN = 252;
+ public static final int ICE = 253;
+ public static final int INFESTED_CHISELED_STONE_BRICKS = 254;
+ public static final int INFESTED_COBBLESTONE = 255;
+ public static final int INFESTED_CRACKED_STONE_BRICKS = 256;
+ public static final int INFESTED_MOSSY_STONE_BRICKS = 257;
+ public static final int INFESTED_STONE = 258;
+ public static final int INFESTED_STONE_BRICKS = 259;
+ public static final int IRON_BARS = 260;
+ public static final int IRON_BLOCK = 261;
+ public static final int IRON_DOOR = 262;
+ public static final int IRON_ORE = 263;
+ public static final int IRON_TRAPDOOR = 264;
+ public static final int JACK_O_LANTERN = 265;
+ public static final int JUKEBOX = 266;
+ public static final int JUNGLE_BUTTON = 267;
+ public static final int JUNGLE_DOOR = 268;
+ public static final int JUNGLE_FENCE = 269;
+ public static final int JUNGLE_FENCE_GATE = 270;
+ public static final int JUNGLE_LEAVES = 271;
+ public static final int JUNGLE_LOG = 272;
+ public static final int JUNGLE_PLANKS = 273;
+ public static final int JUNGLE_PRESSURE_PLATE = 274;
+ public static final int JUNGLE_SAPLING = 275;
+ public static final int JUNGLE_SLAB = 276;
+ public static final int JUNGLE_STAIRS = 277;
+ public static final int JUNGLE_TRAPDOOR = 278;
+ public static final int JUNGLE_WOOD = 279;
+ public static final int KELP = 280;
+ public static final int KELP_PLANT = 281;
+ public static final int LADDER = 282;
+ public static final int LAPIS_BLOCK = 283;
+ public static final int LAPIS_ORE = 284;
+ public static final int LARGE_FERN = 285;
+ public static final int LAVA = 286;
+ public static final int LEVER = 287;
+ public static final int LIGHT_BLUE_BANNER = 288;
+ public static final int LIGHT_BLUE_BED = 289;
+ public static final int LIGHT_BLUE_CARPET = 290;
+ public static final int LIGHT_BLUE_CONCRETE = 291;
+ public static final int LIGHT_BLUE_CONCRETE_POWDER = 292;
+ public static final int LIGHT_BLUE_GLAZED_TERRACOTTA = 293;
+ public static final int LIGHT_BLUE_SHULKER_BOX = 294;
+ public static final int LIGHT_BLUE_STAINED_GLASS = 295;
+ public static final int LIGHT_BLUE_STAINED_GLASS_PANE = 296;
+ public static final int LIGHT_BLUE_TERRACOTTA = 297;
+ public static final int LIGHT_BLUE_WALL_BANNER = 298;
+ public static final int LIGHT_BLUE_WOOL = 299;
+ public static final int LIGHT_GRAY_BANNER = 300;
+ public static final int LIGHT_GRAY_BED = 301;
+ public static final int LIGHT_GRAY_CARPET = 302;
+ public static final int LIGHT_GRAY_CONCRETE = 303;
+ public static final int LIGHT_GRAY_CONCRETE_POWDER = 304;
+ public static final int LIGHT_GRAY_GLAZED_TERRACOTTA = 305;
+ public static final int LIGHT_GRAY_SHULKER_BOX = 306;
+ public static final int LIGHT_GRAY_STAINED_GLASS = 307;
+ public static final int LIGHT_GRAY_STAINED_GLASS_PANE = 308;
+ public static final int LIGHT_GRAY_TERRACOTTA = 309;
+ public static final int LIGHT_GRAY_WALL_BANNER = 310;
+ public static final int LIGHT_GRAY_WOOL = 311;
+ public static final int LIGHT_WEIGHTED_PRESSURE_PLATE = 312;
+ public static final int LILAC = 313;
+ public static final int LILY_PAD = 314;
+ public static final int LIME_BANNER = 315;
+ public static final int LIME_BED = 316;
+ public static final int LIME_CARPET = 317;
+ public static final int LIME_CONCRETE = 318;
+ public static final int LIME_CONCRETE_POWDER = 319;
+ public static final int LIME_GLAZED_TERRACOTTA = 320;
+ public static final int LIME_SHULKER_BOX = 321;
+ public static final int LIME_STAINED_GLASS = 322;
+ public static final int LIME_STAINED_GLASS_PANE = 323;
+ public static final int LIME_TERRACOTTA = 324;
+ public static final int LIME_WALL_BANNER = 325;
+ public static final int LIME_WOOL = 326;
+ public static final int MAGENTA_BANNER = 327;
+ public static final int MAGENTA_BED = 328;
+ public static final int MAGENTA_CARPET = 329;
+ public static final int MAGENTA_CONCRETE = 330;
+ public static final int MAGENTA_CONCRETE_POWDER = 331;
+ public static final int MAGENTA_GLAZED_TERRACOTTA = 332;
+ public static final int MAGENTA_SHULKER_BOX = 333;
+ public static final int MAGENTA_STAINED_GLASS = 334;
+ public static final int MAGENTA_STAINED_GLASS_PANE = 335;
+ public static final int MAGENTA_TERRACOTTA = 336;
+ public static final int MAGENTA_WALL_BANNER = 337;
+ public static final int MAGENTA_WOOL = 338;
+ public static final int MAGMA_BLOCK = 339;
+ public static final int MELON = 340;
+ public static final int MELON_STEM = 341;
+ public static final int MOSSY_COBBLESTONE = 342;
+ public static final int MOSSY_COBBLESTONE_WALL = 343;
+ public static final int MOSSY_STONE_BRICKS = 344;
+ public static final int MOVING_PISTON = 345;
+ public static final int MUSHROOM_STEM = 346;
+ public static final int MYCELIUM = 347;
+ public static final int NETHER_BRICK_FENCE = 348;
+ public static final int NETHER_BRICK_SLAB = 349;
+ public static final int NETHER_BRICK_STAIRS = 350;
+ public static final int NETHER_BRICKS = 351;
+ public static final int NETHER_PORTAL = 352;
+ public static final int NETHER_QUARTZ_ORE = 353;
+ public static final int NETHER_WART = 354;
+ public static final int NETHER_WART_BLOCK = 355;
+ public static final int NETHERRACK = 356;
+ public static final int NOTE_BLOCK = 357;
+ public static final int OAK_BUTTON = 358;
+ public static final int OAK_DOOR = 359;
+ public static final int OAK_FENCE = 360;
+ public static final int OAK_FENCE_GATE = 361;
+ public static final int OAK_LEAVES = 362;
+ public static final int OAK_LOG = 363;
+ public static final int OAK_PLANKS = 364;
+ public static final int OAK_PRESSURE_PLATE = 365;
+ public static final int OAK_SAPLING = 366;
+ public static final int OAK_SLAB = 367;
+ public static final int OAK_STAIRS = 368;
+ public static final int OAK_TRAPDOOR = 369;
+ public static final int OAK_WOOD = 370;
+ public static final int OBSERVER = 371;
+ public static final int OBSIDIAN = 372;
+ public static final int ORANGE_BANNER = 373;
+ public static final int ORANGE_BED = 374;
+ public static final int ORANGE_CARPET = 375;
+ public static final int ORANGE_CONCRETE = 376;
+ public static final int ORANGE_CONCRETE_POWDER = 377;
+ public static final int ORANGE_GLAZED_TERRACOTTA = 378;
+ public static final int ORANGE_SHULKER_BOX = 379;
+ public static final int ORANGE_STAINED_GLASS = 380;
+ public static final int ORANGE_STAINED_GLASS_PANE = 381;
+ public static final int ORANGE_TERRACOTTA = 382;
+ public static final int ORANGE_TULIP = 383;
+ public static final int ORANGE_WALL_BANNER = 384;
+ public static final int ORANGE_WOOL = 385;
+ public static final int OXEYE_DAISY = 386;
+ public static final int PACKED_ICE = 387;
+ public static final int PEONY = 388;
+ public static final int PETRIFIED_OAK_SLAB = 389;
+ public static final int PINK_BANNER = 390;
+ public static final int PINK_BED = 391;
+ public static final int PINK_CARPET = 392;
+ public static final int PINK_CONCRETE = 393;
+ public static final int PINK_CONCRETE_POWDER = 394;
+ public static final int PINK_GLAZED_TERRACOTTA = 395;
+ public static final int PINK_SHULKER_BOX = 396;
+ public static final int PINK_STAINED_GLASS = 397;
+ public static final int PINK_STAINED_GLASS_PANE = 398;
+ public static final int PINK_TERRACOTTA = 399;
+ public static final int PINK_TULIP = 400;
+ public static final int PINK_WALL_BANNER = 401;
+ public static final int PINK_WOOL = 402;
+ public static final int PISTON = 403;
+ public static final int PISTON_HEAD = 404;
+ public static final int PLAYER_HEAD = 405;
+ public static final int PLAYER_WALL_HEAD = 406;
+ public static final int PODZOL = 407;
+ public static final int POLISHED_ANDESITE = 408;
+ public static final int POLISHED_DIORITE = 409;
+ public static final int POLISHED_GRANITE = 410;
+ public static final int POPPY = 411;
+ public static final int POTATOES = 412;
+ public static final int POTTED_ACACIA_SAPLING = 413;
+ public static final int POTTED_ALLIUM = 414;
+ public static final int POTTED_AZURE_BLUET = 415;
+ public static final int POTTED_BIRCH_SAPLING = 416;
+ public static final int POTTED_BLUE_ORCHID = 417;
+ public static final int POTTED_BROWN_MUSHROOM = 418;
+ public static final int POTTED_CACTUS = 419;
+ public static final int POTTED_DANDELION = 420;
+ public static final int POTTED_DARK_OAK_SAPLING = 421;
+ public static final int POTTED_DEAD_BUSH = 422;
+ public static final int POTTED_FERN = 423;
+ public static final int POTTED_JUNGLE_SAPLING = 424;
+ public static final int POTTED_OAK_SAPLING = 425;
+ public static final int POTTED_ORANGE_TULIP = 426;
+ public static final int POTTED_OXEYE_DAISY = 427;
+ public static final int POTTED_PINK_TULIP = 428;
+ public static final int POTTED_POPPY = 429;
+ public static final int POTTED_RED_MUSHROOM = 430;
+ public static final int POTTED_RED_TULIP = 431;
+ public static final int POTTED_SPRUCE_SAPLING = 432;
+ public static final int POTTED_WHITE_TULIP = 433;
+ public static final int POWERED_RAIL = 434;
+ public static final int PRISMARINE = 435;
+ public static final int PRISMARINE_BRICK_SLAB = 436;
+ public static final int PRISMARINE_BRICK_STAIRS = 437;
+ public static final int PRISMARINE_BRICKS = 438;
+ public static final int PRISMARINE_SLAB = 439;
+ public static final int PRISMARINE_STAIRS = 440;
+ public static final int PUMPKIN = 441;
+ public static final int PUMPKIN_STEM = 442;
+ public static final int PURPLE_BANNER = 443;
+ public static final int PURPLE_BED = 444;
+ public static final int PURPLE_CARPET = 445;
+ public static final int PURPLE_CONCRETE = 446;
+ public static final int PURPLE_CONCRETE_POWDER = 447;
+ public static final int PURPLE_GLAZED_TERRACOTTA = 448;
+ public static final int PURPLE_SHULKER_BOX = 449;
+ public static final int PURPLE_STAINED_GLASS = 450;
+ public static final int PURPLE_STAINED_GLASS_PANE = 451;
+ public static final int PURPLE_TERRACOTTA = 452;
+ public static final int PURPLE_WALL_BANNER = 453;
+ public static final int PURPLE_WOOL = 454;
+ public static final int PURPUR_BLOCK = 455;
+ public static final int PURPUR_PILLAR = 456;
+ public static final int PURPUR_SLAB = 457;
+ public static final int PURPUR_STAIRS = 458;
+ public static final int QUARTZ_BLOCK = 459;
+ public static final int QUARTZ_PILLAR = 460;
+ public static final int QUARTZ_SLAB = 461;
+ public static final int QUARTZ_STAIRS = 462;
+ public static final int RAIL = 463;
+ public static final int RED_BANNER = 464;
+ public static final int RED_BED = 465;
+ public static final int RED_CARPET = 466;
+ public static final int RED_CONCRETE = 467;
+ public static final int RED_CONCRETE_POWDER = 468;
+ public static final int RED_GLAZED_TERRACOTTA = 469;
+ public static final int RED_MUSHROOM = 470;
+ public static final int RED_MUSHROOM_BLOCK = 471;
+ public static final int RED_NETHER_BRICKS = 472;
+ public static final int RED_SAND = 473;
+ public static final int RED_SANDSTONE = 474;
+ public static final int RED_SANDSTONE_SLAB = 475;
+ public static final int RED_SANDSTONE_STAIRS = 476;
+ public static final int RED_SHULKER_BOX = 477;
+ public static final int RED_STAINED_GLASS = 478;
+ public static final int RED_STAINED_GLASS_PANE = 479;
+ public static final int RED_TERRACOTTA = 480;
+ public static final int RED_TULIP = 481;
+ public static final int RED_WALL_BANNER = 482;
+ public static final int RED_WOOL = 483;
+ public static final int REDSTONE_BLOCK = 484;
+ public static final int REDSTONE_LAMP = 485;
+ public static final int REDSTONE_ORE = 486;
+ public static final int REDSTONE_TORCH = 487;
+ public static final int REDSTONE_WALL_TORCH = 488;
+ public static final int REDSTONE_WIRE = 489;
+ public static final int REPEATER = 490;
+ public static final int REPEATING_COMMAND_BLOCK = 491;
+ public static final int ROSE_BUSH = 492;
+ public static final int SAND = 493;
+ public static final int SANDSTONE = 494;
+ public static final int SANDSTONE_SLAB = 495;
+ public static final int SANDSTONE_STAIRS = 496;
+ public static final int SEA_LANTERN = 497;
+ public static final int SEA_PICKLE = 498;
+ public static final int SEAGRASS = 499;
+ public static final int SHULKER_BOX = 500;
+ public static final int SIGN = 501;
+ public static final int SKELETON_SKULL = 502;
+ public static final int SKELETON_WALL_SKULL = 503;
+ public static final int SLIME_BLOCK = 504;
+ public static final int SMOOTH_QUARTZ = 505;
+ public static final int SMOOTH_RED_SANDSTONE = 506;
+ public static final int SMOOTH_SANDSTONE = 507;
+ public static final int SMOOTH_STONE = 508;
+ public static final int SNOW = 509;
+ public static final int SNOW_BLOCK = 510;
+ public static final int SOUL_SAND = 511;
+ public static final int SPAWNER = 512;
+ public static final int SPONGE = 513;
+ public static final int SPRUCE_BUTTON = 514;
+ public static final int SPRUCE_DOOR = 515;
+ public static final int SPRUCE_FENCE = 516;
+ public static final int SPRUCE_FENCE_GATE = 517;
+ public static final int SPRUCE_LEAVES = 518;
+ public static final int SPRUCE_LOG = 519;
+ public static final int SPRUCE_PLANKS = 520;
+ public static final int SPRUCE_PRESSURE_PLATE = 521;
+ public static final int SPRUCE_SAPLING = 522;
+ public static final int SPRUCE_SLAB = 523;
+ public static final int SPRUCE_STAIRS = 524;
+ public static final int SPRUCE_TRAPDOOR = 525;
+ public static final int SPRUCE_WOOD = 526;
+ public static final int STICKY_PISTON = 527;
+ public static final int STONE = 528;
+ public static final int STONE_BRICK_SLAB = 529;
+ public static final int STONE_BRICK_STAIRS = 530;
+ public static final int STONE_BRICKS = 531;
+ public static final int STONE_BUTTON = 532;
+ public static final int STONE_PRESSURE_PLATE = 533;
+ public static final int STONE_SLAB = 534;
+ public static final int STRIPPED_ACACIA_LOG = 535;
+ public static final int STRIPPED_ACACIA_WOOD = 536;
+ public static final int STRIPPED_BIRCH_LOG = 537;
+ public static final int STRIPPED_BIRCH_WOOD = 538;
+ public static final int STRIPPED_DARK_OAK_LOG = 539;
+ public static final int STRIPPED_DARK_OAK_WOOD = 540;
+ public static final int STRIPPED_JUNGLE_LOG = 541;
+ public static final int STRIPPED_JUNGLE_WOOD = 542;
+ public static final int STRIPPED_OAK_LOG = 543;
+ public static final int STRIPPED_OAK_WOOD = 544;
+ public static final int STRIPPED_SPRUCE_LOG = 545;
+ public static final int STRIPPED_SPRUCE_WOOD = 546;
+ public static final int STRUCTURE_BLOCK = 547;
+ public static final int STRUCTURE_VOID = 548;
+ public static final int SUGAR_CANE = 549;
+ public static final int SUNFLOWER = 550;
+ public static final int TALL_GRASS = 551;
+ public static final int TALL_SEAGRASS = 552;
+ public static final int TERRACOTTA = 553;
+ public static final int TNT = 554;
+ public static final int TORCH = 555;
+ public static final int TRAPPED_CHEST = 556;
+ public static final int TRIPWIRE = 557;
+ public static final int TRIPWIRE_HOOK = 558;
+ public static final int TUBE_CORAL = 559;
+ public static final int TUBE_CORAL_BLOCK = 560;
+ public static final int TUBE_CORAL_FAN = 561;
+ public static final int TUBE_CORAL_WALL_FAN = 562;
+ public static final int TURTLE_EGG = 563;
+ public static final int VINE = 564;
public static final int WALL_SIGN = 565;
public static final int WALL_TORCH = 566;
public static final int WATER = 567;
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockState.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockState.java
index 4fe002ee7..389f8f5ed 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockState.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockState.java
@@ -19,6 +19,7 @@
package com.sk89q.worldedit.world.block;
+import com.boydti.fawe.beta.FilterBlock;
import com.boydti.fawe.command.SuggestInputParseException;
import com.boydti.fawe.object.string.MutableCharSequence;
import com.boydti.fawe.util.StringMan;
@@ -49,6 +50,7 @@ import java.util.stream.Stream;
public class BlockState implements BlockStateHolder, FawePattern {
private final int internalId;
private final int ordinal;
+ private final char ordinalChar;
private final BlockType blockType;
private BlockMaterial material;
private BaseBlock emptyBaseBlock;
@@ -57,7 +59,8 @@ public class BlockState implements BlockStateHolder, FawePattern {
this.blockType = blockType;
this.internalId = internalId;
this.ordinal = ordinal;
- this.emptyBaseBlock = new BaseBlock(this);
+ this.ordinalChar = (char) ordinal;
+ this.emptyBaseBlock = new ImmutableBaseBlock(this);
}
/**
@@ -215,7 +218,7 @@ public class BlockState implements BlockStateHolder, FawePattern {
}
@Override
public boolean apply(Extent extent, BlockVector3 get, BlockVector3 set) throws WorldEditException {
- return extent.setBlock(set, this);
+ return set.setBlock(extent, this);
}
@Override
@@ -261,6 +264,24 @@ public class BlockState implements BlockStateHolder, FawePattern {
}
}
+ public BlockState withProperties(final BlockState other) {
+ BlockType ot = other.getBlockType();
+ if (ot == blockType) {
+ return other;
+ }
+ if (ot.getProperties().isEmpty() || blockType.getProperties().isEmpty()) {
+ return this;
+ }
+ BlockState newState = this;
+ for (Property> prop: ot.getProperties()) {
+ PropertyKey key = prop.getKey();
+ if (blockType.hasProperty(key)) {
+ newState = newState.with(key, other.getState(key));
+ }
+ }
+ return this;
+ }
+
@Override
public final Map, Object> getStates() {
BlockType type = this.getBlockType();
@@ -327,10 +348,15 @@ public class BlockState implements BlockStateHolder, FawePattern {
return material;
}
- @Override
- public int getOrdinal() {
- return this.ordinal;
- }
+ @Override
+ public final int getOrdinal() {
+ return this.ordinal;
+ }
+
+ @Override
+ public final char getOrdinalChar() {
+ return this.ordinalChar;
+ }
@Override
public String toString() {
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockStateHolder.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockStateHolder.java
index eed1c68eb..5b8e12032 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockStateHolder.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockStateHolder.java
@@ -64,6 +64,9 @@ public interface BlockStateHolder> extends FawePat
@Deprecated
int getOrdinal();
+ @Deprecated
+ char getOrdinalChar();
+
BlockMaterial getMaterial();
/**
* Get type id (legacy uses)
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockType.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockType.java
index cf2f0a8dc..1e1d4a823 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockType.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockType.java
@@ -21,7 +21,6 @@ package com.sk89q.worldedit.world.block;
import static com.google.common.base.Preconditions.checkArgument;
-import com.boydti.fawe.util.ReflectionUtils;
import com.sk89q.worldedit.WorldEditException;
import com.sk89q.worldedit.extent.Extent;
import com.sk89q.worldedit.function.mask.Mask;
@@ -33,14 +32,12 @@ import com.sk89q.worldedit.registry.Keyed;
import com.sk89q.worldedit.world.item.ItemTypes;
import com.sk89q.worldedit.world.registry.BlockMaterial;
import com.sk89q.worldedit.extension.platform.Capability;
-import com.sk89q.worldedit.registry.NamespacedRegistry;
import com.sk89q.worldedit.registry.state.AbstractProperty;
import com.sk89q.worldedit.registry.state.Property;
import com.sk89q.worldedit.registry.state.PropertyKey;
import com.sk89q.worldedit.world.item.ItemType;
import com.sk89q.worldedit.world.registry.LegacyMapper;
-import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import java.util.*;
import java.util.stream.Collectors;
@@ -181,10 +178,15 @@ public class BlockType implements FawePattern, Keyed {
*
* @return The default state
*/
- public BlockState getDefaultState() {
+ public final BlockState getDefaultState() {
return this.settings.defaultState;
}
+ /**
+ * @Deprecated use a Mask instead
+ * @return
+ */
+ @Deprecated
public FuzzyBlockState getFuzzyMatcher() { //
return new FuzzyBlockState(this);
}
@@ -296,7 +298,7 @@ public class BlockType implements FawePattern, Keyed {
@Override
public boolean apply(Extent extent, BlockVector3 get, BlockVector3 set) throws WorldEditException {
- return extent.setBlock(set, this.getDefaultState());
+ return set.setBlock(extent, getDefaultState());
}
@Override
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockTypes.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockTypes.java
index dcf1baba6..db7f2443d 100644
--- a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockTypes.java
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/BlockTypes.java
@@ -52,6 +52,10 @@ import java.util.stream.Stream;
public final class BlockTypes {
// Doesn't really matter what the hardcoded values are, as FAWE will update it on load
@Nullable public static final BlockType __RESERVED__ = null;
+ @Nullable public static final BlockType AIR = null;
+ @Nullable public static final BlockType CAVE_AIR = null;
+ @Nullable public static final BlockType VOID_AIR = null;
+
@Nullable public static final BlockType ACACIA_BUTTON = null;
@Nullable public static final BlockType ACACIA_DOOR = null;
@Nullable public static final BlockType ACACIA_FENCE = null;
@@ -66,7 +70,6 @@ public final class BlockTypes {
@Nullable public static final BlockType ACACIA_TRAPDOOR = null;
@Nullable public static final BlockType ACACIA_WOOD = null;
@Nullable public static final BlockType ACTIVATOR_RAIL = null;
- @Nullable public static final BlockType AIR = null;
@Nullable public static final BlockType ALLIUM = null;
@Nullable public static final BlockType ANDESITE = null;
@Nullable public static final BlockType ANVIL = null;
@@ -150,7 +153,6 @@ public final class BlockTypes {
@Nullable public static final BlockType CARROTS = null;
@Nullable public static final BlockType CARVED_PUMPKIN = null;
@Nullable public static final BlockType CAULDRON = null;
- @Nullable public static final BlockType CAVE_AIR = null;
@Nullable public static final BlockType CHAIN_COMMAND_BLOCK = null;
@Nullable public static final BlockType CHEST = null;
@Nullable public static final BlockType CHIPPED_ANVIL = null;
@@ -615,7 +617,6 @@ public final class BlockTypes {
@Nullable public static final BlockType TUBE_CORAL_WALL_FAN = null;
@Nullable public static final BlockType TURTLE_EGG = null;
@Nullable public static final BlockType VINE = null;
- @Nullable public static final BlockType VOID_AIR = null;
@Nullable public static final BlockType WALL_SIGN = null;
@Nullable public static final BlockType WALL_TORCH = null;
@Nullable public static final BlockType WATER = null;
diff --git a/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/ImmutableBaseBlock.java b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/ImmutableBaseBlock.java
new file mode 100644
index 000000000..708e9c70e
--- /dev/null
+++ b/worldedit-core/src/main/java/com/sk89q/worldedit/world/block/ImmutableBaseBlock.java
@@ -0,0 +1,50 @@
+package com.sk89q.worldedit.world.block;
+
+import com.boydti.fawe.beta.FilterBlock;
+import com.sk89q.jnbt.CompoundTag;
+import com.sk89q.worldedit.WorldEditException;
+import com.sk89q.worldedit.extent.Extent;
+import com.sk89q.worldedit.math.BlockVector3;
+import com.sk89q.worldedit.registry.state.Property;
+
+import javax.annotation.Nullable;
+
+public final class ImmutableBaseBlock extends BaseBlock {
+ public ImmutableBaseBlock(BlockState blockState) {
+ super(blockState);
+ }
+
+ @Nullable
+ @Override
+ public CompoundTag getNbtData() {
+ return null;
+ }
+
+ @Override
+ public boolean hasNbtData() {
+ return false;
+ }
+
+ @Override
+ public String getNbtId() {
+ return "";
+ }
+
+ @Override
+ public boolean apply(Extent extent, BlockVector3 get, BlockVector3 set) throws WorldEditException {
+ return set.setBlock(extent, toBlockState());
+ }
+
+ @Override
+ public BaseBlock with(Property property, V value) {
+ return toImmutableState().with(property, value).toBaseBlock();
+ }
+
+ @Override
+ public BaseBlock toBaseBlock(CompoundTag compoundTag) {
+ if (compoundTag != null) {
+ return new BaseBlock(this.toImmutableState(), compoundTag);
+ }
+ return this;
+ }
+}
diff --git a/worldedit-core/src/main/java/net/jpountz/util/UnsafeUtils.java b/worldedit-core/src/main/java/net/jpountz/util/UnsafeUtils.java
new file mode 100644
index 000000000..665616011
--- /dev/null
+++ b/worldedit-core/src/main/java/net/jpountz/util/UnsafeUtils.java
@@ -0,0 +1,151 @@
+package net.jpountz.util;
+
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import java.lang.reflect.Field;
+import java.nio.ByteOrder;
+import sun.misc.Unsafe;
+
+
+import static net.jpountz.util.Utils.NATIVE_BYTE_ORDER;
+
+public enum UnsafeUtils {
+ ;
+
+ private static final Unsafe UNSAFE;
+ private static final long BYTE_ARRAY_OFFSET;
+ private static final int BYTE_ARRAY_SCALE;
+ private static final long INT_ARRAY_OFFSET;
+ private static final int INT_ARRAY_SCALE;
+ private static final long SHORT_ARRAY_OFFSET;
+ private static final int SHORT_ARRAY_SCALE;
+
+ static {
+ try {
+ Field theUnsafe = Unsafe.class.getDeclaredField("theUnsafe");
+ theUnsafe.setAccessible(true);
+ UNSAFE = (Unsafe) theUnsafe.get(null);
+ BYTE_ARRAY_OFFSET = UNSAFE.arrayBaseOffset(byte[].class);
+ BYTE_ARRAY_SCALE = UNSAFE.arrayIndexScale(byte[].class);
+ INT_ARRAY_OFFSET = UNSAFE.arrayBaseOffset(int[].class);
+ INT_ARRAY_SCALE = UNSAFE.arrayIndexScale(int[].class);
+ SHORT_ARRAY_OFFSET = UNSAFE.arrayBaseOffset(short[].class);
+ SHORT_ARRAY_SCALE = UNSAFE.arrayIndexScale(short[].class);
+ } catch (IllegalAccessException e) {
+ throw new ExceptionInInitializerError("Cannot access Unsafe");
+ } catch (NoSuchFieldException e) {
+ throw new ExceptionInInitializerError("Cannot access Unsafe");
+ } catch (SecurityException e) {
+ throw new ExceptionInInitializerError("Cannot access Unsafe");
+ }
+ }
+
+ public static void checkRange(byte[] buf, int off) {
+ SafeUtils.checkRange(buf, off);
+ }
+
+ public static void checkRange(byte[] buf, int off, int len) {
+ SafeUtils.checkRange(buf, off, len);
+ }
+
+ public static void checkLength(int len) {
+ SafeUtils.checkLength(len);
+ }
+
+ public static byte readByte(byte[] src, int srcOff) {
+ return UNSAFE.getByte(src, BYTE_ARRAY_OFFSET + BYTE_ARRAY_SCALE * srcOff);
+ }
+
+ public static void writeByte(byte[] src, int srcOff, byte value) {
+ UNSAFE.putByte(src, BYTE_ARRAY_OFFSET + BYTE_ARRAY_SCALE * srcOff, (byte) value);
+ }
+
+ public static void writeByte(byte[] src, int srcOff, int value) {
+ writeByte(src, srcOff, (byte) value);
+ }
+
+ public static long readLong(byte[] src, int srcOff) {
+ return UNSAFE.getLong(src, BYTE_ARRAY_OFFSET + srcOff);
+ }
+
+ public static long readLongLE(byte[] src, int srcOff) {
+ long i = readLong(src, srcOff);
+ if (NATIVE_BYTE_ORDER == ByteOrder.BIG_ENDIAN) {
+ i = Long.reverseBytes(i);
+ }
+ return i;
+ }
+
+ public static void writeLong(byte[] dest, int destOff, long value) {
+ UNSAFE.putLong(dest, BYTE_ARRAY_OFFSET + destOff, value);
+ }
+
+ public static int readInt(byte[] src, int srcOff) {
+ return UNSAFE.getInt(src, BYTE_ARRAY_OFFSET + srcOff);
+ }
+
+ public static int readIntLE(byte[] src, int srcOff) {
+ int i = readInt(src, srcOff);
+ if (NATIVE_BYTE_ORDER == ByteOrder.BIG_ENDIAN) {
+ i = Integer.reverseBytes(i);
+ }
+ return i;
+ }
+
+ public static void writeInt(byte[] dest, int destOff, int value) {
+ UNSAFE.putInt(dest, BYTE_ARRAY_OFFSET + destOff, value);
+ }
+
+ public static short readShort(byte[] src, int srcOff) {
+ return UNSAFE.getShort(src, BYTE_ARRAY_OFFSET + srcOff);
+ }
+
+ public static int readShortLE(byte[] src, int srcOff) {
+ short s = readShort(src, srcOff);
+ if (NATIVE_BYTE_ORDER == ByteOrder.BIG_ENDIAN) {
+ s = Short.reverseBytes(s);
+ }
+ return s & 0xFFFF;
+ }
+
+ public static void writeShort(byte[] dest, int destOff, short value) {
+ UNSAFE.putShort(dest, BYTE_ARRAY_OFFSET + destOff, value);
+ }
+
+ public static void writeShortLE(byte[] buf, int off, int v) {
+ writeByte(buf, off, (byte) v);
+ writeByte(buf, off + 1, (byte) (v >>> 8));
+ }
+
+ public static int readInt(int[] src, int srcOff) {
+ return UNSAFE.getInt(src, INT_ARRAY_OFFSET + INT_ARRAY_SCALE * srcOff);
+ }
+
+ public static void writeInt(int[] dest, int destOff, int value) {
+ UNSAFE.putInt(dest, INT_ARRAY_OFFSET + INT_ARRAY_SCALE * destOff, value);
+ }
+
+ public static int readShort(short[] src, int srcOff) {
+ return UNSAFE.getShort(src, SHORT_ARRAY_OFFSET + SHORT_ARRAY_SCALE * srcOff) & 0xFFFF;
+ }
+
+ public static void writeShort(short[] dest, int destOff, int value) {
+ UNSAFE.putShort(dest, SHORT_ARRAY_OFFSET + SHORT_ARRAY_SCALE * destOff, (short) value);
+ }
+
+ public static Unsafe getUNSAFE() {
+ return UNSAFE;
+ }
+}