public class BoundingBoxCache {
- protected ConcurrentHashMap<BoundingBox, Set<BoundingBox>> cache = new ConcurrentHashMap<BoundingBox, Set<BoundingBox>>();
+ private Map<BoundingBox, Set<BoundingBox>> cache = new ConcurrentHashMap<BoundingBox, Set<BoundingBox>>();
public Map<BoundingBox, Set<BoundingBox>> getBoundingBoxes() {
return cache;
cache.clear();
}
- public void addBoundingBox(BoundingBox key, Set<BoundingBox> boundingBoxes) {
+ public boolean isCached(BoundingBox key) {
+ return cache.containsKey(key);
+ }
+
+ public void addBoundingBoxes(BoundingBox key, Set<BoundingBox> boundingBoxes) {
cache.put(key, boundingBoxes);
}
public void addBoundingBox(BoundingBox key) {
Set<BoundingBox> boundingBoxes = new HashSet<BoundingBox>();
boundingBoxes.add(key);
- addBoundingBox(key, boundingBoxes);
+ addBoundingBoxes(key, boundingBoxes);
}
public void removeBoundingBox(BoundingBox key) {
cache.remove(key);
}
}
-}
+}
\ No newline at end of file
package com.irtimaled.bbor;
-import net.minecraftforge.common.MinecraftForge;
-import net.minecraftforge.fml.common.FMLCommonHandler;
-import net.minecraftforge.fml.common.Mod;
-import net.minecraftforge.fml.common.Mod.EventHandler;
-import net.minecraftforge.fml.common.SidedProxy;
-import net.minecraftforge.fml.common.event.FMLInitializationEvent;
-import net.minecraftforge.fml.common.event.FMLPreInitializationEvent;
-import net.minecraftforge.fml.common.network.simpleimpl.SimpleNetworkWrapper;
+import net.minecraft.client.Minecraft;
+import net.minecraft.network.NetworkManager;
+import net.minecraft.world.World;
+import net.minecraft.world.chunk.Chunk;
+import java.io.File;
-@Mod(modid = BoundingBoxOutlineReloaded.MODID, name = BoundingBoxOutlineReloaded.NAME, version = BoundingBoxOutlineReloaded.VERSION)
public class BoundingBoxOutlineReloaded {
- public static final String MODID = "bbor";
- public static final String NAME = "Bounding Box Outline Reloaded";
- public static final String VERSION = "1.0.0-beta7";
+ public static ClientProxy proxy;
- private ConfigManager configManager;
-
- public SimpleNetworkWrapper network;
+ public static void init() {
+ proxy = new ClientProxy();
+ proxy.init(new ConfigManager(new File(Minecraft.getMinecraft().mcDataDir, "config")));
+ }
- @Mod.Instance()
- public static BoundingBoxOutlineReloaded instance;
+ public static void chunkLoaded(Chunk chunk) {
+ proxy.chunkLoaded(chunk);
+ }
- @SidedProxy(clientSide = "com.irtimaled.bbor.ClientProxy", serverSide = "com.irtimaled.bbor.CommonProxy")
- public static CommonProxy proxy;
+ public static void worldLoaded(World world) {
+ proxy.worldLoaded(world);
+ }
+ public static void keyPressed() {
+ proxy.keyPressed();
+ }
- @EventHandler
- public void preInit(FMLPreInitializationEvent evt) {
- configManager = new ConfigManager(evt.getModConfigurationDirectory());
+ public static void render(float partialTicks) {
+ proxy.render(partialTicks);
}
- @EventHandler
- public void load(FMLInitializationEvent evt) {
- MinecraftForge.EVENT_BUS.register(proxy);
- FMLCommonHandler.instance().bus().register(proxy);
+ public static void playerConnectedToServer(NetworkManager networkManager) {
+ proxy.playerConnectedToServer(networkManager);
+ }
- proxy.configManager = configManager;
- proxy.init();
+ public static void playerDisconnectedFromServer() {
+ proxy.playerDisconnectedFromServer();
}
}
+
package com.irtimaled.bbor;
import net.minecraft.client.Minecraft;
-import net.minecraft.client.gui.ScaledResolution;
import net.minecraft.client.renderer.Tessellator;
import net.minecraft.client.renderer.WorldRenderer;
import net.minecraft.client.settings.KeyBinding;
import net.minecraft.nbt.CompressedStreamTools;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTTagList;
+import net.minecraft.network.NetworkManager;
import net.minecraft.util.AxisAlignedBB;
import net.minecraft.util.BlockPos;
import net.minecraft.world.ChunkCoordIntPair;
import net.minecraft.world.World;
-import net.minecraftforge.client.event.RenderWorldLastEvent;
-import net.minecraftforge.common.util.Constants;
-import net.minecraftforge.fml.client.registry.ClientRegistry;
-import net.minecraftforge.fml.common.FMLLog;
-import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
-import net.minecraftforge.fml.common.gameevent.InputEvent;
-import net.minecraftforge.fml.common.network.FMLNetworkEvent;
-import net.minecraftforge.fml.relauncher.ReflectionHelper;
+import org.apache.commons.lang3.ArrayUtils;
import org.lwjgl.input.Keyboard;
import org.lwjgl.opengl.GL11;
private BoundingBox spawnChunksBoundingBox;
private BoundingBox lazySpawnChunksBoundingBox;
- @SubscribeEvent
- public void onKeyInputEvent(InputEvent.KeyInputEvent evt) {
+ public void keyPressed() {
if (hotKey.isPressed()) {
active = !active;
if (active)
}
@Override
- public void init() {
- super.init();
- hotKey = new KeyBinding("key.bbor.hotKey", Keyboard.KEY_B, "key.categories.bbor");
- ClientRegistry.registerKeyBinding(hotKey);
+ public void init(ConfigManager configManager) {
+ super.init(configManager);
+ hotKey = new KeyBinding("Toggle On/Off", Keyboard.KEY_B, "Bounding Box Outline Reloaded");
+ Minecraft.getMinecraft().gameSettings.keyBindings = ArrayUtils.add(Minecraft.getMinecraft().gameSettings.keyBindings, hotKey);
}
@Override
- protected boolean isRemotePlayer(EntityPlayer player) {
- if (Minecraft.getMinecraft().isSingleplayer()) {
- EntityPlayer singlePlayer = Minecraft.getMinecraft().thePlayer;
- if (singlePlayer == null)
- return false;
- return player.getGameProfile() != singlePlayer.getGameProfile();
- }
- return true;
- }
-
- @Override
- public void setWorldData(long seed, int spawnX, int spawnZ) {
+ public void setWorldData(WorldData worldData) {
worldSpawnBoundingBox = null;
spawnChunksBoundingBox = null;
lazySpawnChunksBoundingBox = null;
- super.setWorldData(seed, spawnX, spawnZ);
+ super.setWorldData(worldData);
}
- @SubscribeEvent
- public void renderWorldLastEvent(RenderWorldLastEvent event) {
+ public void render(float partialTicks) {
EntityPlayer entityPlayer = Minecraft.getMinecraft().thePlayer;
- playerX = entityPlayer.lastTickPosX + (entityPlayer.posX - entityPlayer.lastTickPosX) * (double) event.partialTicks;
- playerY = entityPlayer.lastTickPosY + (entityPlayer.posY - entityPlayer.lastTickPosY) * (double) event.partialTicks;
- playerZ = entityPlayer.lastTickPosZ + (entityPlayer.posZ - entityPlayer.lastTickPosZ) * (double) event.partialTicks;
+ playerX = entityPlayer.lastTickPosX + (entityPlayer.posX - entityPlayer.lastTickPosX) * (double) partialTicks;
+ playerY = entityPlayer.lastTickPosY + (entityPlayer.posY - entityPlayer.lastTickPosY) * (double) partialTicks;
+ playerZ = entityPlayer.lastTickPosZ + (entityPlayer.posZ - entityPlayer.lastTickPosZ) * (double) partialTicks;
if (this.active) {
int activeDimensionId = entityPlayer.worldObj.provider.getDimensionId();
}
}
- @SubscribeEvent
- public void clientConnectionToServerEvent(FMLNetworkEvent.ClientConnectedToServerEvent evt) {
- if (!evt.isLocal) {
- SocketAddress remoteAddress = evt.manager.getRemoteAddress();
- if (remoteAddress instanceof InetSocketAddress) {
- InetSocketAddress socketAddress = (InetSocketAddress) remoteAddress;
- loadLocalStructures(socketAddress.getHostString(), socketAddress.getPort());
- }
+ public void playerConnectedToServer(NetworkManager networkManager) {
+ SocketAddress remoteAddress = networkManager.getRemoteAddress();
+ if (remoteAddress instanceof InetSocketAddress) {
+ InetSocketAddress socketAddress = (InetSocketAddress) remoteAddress;
+ loadLocalStructures(socketAddress.getHostName(), socketAddress.getPort());
}
}
private void loadLocalStructures(String host, int port) {
+ Logger.info("Looking for local structures (host:port=%s:%d)", host, port);
String path = String.format("BBOutlineReloaded%s%s", File.separator, host);
File localStructuresFolder = new File(configManager.configDir, path);
+ Logger.info("Looking for local structures (folder=%s)", localStructuresFolder.getAbsolutePath());
if (!localStructuresFolder.exists()) {
path = String.format("%s,%d", path, port);
localStructuresFolder = new File(configManager.configDir, path);
+ Logger.info("Looking for local structures (folder=%s)", localStructuresFolder.getAbsolutePath());
}
if (!localStructuresFolder.exists())
return;
BlockPos center = new BlockPos(village.getInteger("CX"), village.getInteger("CY"), village.getInteger("CZ"));
int radius = village.getInteger("Radius");
int numVillagers = village.getInteger("PopSize");
- int numVillageDoors = village.getTagList("Doors", Constants.NBT.TAG_COMPOUND).tagCount();
+ int numVillageDoors = village.getTagList("Doors", 10).tagCount();
BoundingBox boundingBox = BoundingBoxVillage.from(center, radius, numVillagers, numVillageDoors);
cache.addBoundingBox(boundingBox);
}
- FMLLog.info("Loaded %s (%d villages)", fileName, villages.length);
+ Logger.info("Loaded %s (%d villages)", fileName, villages.length);
}
private void loadStructureNbtFile(File localStructuresFolder, BoundingBoxCache cache, String fileName, Color color, String id) {
}
if (boundingBoxes.size() > 0)
++loadedStructureCount;
- cache.addBoundingBox(structure, boundingBoxes);
+ cache.addBoundingBoxes(structure, boundingBoxes);
}
- FMLLog.info("Loaded %s (%d structures with type %s)", fileName, loadedStructureCount, id);
+ Logger.info("Loaded %s (%d structures with type %s)", fileName, loadedStructureCount, id);
}
private NBTTagCompound[] getChildCompoundTags(NBTTagCompound parent, String key) {
- NBTTagList tagList = parent.getTagList(key, Constants.NBT.TAG_COMPOUND);
+ NBTTagList tagList = parent.getTagList(key, 10);
NBTTagCompound[] result = new NBTTagCompound[tagList.tagCount()];
for (int index = 0; index < tagList.tagCount(); index++) {
result[index] = tagList.getCompoundTagAt(index);
return;
NBTTagCompound data = nbt.getCompoundTag("Data");
- setWorldData(data.getLong("RandomSeed"), data.getInteger("SpawnX"), data.getInteger("SpawnZ"));
- FMLLog.info("Loaded level.dat (seed: %d, spawn: %d,%d)", seed, spawnX, spawnZ);
+ long seed = data.getLong("RandomSeed");
+ int spawnX = data.getInteger("SpawnX");
+ int spawnZ = data.getInteger("SpawnZ");
+ setWorldData(new WorldData(seed, spawnX, spawnZ));
+ Logger.info("Loaded level.dat (seed: %d, spawn: %d,%d)", worldData.getSeed(), worldData.getSpawnX(), worldData.getSpawnZ());
}
private NBTTagCompound loadNbtFile(File file) {
return null;
}
- @SubscribeEvent
- public void clientDisconnectionFromServerEvent(FMLNetworkEvent.ClientDisconnectionFromServerEvent evt) {
+ public void playerDisconnectedFromServer() {
active = false;
if (configManager.keepCacheBetweenSessions.getBoolean()) return;
- initialized = false;
+ worldData = null;
worldSpawnBoundingBox = null;
spawnChunksBoundingBox = null;
for (BoundingBoxCache cache : boundingBoxCacheMap.values()) {
GL11.glEnable(GL11.GL_CULL_FACE);
GL11.glEnable(GL11.GL_TEXTURE_2D);
GL11.glDisable(GL11.GL_BLEND);
-
- if (configManager.showDebugInfo.getBoolean()) {
- Minecraft mc = Minecraft.getMinecraft();
- ScaledResolution var5 = new ScaledResolution(mc, mc.displayWidth, mc.displayHeight);
- int screenWidth = var5.getScaledWidth();
- mc.entityRenderer.setupOverlayRendering();
- int count = 0;
- for (BoundingBox bb : map.keySet()) {
- count += map.get(bb).size();
- }
- String debug = String.format("%d/%d", map.keySet().size(), count);
- int width = screenWidth - mc.fontRendererObj.getStringWidth(debug);
-
- mc.fontRendererObj.drawStringWithShadow(debug, width - 2, 2, 16777215);
- }
}
private void renderBoundingBoxes(Set<BoundingBox> bbList) {
}
private Set getActiveChunks(World world) {
- return ReflectionHelper.getPrivateValue(World.class, world, 33);
+ Set result = ReflectionHelper.getPrivateValue(World.class, world, 32, Set.class);
+ if (result == null) {
+ result = ReflectionHelper.getPrivateValue(World.class, world, 33, Set.class);
+ }
+ return result;
}
private void renderBoundingBox(BoundingBox bb) {
private Set<BoundingBox> getClientBoundingBoxes() {
Set<BoundingBox> boundingBoxes = new HashSet<BoundingBox>();
- if (initialized) {
+ if (worldData != null) {
World world = Minecraft.getMinecraft().theWorld;
int dimensionId = world.provider.getDimensionId();
if (dimensionId == 0) {
if (configManager.drawWorldSpawn.getBoolean()) {
- boundingBoxes.add(getWorldSpawnBoundingBox(spawnX, spawnZ));
- boundingBoxes.add(getSpawnChunksBoundingBox(spawnX, spawnZ));
+ boundingBoxes.add(getWorldSpawnBoundingBox(worldData.getSpawnX(), worldData.getSpawnZ()));
+ boundingBoxes.add(getSpawnChunksBoundingBox(worldData.getSpawnX(), worldData.getSpawnZ()));
}
if (configManager.drawLazySpawnChunks.getBoolean()) ;
- boundingBoxes.add(getLazySpawnChunksBoundingBox(spawnX, spawnZ));
+ boundingBoxes.add(getLazySpawnChunksBoundingBox(worldData.getSpawnX(), worldData.getSpawnZ()));
if (configManager.drawSlimeChunks.getBoolean()) {
Set<ChunkCoordIntPair> activeChunks = getActiveChunks(world);
}
private boolean isSlimeChunk(int chunkX, int chunkZ) {
- Random r = new Random(seed +
+ Random r = new Random(worldData.getSeed() +
(long) (chunkX * chunkX * 4987142) +
(long) (chunkX * 5947611) +
(long) (chunkZ * chunkZ) * 4392871L +
package com.irtimaled.bbor;
-import com.irtimaled.bbor.messages.*;
-import net.minecraft.entity.player.EntityPlayer;
-import net.minecraft.entity.player.EntityPlayerMP;
-import net.minecraft.server.MinecraftServer;
+import net.minecraft.world.World;
+import net.minecraft.world.chunk.Chunk;
import net.minecraft.world.chunk.IChunkProvider;
import net.minecraft.world.gen.ChunkProviderServer;
-import net.minecraftforge.event.world.ChunkEvent;
-import net.minecraftforge.event.world.WorldEvent;
-import net.minecraftforge.fml.common.FMLLog;
-import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
-import net.minecraftforge.fml.common.gameevent.PlayerEvent;
-import net.minecraftforge.fml.common.gameevent.TickEvent;
-import net.minecraftforge.fml.common.network.NetworkRegistry;
-import net.minecraftforge.fml.common.network.simpleimpl.SimpleNetworkWrapper;
-import net.minecraftforge.fml.relauncher.Side;
-import java.util.HashMap;
-import java.util.HashSet;
import java.util.Map;
-import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
-public class CommonProxy {
+public class CommonProxy implements IEventHandler {
public Map<Integer, BoundingBoxCache> boundingBoxCacheMap = new ConcurrentHashMap<Integer, BoundingBoxCache>();
- public Map<EntityPlayerMP, Integer> playerDimensions = new ConcurrentHashMap<EntityPlayerMP, Integer>();
- private Map<EntityPlayerMP, Set<BoundingBox>> playerBoundingBoxesCache = new HashMap<EntityPlayerMP, Set<BoundingBox>>();
public ConfigManager configManager;
- protected SimpleNetworkWrapper network;
- protected long seed;
- protected int spawnX;
- protected int spawnZ;
- protected boolean initialized;
+ protected WorldData worldData;
- public void init() {
- network = NetworkRegistry.INSTANCE.newSimpleChannel("bbor");
- network.registerMessage(AddBoundingBoxMessageHandler.class, AddBoundingBoxMessage.class, 0, Side.CLIENT);
- network.registerMessage(RemoveBoundingBoxMessageHandler.class, RemoveBoundingBoxMessage.class, 1, Side.CLIENT);
- network.registerMessage(InitializeClientMessageHandler.class, InitializeClientMessage.class, 2, Side.CLIENT);
+ public void init(ConfigManager configManager) {
+ this.configManager = configManager;
}
- @SubscribeEvent
- public void worldEvent(WorldEvent.Load event) {
- IChunkProvider chunkProvider = event.world.getChunkProvider();
+ public void worldLoaded(World world) {
+ IChunkProvider chunkProvider = world.getChunkProvider();
if (chunkProvider instanceof ChunkProviderServer) {
- chunkProvider = ((ChunkProviderServer) chunkProvider).serverChunkGenerator;
- setWorldData(event.world.getSeed(), event.world.getWorldInfo().getSpawnX(), event.world.getWorldInfo().getSpawnZ());
- int dimensionId = event.world.provider.getDimensionId();
- FMLLog.info("create world dimension: %d, %s (chunkprovider: %s) (seed: %d)", dimensionId, event.world.getClass().toString(), chunkProvider.getClass().toString(), seed);
- boundingBoxCacheMap.put(dimensionId, new DimensionProcessor(configManager, event.world, dimensionId, chunkProvider));
+ chunkProvider = ReflectionHelper.getPrivateValue(ChunkProviderServer.class, (ChunkProviderServer) chunkProvider, 3, IChunkProvider.class);
+ setWorldData(new WorldData(world.getSeed(), world.getWorldInfo().getSpawnX(), world.getWorldInfo().getSpawnZ()));
+ int dimensionId = world.provider.getDimensionId();
+ Logger.info("create world dimension: %d, %s (chunkprovider: %s) (seed: %d)", dimensionId, world.getClass().toString(), chunkProvider.getClass().toString(), worldData.getSeed());
+ boundingBoxCacheMap.put(dimensionId, new DimensionProcessor(this, configManager, world, dimensionId, chunkProvider));
}
}
- @SubscribeEvent
- public void chunkEvent(ChunkEvent.Load event) {
- int dimensionId = event.world.provider.getDimensionId();
+ public void chunkLoaded(Chunk chunk) {
+ int dimensionId = chunk.getWorld().provider.getDimensionId();
if (boundingBoxCacheMap.containsKey(dimensionId)) {
boundingBoxCacheMap.get(dimensionId).refresh();
}
}
- @SubscribeEvent
- public void playerChangedDimensionEvent(PlayerEvent.PlayerChangedDimensionEvent evt) {
- if (playerDimensions.containsKey(evt.player)) {
- EntityPlayerMP player = (EntityPlayerMP) evt.player;
- int dimension = player.dimension;
- playerDimensions.put(player, dimension);
-
- sendToPlayer(player, boundingBoxCacheMap.get(dimension));
- }
- }
-
- protected boolean isRemotePlayer(EntityPlayer player) {
- return true;
- }
-
- @SubscribeEvent
- public void playerLoggedInEvent(PlayerEvent.PlayerLoggedInEvent evt) {
- if (evt.player instanceof EntityPlayerMP &&
- isRemotePlayer(evt.player)) {
- EntityPlayerMP player = (EntityPlayerMP) evt.player;
- initializeClient(player);
- int dimension = player.dimension;
- playerDimensions.put(player, dimension);
- sendToPlayer(player, boundingBoxCacheMap.get(dimension));
- }
- }
-
- @SubscribeEvent
- public void playerLoggedOutEvent(PlayerEvent.PlayerLoggedOutEvent evt) {
- if (playerDimensions.containsKey(evt.player)) {
- playerDimensions.remove(evt.player);
- playerBoundingBoxesCache.remove(evt.player);
- }
- }
-
- @SubscribeEvent
- public void tickEvent(TickEvent event) {
- for (EntityPlayerMP player : playerDimensions.keySet()) {
-
- MinecraftServer mc = MinecraftServer.getServer();
- if (!mc.getConfigurationManager().playerEntityList.contains(player)) {
- playerDimensions.remove(player);
- } else {
- int dimension = playerDimensions.get(player);
- if (boundingBoxCacheMap.containsKey(dimension)) {
- sendToPlayer(player, boundingBoxCacheMap.get(dimension));
- }
- }
- }
- }
-
- private void initializeClient(EntityPlayerMP player) {
- network.sendTo(InitializeClientMessage.from(seed, spawnX, spawnZ), player);
- }
-
- private void sendToPlayer(EntityPlayerMP player, BoundingBoxCache boundingBoxCache) {
- Map<BoundingBox, Set<BoundingBox>> cacheSubset = getBoundingBoxMap(player, boundingBoxCache.getBoundingBoxes());
-
- int dimension = player.dimension;
- if (cacheSubset.keySet().size() > 0) {
- FMLLog.info("send %d entries to %s (%d)", cacheSubset.keySet().size(), player.getDisplayNameString(), dimension);
- }
-
- for (BoundingBox key : cacheSubset.keySet()) {
- Set<BoundingBox> boundingBoxes = cacheSubset.get(key);
- network.sendTo(AddBoundingBoxMessage.from(dimension, key, boundingBoxes), player);
-
- if (!playerBoundingBoxesCache.containsKey(player)) {
- playerBoundingBoxesCache.put(player, new HashSet<BoundingBox>());
- }
- playerBoundingBoxesCache.get(player).add(key);
- }
- }
-
- private Map<BoundingBox, Set<BoundingBox>> getBoundingBoxMap(EntityPlayerMP player, Map<BoundingBox, Set<BoundingBox>> boundingBoxMap) {
- Map<BoundingBox, Set<BoundingBox>> cacheSubset = new HashMap<BoundingBox, Set<BoundingBox>>();
- for (BoundingBox key : boundingBoxMap.keySet()) {
- if (!playerBoundingBoxesCache.containsKey(player) || !playerBoundingBoxesCache.get(player).contains(key)) {
- cacheSubset.put(key, boundingBoxMap.get(key));
- }
- }
- return cacheSubset;
- }
-
public void boundingBoxRemoved(BoundingBox bb) {
- // the only bounding boxes that can change are spawn or villages - both of these are in overworld so I guess
- // hard coding dimension 0 is okay.
- RemoveBoundingBoxMessage message = RemoveBoundingBoxMessage.from(0, bb);
- for (EntityPlayerMP player : playerDimensions.keySet()) {
- if (player.dimension == 0) {
- FMLLog.info("remove 1 entry from %s (0)", player.getDisplayNameString());
- network.sendTo(message, player);
-
- if (playerBoundingBoxesCache.containsKey(player) &&
- playerBoundingBoxesCache.get(player).contains(bb)) {
- playerBoundingBoxesCache.get(player).remove(bb);
- }
- }
- }
}
- public void setWorldData(long seed, int spawnX, int spawnZ) {
- this.seed = seed;
- this.spawnX = spawnX;
- this.spawnZ = spawnZ;
- this.initialized = true;
+ public WorldData getWorldData() {
+ return worldData;
}
- public void setWorldData(IWorldData worldData) {
- setWorldData(worldData.getSeed(), worldData.getSpawnX(), worldData.getSpawnZ());
+ public void setWorldData(WorldData worldData) {
+ this.worldData = worldData;
}
}
package com.irtimaled.bbor;
-import net.minecraftforge.common.config.Configuration;
-import net.minecraftforge.common.config.Property;
+import com.irtimaled.bbor.config.Configuration;
+import com.irtimaled.bbor.config.Setting;
import java.io.File;
public class ConfigManager {
public final File configDir;
- public Property showDebugInfo;
- public Property fill;
- public Property drawVillages;
- public Property drawDesertTemples;
- public Property drawJungleTemples;
- public Property drawWitchHuts;
- public Property drawStrongholds;
- public Property drawMineShafts;
- public Property drawNetherFortresses;
- public Property drawOceanMonuments;
- public Property alwaysVisible;
- public Property renderVillageAsSphere;
- public Property drawIronGolemSpawnArea;
- public Property drawSlimeChunks;
- public Property slimeChunkMaxY;
- public Property keepCacheBetweenSessions;
- public Property drawWorldSpawn;
- public Property worldSpawnMaxY;
- public Property drawLazySpawnChunks;
+ public Setting fill;
+ public Setting drawVillages;
+ public Setting drawDesertTemples;
+ public Setting drawJungleTemples;
+ public Setting drawWitchHuts;
+ public Setting drawStrongholds;
+ public Setting drawMineShafts;
+ public Setting drawNetherFortresses;
+ public Setting drawOceanMonuments;
+ public Setting alwaysVisible;
+ public Setting renderVillageAsSphere;
+ public Setting drawIronGolemSpawnArea;
+ public Setting drawSlimeChunks;
+ public Setting slimeChunkMaxY;
+ public Setting keepCacheBetweenSessions;
+ public Setting drawWorldSpawn;
+ public Setting worldSpawnMaxY;
+ public Setting drawLazySpawnChunks;
private Configuration config;
config = new Configuration(new File(configDir, "BBOutlineReloaded.cfg"));
config.load();
- showDebugInfo = SetupBooleanProperty(config, "general", "showDebugInfo", false, "If set to true debug information will be displayed. (default: false)");
fill = SetupBooleanProperty(config, "general", "fill", false, "If set to true the bounding boxes are filled. (default: false)");
alwaysVisible = SetupBooleanProperty(config, "general", "alwaysVisible", false, "If set to true boxes will be visible even through other blocks. (default: false)");
keepCacheBetweenSessions = SetupBooleanProperty(config, "general", "keepCacheBetweenSessions", false, "If set to true bounding box caches will be kept between sessions. (default: false)");
config.save();
}
- private Property SetupBooleanProperty(Configuration config, String category, String configName, Boolean defaultValue, String comment) {
- Property property = config.get(category, configName, defaultValue);
+ private Setting SetupBooleanProperty(Configuration config, String category, String settingName, Boolean defaultValue, String comment) {
+ Setting property = config.get(category, settingName, defaultValue);
property.comment = comment;
property.set(property.getBoolean(defaultValue));
return property;
}
- private Property SetupIntegerProperty(Configuration config, String category, String configName, int defaultValue, String comment) {
- Property property = config.get(category, configName, defaultValue);
+ private Setting SetupIntegerProperty(Configuration config, String category, String settingName, int defaultValue, String comment) {
+ Setting property = config.get(category, settingName, defaultValue);
property.comment = comment;
property.set(property.getInt(defaultValue));
return property;
import net.minecraft.world.gen.structure.MapGenStructure;
import net.minecraft.world.gen.structure.StructureComponent;
import net.minecraft.world.gen.structure.StructureStart;
-import net.minecraftforge.fml.common.FMLLog;
-import net.minecraftforge.fml.relauncher.ReflectionHelper;
import java.awt.*;
import java.util.*;
private ConfigManager configManager;
private World world;
+ private IEventHandler eventHandler;
- public DimensionProcessor(ConfigManager configManager, World world, int dimensionId, IChunkProvider chunkProvider) {
+ public DimensionProcessor(IEventHandler eventHandler, ConfigManager configManager, World world, int dimensionId, IChunkProvider chunkProvider) {
+ this.eventHandler = eventHandler;
this.configManager = configManager;
this.world = world;
this.dimensionId = dimensionId;
}
private static <T extends IChunkProvider> Collection<StructureStart> getStructures(T chunkProvider, int method) {
- Class<T> cpClass = (Class<T>) chunkProvider.getClass();
- Object structureGenerator = ReflectionHelper.getPrivateValue(cpClass, chunkProvider, method);
- if (structureGenerator instanceof MapGenStructure) {
- Map<ChunkCoordIntPair, StructureStart> structureMap = ReflectionHelper.getPrivateValue(MapGenStructure.class, (MapGenStructure) structureGenerator, 1);
+ Class<T> chunkProviderClass = (Class<T>) chunkProvider.getClass();
+ MapGenStructure structureGenerator = ReflectionHelper.getPrivateValue(chunkProviderClass, chunkProvider, method, MapGenStructure.class);
+ if (structureGenerator != null) {
+ Map<ChunkCoordIntPair, StructureStart> structureMap = ReflectionHelper.getPrivateValue(MapGenStructure.class, structureGenerator, 1);
return structureMap.values();
}
return Collections.emptyList();
Color color = structureType.getColor();
for (StructureStart structureStart : structureMap.get(structureType)) {
BoundingBox boundingBox = BoundingBoxStructure.from(structureStart.getBoundingBox(), color);
- if (!cache.containsKey(boundingBox)) {
+ if (!isCached(boundingBox)) {
Set<BoundingBox> structureBoundingBoxes = new HashSet<BoundingBox>();
Iterator structureComponents = structureStart.getComponents().iterator();
while (structureComponents.hasNext()) {
StructureComponent structureComponent = (StructureComponent) structureComponents.next();
structureBoundingBoxes.add(BoundingBoxStructure.from(structureComponent.getBoundingBox(), color));
}
- cache.put(boundingBox, structureBoundingBoxes);
- FMLLog.info("[%d] new boundingBoxCacheMap entries: %d", dimensionId, structureBoundingBoxes.size());
+ addBoundingBoxes(boundingBox, structureBoundingBoxes);
+ Logger.info("[%d] new boundingBoxCacheMap entries: %d", dimensionId, structureBoundingBoxes.size());
}
}
}
if (configManager.drawVillages.getBoolean() &&
- (world.villageCollectionObj != null)) {
+ (world.getVillageCollection() != null)) {
Set<BoundingBox> villageBoundingBoxes = new HashSet<BoundingBox>();
- List<Village> villages = world.villageCollectionObj.getVillageList();
+ List<Village> villages = world.getVillageCollection().getVillageList();
int c = 0;
for (Village village : villages) {
- BlockPos center = ReflectionHelper.getPrivateValue(Village.class, village, 3);
- Integer radius = ReflectionHelper.getPrivateValue(Village.class, village, 4);
- villageBoundingBoxes.add(BoundingBoxVillage.from(center, radius, village.getNumVillagers(), village.getNumVillageDoors()));
+ BlockPos center = village.getCenter();
+ Integer radius = village.getVillageRadius();
+ int numVillagers = village.getNumVillagers();
+ int numVillageDoors = village.getNumVillageDoors();
+ villageBoundingBoxes.add(BoundingBoxVillage.from(center, radius, numVillagers, numVillageDoors));
}
processDelta(villageCache, villageBoundingBoxes);
private void processDelta(Set<BoundingBox> oldBoundingBoxes, Set<BoundingBox> newBoundingBoxes) {
for (BoundingBox bb : oldBoundingBoxes) {
if (!newBoundingBoxes.contains(bb)) {
- cache.remove(bb);
- BoundingBoxOutlineReloaded.proxy.boundingBoxRemoved(bb);
+ removeBoundingBox(bb);
+ eventHandler.boundingBoxRemoved(bb);
} else {
- if (!cache.containsKey(bb)) {
- Set<BoundingBox> boundingBoxes = new HashSet<BoundingBox>();
- boundingBoxes.add(bb);
- cache.put(bb, boundingBoxes);
+ if (!isCached(bb)) {
+ addBoundingBox(bb);
}
}
}
--- /dev/null
+package com.irtimaled.bbor;
+
+public interface IEventHandler {
+ void boundingBoxRemoved(BoundingBox bb);
+}
+++ /dev/null
-package com.irtimaled.bbor;
-
-/**
- * Created by richard on 04/02/15.
- */
-public interface IWorldData {
- long getSeed();
-
- int getSpawnX();
-
- int getSpawnZ();
-}
--- /dev/null
+package com.irtimaled.bbor;
+
+import org.apache.logging.log4j.LogManager;
+
+public class Logger {
+ private static final org.apache.logging.log4j.Logger logger = LogManager.getLogger();
+
+
+ public static void info(String s, Object... objects) {
+ if (objects.length == 0)
+ logger.info(s);
+ else
+ logger.info(String.format(s, objects));
+ }
+}
\ No newline at end of file
--- /dev/null
+package com.irtimaled.bbor;
+
+import java.lang.reflect.Field;
+
+public class ReflectionHelper {
+
+ public static <T, R> R getPrivateValue(Class<T> instanceClass, T instance, int fieldIndex) {
+ try {
+ Field f = instanceClass.getDeclaredFields()[fieldIndex];
+ f.setAccessible(true);
+ Object value = f.get(instance);
+ return (R) value;
+ } catch (Exception e) {
+ return null;
+ }
+ }
+
+ public static <T, R> R getPrivateValue(Class<T> instanceClass, T instance, int fieldIndex, Class<R> resultClass) {
+ try {
+ Field f = instanceClass.getDeclaredFields()[fieldIndex];
+ f.setAccessible(true);
+ Object value = f.get(instance);
+ if (resultClass.isAssignableFrom(value.getClass()))
+ return (R) value;
+ } catch (Exception e) {
+ }
+ return null;
+ }
+}
--- /dev/null
+package com.irtimaled.bbor;
+
+public class WorldData {
+ private long seed;
+ private int spawnX;
+ private int spawnZ;
+
+ public WorldData(long seed, int spawnX, int spawnZ) {
+ this.seed = seed;
+ this.spawnX = spawnX;
+ this.spawnZ = spawnZ;
+ }
+
+ public long getSeed() {
+ return seed;
+ }
+
+ public int getSpawnX() {
+ return spawnX;
+ }
+
+ public int getSpawnZ() {
+ return spawnZ;
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.config;
+
+import com.google.common.io.Files;
+
+import java.io.*;
+import java.nio.charset.Charset;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public class Configuration {
+ private final File file;
+
+ public Configuration(File file) {
+ this.file = file;
+ }
+
+ public void save() {
+ Writer writer = null;
+ try {
+ writer = new BufferedWriter(new OutputStreamWriter(
+ new FileOutputStream(file), "utf-8"));
+ writer.write("# Configuration file\n");
+ for (String category : settingsGroup.keySet()) {
+ writer.write("\n");
+ writer.write(String.format("%s {\n", category));
+ Map<String, Setting> settings = settingsGroup.get(category);
+ Boolean first = true;
+ for (String settingName : settings.keySet()) {
+ if(!first)
+ writer.write("\n");
+ first = false;
+ Setting setting = settings.get(settingName);
+ writer.write(String.format(" # %s\n", setting.comment));
+ writer.write(String.format(" %s:%s=%s\n", setting.getType(), settingName, setting.getValue()));
+ }
+ writer.write("}\n");
+ }
+ } catch (IOException ex) {
+ } finally {
+ try {
+ writer.close();
+ } catch (Exception ex) {
+ }
+ }
+ }
+
+ Map<String, Map<String, Setting>> settingsGroup = new HashMap<String, Map<String, Setting>>();
+
+ public void load() {
+ try {
+ List<String> lines = Files.readLines(file, Charset.forName("utf-8"));
+ String category = null;
+ String lastCommentLine = null;
+ for (String line : lines) {
+ String trimmedLine = line.trim();
+ if (trimmedLine.isEmpty()) {
+ continue;
+ }
+ if (trimmedLine.startsWith("#")) {
+ lastCommentLine = trimmedLine.substring(1).trim();
+ continue;
+ }
+ if (trimmedLine.equals("}")) {
+ category = null;
+ continue;
+ }
+ if (category == null && trimmedLine.endsWith("{")) {
+ category = trimmedLine.substring(0, trimmedLine.length() - 1).trim();
+ settingsGroup.put(category, new HashMap<String, Setting>());
+ continue;
+ }
+ if (category != null) {
+ String[] items = trimmedLine.split("[:=]");
+ char type = items[0].charAt(0);
+ String name = items[1];
+ String stringValue = items[2];
+ Object value = getTypedValue(type, stringValue);
+ Setting setting = new Setting(value);
+ setting.comment = lastCommentLine;
+ settingsGroup.get(category).put(name, setting);
+ continue;
+ }
+ }
+ } catch (IOException e) {
+ }
+ }
+
+ private Object getTypedValue(char type, String stringValue) {
+ switch (type) {
+ case 'I':
+ return Integer.parseInt(stringValue);
+ case 'B':
+ return stringValue.equals("1") || stringValue.toLowerCase().equals("true");
+ }
+ return stringValue;
+ }
+
+ public Setting get(String category, String settingName, Object defaultValue) {
+ if (!settingsGroup.containsKey(category)) {
+ settingsGroup.put(category, new HashMap<String, Setting>());
+ }
+ Map<String, Setting> settings = settingsGroup.get(category);
+ if (!settings.containsKey(settingName)) {
+ settings.put(settingName, new Setting(defaultValue));
+ }
+ return settings.get(settingName);
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.config;
+
+public class Setting {
+
+ private Object value;
+ public String comment;
+
+ public Setting(Object value) {
+
+ this.value = value;
+ }
+
+ public Boolean getBoolean(Boolean defaultValue) {
+ if (value instanceof Boolean)
+ return (Boolean) value;
+
+ return defaultValue;
+ }
+
+ public int getInt(int defaultValue) {
+ if (value instanceof Integer)
+ return (Integer) value;
+
+ return defaultValue;
+ }
+
+ public void set(Object value) {
+ this.value = value;
+ }
+
+ public boolean getBoolean() {
+ return getBoolean(false);
+ }
+
+ public int getInt() {
+ return getInt(0);
+ }
+
+ public String getType() {
+ if (value instanceof Integer)
+ return "I";
+ if (value instanceof Boolean)
+ return "B";
+ return "S";
+ }
+
+ public Object getValue() {
+ return value;
+ }
+}
\ No newline at end of file
--- /dev/null
+package com.irtimaled.bbor.forge;
+
+import com.irtimaled.bbor.ClientProxy;
+import net.minecraft.client.Minecraft;
+import net.minecraft.entity.player.EntityPlayer;
+import net.minecraftforge.client.event.RenderWorldLastEvent;
+import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
+import net.minecraftforge.fml.common.gameevent.InputEvent;
+import net.minecraftforge.fml.common.network.FMLNetworkEvent;
+
+public class ForgeClientProxy extends ForgeCommonProxy {
+
+ private ClientProxy proxy;
+
+ @Override
+ public ClientProxy getProxy() {
+ if (proxy == null) {
+ proxy = new ClientProxy();
+ }
+ return proxy;
+ }
+
+ @SubscribeEvent
+ public void onKeyInputEvent(InputEvent.KeyInputEvent evt) {
+ getProxy().keyPressed();
+ }
+
+ @Override
+ protected boolean isRemotePlayer(EntityPlayer player) {
+ if (Minecraft.getMinecraft().isSingleplayer()) {
+ EntityPlayer singlePlayer = Minecraft.getMinecraft().thePlayer;
+ if (singlePlayer == null)
+ return false;
+ return player.getGameProfile() != singlePlayer.getGameProfile();
+ }
+ return true;
+ }
+
+ @SubscribeEvent
+ public void renderWorldLastEvent(RenderWorldLastEvent event) {
+ getProxy().render(event.partialTicks);
+ }
+
+ @SubscribeEvent
+ public void clientConnectionToServerEvent(FMLNetworkEvent.ClientConnectedToServerEvent evt) {
+ if (!evt.isLocal) {
+ getProxy().playerConnectedToServer(evt.manager);
+ }
+ }
+
+ @SubscribeEvent
+ public void clientDisconnectionFromServerEvent(FMLNetworkEvent.ClientDisconnectionFromServerEvent evt) {
+ getProxy().playerDisconnectedFromServer();
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.forge;
+
+import com.irtimaled.bbor.*;
+import com.irtimaled.bbor.forge.messages.*;
+import net.minecraft.entity.player.EntityPlayer;
+import net.minecraft.entity.player.EntityPlayerMP;
+import net.minecraft.server.MinecraftServer;
+import net.minecraftforge.event.world.ChunkEvent;
+import net.minecraftforge.event.world.WorldEvent;
+import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
+import net.minecraftforge.fml.common.gameevent.PlayerEvent;
+import net.minecraftforge.fml.common.gameevent.TickEvent;
+import net.minecraftforge.fml.common.network.NetworkRegistry;
+import net.minecraftforge.fml.common.network.simpleimpl.SimpleNetworkWrapper;
+import net.minecraftforge.fml.relauncher.Side;
+
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+
+public class ForgeCommonProxy implements IEventHandler {
+
+ public Map<EntityPlayerMP, Integer> playerDimensions = new ConcurrentHashMap<EntityPlayerMP, Integer>();
+ private Map<EntityPlayerMP, Set<BoundingBox>> playerBoundingBoxesCache = new HashMap<EntityPlayerMP, Set<BoundingBox>>();
+
+ protected CommonProxy getProxy() {
+ if (commonProxy == null)
+ commonProxy = new CommonProxy();
+ return commonProxy;
+ }
+
+ protected SimpleNetworkWrapper network;
+ private CommonProxy commonProxy;
+
+ public void init(ConfigManager configManager) {
+ getProxy().init(configManager);
+ network = NetworkRegistry.INSTANCE.newSimpleChannel("bbor");
+ network.registerMessage(AddBoundingBoxMessageHandler.class, AddBoundingBoxMessage.class, 0, Side.CLIENT);
+ network.registerMessage(RemoveBoundingBoxMessageHandler.class, RemoveBoundingBoxMessage.class, 1, Side.CLIENT);
+ network.registerMessage(InitializeClientMessageHandler.class, InitializeClientMessage.class, 2, Side.CLIENT);
+ }
+
+ @SubscribeEvent
+ public void worldEvent(WorldEvent.Load event) {
+ getProxy().worldLoaded(event.world);
+ }
+
+ @SubscribeEvent
+ public void chunkEvent(ChunkEvent.Load event) {
+ getProxy().chunkLoaded(event.getChunk());
+ }
+
+ @SubscribeEvent
+ public void playerChangedDimensionEvent(PlayerEvent.PlayerChangedDimensionEvent evt) {
+ if (playerDimensions.containsKey(evt.player)) {
+ EntityPlayerMP player = (EntityPlayerMP) evt.player;
+ int dimension = player.dimension;
+ playerDimensions.put(player, dimension);
+
+ sendToPlayer(player, getProxy().boundingBoxCacheMap.get(dimension));
+ }
+ }
+
+ protected boolean isRemotePlayer(EntityPlayer player) {
+ return true;
+ }
+
+ @SubscribeEvent
+ public void playerLoggedInEvent(PlayerEvent.PlayerLoggedInEvent evt) {
+ if (evt.player instanceof EntityPlayerMP &&
+ isRemotePlayer(evt.player)) {
+ EntityPlayerMP player = (EntityPlayerMP) evt.player;
+ initializeClient(player);
+ int dimension = player.dimension;
+ playerDimensions.put(player, dimension);
+ sendToPlayer(player, getProxy().boundingBoxCacheMap.get(dimension));
+ }
+ }
+
+ @SubscribeEvent
+ public void playerLoggedOutEvent(PlayerEvent.PlayerLoggedOutEvent evt) {
+ if (playerDimensions.containsKey(evt.player)) {
+ playerDimensions.remove(evt.player);
+ playerBoundingBoxesCache.remove(evt.player);
+ }
+ }
+
+ @SubscribeEvent
+ public void tickEvent(TickEvent event) {
+ for (EntityPlayerMP player : playerDimensions.keySet()) {
+
+ MinecraftServer mc = MinecraftServer.getServer();
+ if (!mc.getConfigurationManager().playerEntityList.contains(player)) {
+ playerDimensions.remove(player);
+ } else {
+ int dimension = playerDimensions.get(player);
+ if (getProxy().boundingBoxCacheMap.containsKey(dimension)) {
+ sendToPlayer(player, getProxy().boundingBoxCacheMap.get(dimension));
+ }
+ }
+ }
+ }
+
+ private void initializeClient(EntityPlayerMP player) {
+ network.sendTo(InitializeClientMessage.from(getProxy().getWorldData()), player);
+ }
+
+ private void sendToPlayer(EntityPlayerMP player, BoundingBoxCache boundingBoxCache) {
+ Map<BoundingBox, Set<BoundingBox>> cacheSubset = getBoundingBoxMap(player, boundingBoxCache.getBoundingBoxes());
+
+ int dimension = player.dimension;
+ if (cacheSubset.keySet().size() > 0) {
+ Logger.info("send %d entries to %s (%d)", cacheSubset.keySet().size(), player.getDisplayNameString(), dimension);
+ }
+
+ for (BoundingBox key : cacheSubset.keySet()) {
+ Set<BoundingBox> boundingBoxes = cacheSubset.get(key);
+ network.sendTo(AddBoundingBoxMessage.from(dimension, key, boundingBoxes), player);
+
+ if (!playerBoundingBoxesCache.containsKey(player)) {
+ playerBoundingBoxesCache.put(player, new HashSet<BoundingBox>());
+ }
+ playerBoundingBoxesCache.get(player).add(key);
+ }
+ }
+
+ private Map<BoundingBox, Set<BoundingBox>> getBoundingBoxMap(EntityPlayerMP player, Map<BoundingBox, Set<BoundingBox>> boundingBoxMap) {
+ Map<BoundingBox, Set<BoundingBox>> cacheSubset = new HashMap<BoundingBox, Set<BoundingBox>>();
+ for (BoundingBox key : boundingBoxMap.keySet()) {
+ if (!playerBoundingBoxesCache.containsKey(player) || !playerBoundingBoxesCache.get(player).contains(key)) {
+ cacheSubset.put(key, boundingBoxMap.get(key));
+ }
+ }
+ return cacheSubset;
+ }
+
+ public void boundingBoxRemoved(BoundingBox bb) {
+ // the only bounding boxes that can change are spawn or villages - both of these are in overworld so I guess
+ // hard coding dimension 0 is okay.
+ RemoveBoundingBoxMessage message = RemoveBoundingBoxMessage.from(0, bb);
+ for (EntityPlayerMP player : playerDimensions.keySet()) {
+ if (player.dimension == 0) {
+ Logger.info("remove 1 entry from %s (0)", player.getDisplayNameString());
+ network.sendTo(message, player);
+
+ if (playerBoundingBoxesCache.containsKey(player) &&
+ playerBoundingBoxesCache.get(player).contains(bb)) {
+ playerBoundingBoxesCache.get(player).remove(bb);
+ }
+ }
+ }
+ }
+
+ public void setWorldData(WorldData worldData) {
+ getProxy().setWorldData(worldData);
+ }
+
+ public void setConfigManager(ConfigManager configManager) {
+ getProxy().configManager = configManager;
+ }
+
+ public void addBoundingBox(int dimension, BoundingBox key, Set<BoundingBox> boundingBoxes) {
+ Map<Integer, BoundingBoxCache> boundingBoxCacheMap = getProxy().boundingBoxCacheMap;
+ if (!boundingBoxCacheMap.containsKey(dimension)) {
+ boundingBoxCacheMap.put(dimension, new BoundingBoxCache());
+ }
+
+ boundingBoxCacheMap.get(dimension).addBoundingBoxes(key, boundingBoxes);
+ }
+
+ public void removeBoundingBox(int dimension, BoundingBox key) {
+ Map<Integer, BoundingBoxCache> boundingBoxCacheMap = getProxy().boundingBoxCacheMap;
+
+ if (boundingBoxCacheMap.containsKey(dimension)) {
+ boundingBoxCacheMap.get(dimension).removeBoundingBox(key);
+ }
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.forge;
+
+import com.irtimaled.bbor.ConfigManager;
+import net.minecraftforge.common.MinecraftForge;
+import net.minecraftforge.fml.common.FMLCommonHandler;
+import net.minecraftforge.fml.common.Mod;
+import net.minecraftforge.fml.common.SidedProxy;
+import net.minecraftforge.fml.common.event.FMLInitializationEvent;
+import net.minecraftforge.fml.common.event.FMLPreInitializationEvent;
+import net.minecraftforge.fml.common.network.simpleimpl.SimpleNetworkWrapper;
+
+@Mod(modid = ForgeMod.MODID, name = ForgeMod.NAME, version = ForgeMod.VERSION)
+public class ForgeMod {
+
+ public static final String MODID = "bbor";
+ public static final String NAME = "Bounding Box Outline Reloaded";
+ public static final String VERSION = "1.0.0-beta8";
+
+ private ConfigManager configManager;
+
+ public SimpleNetworkWrapper network;
+
+ @Mod.Instance()
+ public static ForgeMod instance;
+
+ @SidedProxy(clientSide = "com.irtimaled.bbor.forge.ForgeClientProxy", serverSide = "com.irtimaled.bbor.forge.ForgeCommonProxy")
+ public static ForgeCommonProxy proxy;
+
+
+ @Mod.EventHandler
+ public void preInit(FMLPreInitializationEvent evt) {
+ configManager = new ConfigManager(evt.getModConfigurationDirectory());
+ }
+
+ @Mod.EventHandler
+ public void load(FMLInitializationEvent evt) {
+ MinecraftForge.EVENT_BUS.register(proxy);
+ FMLCommonHandler.instance().bus().register(proxy);
+
+ proxy.init(configManager);
+ }
+}
+
+
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.BoundingBox;
+import io.netty.buffer.ByteBuf;
+import net.minecraftforge.fml.common.network.ByteBufUtils;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
+
+import java.util.HashSet;
+import java.util.Set;
+
+public class AddBoundingBoxMessage implements IMessage {
+ private int dimension;
+ private BoundingBox key;
+ private Set<BoundingBox> boundingBoxes;
+
+ public static AddBoundingBoxMessage from(int dimension, BoundingBox key, Set<BoundingBox> boundingBoxes) {
+ AddBoundingBoxMessage message = new AddBoundingBoxMessage();
+ message.dimension = dimension;
+ message.key = key;
+ message.boundingBoxes = boundingBoxes;
+ return message;
+ }
+
+ @Override
+ public void fromBytes(ByteBuf buf) {
+ dimension = ByteBufUtils.readVarInt(buf, 5);
+ key = BoundingBoxDeserializer.deserialize(buf);
+ boundingBoxes = new HashSet<BoundingBox>();
+ while (buf.isReadable()) {
+ BoundingBox boundingBox = BoundingBoxDeserializer.deserialize(buf);
+ boundingBoxes.add(boundingBox);
+ }
+ if (boundingBoxes.size() == 0)
+ boundingBoxes.add(key);
+ }
+
+ @Override
+ public void toBytes(ByteBuf buf) {
+ ByteBufUtils.writeVarInt(buf, dimension, 5);
+ BoundingBoxSerializer.serialize(key, buf);
+ if (boundingBoxes != null &&
+ boundingBoxes.size() > 1) {
+ for (BoundingBox boundingBox : boundingBoxes) {
+ BoundingBoxSerializer.serialize(boundingBox, buf);
+ }
+ }
+ }
+
+ public int getDimension() {
+ return dimension;
+ }
+
+ public BoundingBox getKey() {
+ return key;
+ }
+
+ public Set<BoundingBox> getBoundingBoxes() {
+ return boundingBoxes;
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.forge.ForgeMod;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
+import net.minecraftforge.fml.common.network.simpleimpl.MessageContext;
+
+public class AddBoundingBoxMessageHandler implements IMessageHandler<AddBoundingBoxMessage, IMessage> {
+ @Override
+ public IMessage onMessage(AddBoundingBoxMessage message, MessageContext ctx) {
+ ForgeMod.proxy.addBoundingBox(message.getDimension(), message.getKey(), message.getBoundingBoxes());
+ return null;
+ }
+}
\ No newline at end of file
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.BoundingBox;
+import com.irtimaled.bbor.BoundingBoxStructure;
+import com.irtimaled.bbor.BoundingBoxVillage;
+import io.netty.buffer.ByteBuf;
+import net.minecraft.util.BlockPos;
+import net.minecraftforge.fml.common.network.ByteBufUtils;
+
+import java.awt.*;
+
+public class BoundingBoxDeserializer {
+ public static BoundingBox deserialize(ByteBuf buf) {
+ char type = (char) ByteBufUtils.readVarShort(buf);
+ switch (type) {
+ case 'V':
+ return deserializeVillage(buf);
+ case 'S':
+ return deserializeStructure(buf);
+ }
+ return null;
+ }
+
+ private static BoundingBox deserializeStructure(ByteBuf buf) {
+ BlockPos minBlockPos = deserializeBlockPos(buf);
+ BlockPos maxBlockPos = deserializeBlockPos(buf);
+ Color color = new Color(ByteBufUtils.readVarInt(buf, 5));
+ return BoundingBoxStructure.from(minBlockPos, maxBlockPos, color);
+ }
+
+ private static BoundingBox deserializeVillage(ByteBuf buf) {
+ BlockPos center = deserializeBlockPos(buf);
+ int radius = ByteBufUtils.readVarInt(buf, 5);
+ boolean spawnsIronGolems = ByteBufUtils.readVarShort(buf) == 1;
+ Color color = new Color(ByteBufUtils.readVarInt(buf, 5));
+ return BoundingBoxVillage.from(center, radius, spawnsIronGolems, color);
+ }
+
+ private static BlockPos deserializeBlockPos(ByteBuf buf) {
+ int x = ByteBufUtils.readVarInt(buf, 5);
+ int y = ByteBufUtils.readVarInt(buf, 5);
+ int z = ByteBufUtils.readVarInt(buf, 5);
+ return new BlockPos(x, y, z);
+ }
+}
\ No newline at end of file
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.BoundingBox;
+import com.irtimaled.bbor.BoundingBoxStructure;
+import com.irtimaled.bbor.BoundingBoxVillage;
+import io.netty.buffer.ByteBuf;
+import net.minecraft.util.BlockPos;
+import net.minecraftforge.fml.common.network.ByteBufUtils;
+
+import java.awt.*;
+
+public class BoundingBoxSerializer {
+
+ public static void serialize(BoundingBox boundingBox, ByteBuf buf) {
+ if (boundingBox instanceof BoundingBoxVillage) {
+ serializeVillage((BoundingBoxVillage) boundingBox, buf);
+ }
+ if (boundingBox instanceof BoundingBoxStructure) {
+ serializeStructure((BoundingBoxStructure) boundingBox, buf);
+ }
+ }
+
+
+ private static void serializeVillage(BoundingBoxVillage boundingBox, ByteBuf buf) {
+ ByteBufUtils.writeVarShort(buf, 'V');
+ serializeBlockPos(boundingBox.getCenter(), buf);
+ ByteBufUtils.writeVarInt(buf, boundingBox.getRadius(), 5);
+ ByteBufUtils.writeVarShort(buf, boundingBox.getSpawnsIronGolems() ? 1 : 0);
+ serializeColor(boundingBox.getColor(), buf);
+ }
+
+ private static void serializeStructure(BoundingBoxStructure boundingBox, ByteBuf buf) {
+ ByteBufUtils.writeVarShort(buf, 'S');
+ serializeCuboid(boundingBox, buf);
+ serializeColor(boundingBox.getColor(), buf);
+ }
+
+ private static void serializeColor(Color color, ByteBuf buf) {
+ ByteBufUtils.writeVarInt(buf, color.getRGB(), 5);
+ }
+
+ private static void serializeCuboid(BoundingBox boundingBox, ByteBuf buf) {
+ serializeBlockPos(boundingBox.getMinBlockPos(), buf);
+ serializeBlockPos(boundingBox.getMaxBlockPos(), buf);
+ }
+
+ private static void serializeBlockPos(BlockPos blockPos, ByteBuf buf) {
+ ByteBufUtils.writeVarInt(buf, blockPos.getX(), 5);
+ ByteBufUtils.writeVarInt(buf, blockPos.getY(), 5);
+ ByteBufUtils.writeVarInt(buf, blockPos.getZ(), 5);
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.WorldData;
+import io.netty.buffer.ByteBuf;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
+
+public class InitializeClientMessage implements IMessage {
+
+ private WorldData worldData;
+
+ public static InitializeClientMessage from(WorldData worldData) {
+ InitializeClientMessage message = new InitializeClientMessage();
+ message.worldData = new WorldData(worldData.getSeed(), worldData.getSpawnX(), worldData.getSpawnZ());
+ return message;
+ }
+
+
+ @Override
+ public void fromBytes(ByteBuf buf) {
+ long seed = buf.readLong();
+ int spawnX = buf.readInt();
+ int spawnZ = buf.readInt();
+ worldData = new WorldData(seed, spawnX, spawnZ);
+ }
+
+ @Override
+ public void toBytes(ByteBuf buf) {
+ buf.writeLong(worldData.getSeed());
+ buf.writeInt(worldData.getSpawnX());
+ buf.writeInt(worldData.getSpawnZ());
+ }
+
+ public WorldData getWorldData() {
+ return worldData;
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.forge.ForgeMod;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
+import net.minecraftforge.fml.common.network.simpleimpl.MessageContext;
+
+public class InitializeClientMessageHandler implements IMessageHandler<InitializeClientMessage, IMessage> {
+ @Override
+ public IMessage onMessage(InitializeClientMessage message, MessageContext ctx) {
+ ForgeMod.proxy.setWorldData(message.getWorldData());
+ return null;
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.BoundingBox;
+import io.netty.buffer.ByteBuf;
+import net.minecraftforge.fml.common.network.ByteBufUtils;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
+
+public class RemoveBoundingBoxMessage implements IMessage {
+ private int dimension;
+ private BoundingBox key;
+
+ public static RemoveBoundingBoxMessage from(int dimension, BoundingBox key) {
+ RemoveBoundingBoxMessage message = new RemoveBoundingBoxMessage();
+ message.dimension = dimension;
+ message.key = key;
+ return message;
+ }
+
+ @Override
+ public void fromBytes(ByteBuf buf) {
+ dimension = ByteBufUtils.readVarInt(buf, 5);
+ key = BoundingBoxDeserializer.deserialize(buf);
+ }
+
+ @Override
+ public void toBytes(ByteBuf buf) {
+ ByteBufUtils.writeVarInt(buf, dimension, 5);
+ BoundingBoxSerializer.serialize(key, buf);
+ }
+
+ public int getDimension() {
+ return dimension;
+ }
+
+ public BoundingBox getKey() {
+ return key;
+ }
+}
--- /dev/null
+package com.irtimaled.bbor.forge.messages;
+
+import com.irtimaled.bbor.forge.ForgeMod;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
+import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
+import net.minecraftforge.fml.common.network.simpleimpl.MessageContext;
+
+public class RemoveBoundingBoxMessageHandler implements IMessageHandler<RemoveBoundingBoxMessage, IMessage> {
+ @Override
+ public IMessage onMessage(RemoveBoundingBoxMessage message, MessageContext ctx) {
+
+ ForgeMod.proxy.removeBoundingBox(message.getDimension(), message.getKey());
+ return null;
+ }
+}
\ No newline at end of file
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.BoundingBox;
-import io.netty.buffer.ByteBuf;
-import net.minecraftforge.fml.common.network.ByteBufUtils;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
-
-import java.util.HashSet;
-import java.util.Set;
-
-public class AddBoundingBoxMessage implements IMessage {
- private int dimension;
- private BoundingBox key;
- private Set<BoundingBox> boundingBoxes;
-
- public static AddBoundingBoxMessage from(int dimension, BoundingBox key, Set<BoundingBox> boundingBoxes) {
- AddBoundingBoxMessage message = new AddBoundingBoxMessage();
- message.dimension = dimension;
- message.key = key;
- message.boundingBoxes = boundingBoxes;
- return message;
- }
-
- @Override
- public void fromBytes(ByteBuf buf) {
- dimension = ByteBufUtils.readVarInt(buf, 5);
- key = BoundingBoxDeserializer.deserialize(buf);
- boundingBoxes = new HashSet<BoundingBox>();
- while (buf.isReadable()) {
- BoundingBox boundingBox = BoundingBoxDeserializer.deserialize(buf);
- boundingBoxes.add(boundingBox);
- }
- if (boundingBoxes.size() == 0)
- boundingBoxes.add(key);
- }
-
- @Override
- public void toBytes(ByteBuf buf) {
- ByteBufUtils.writeVarInt(buf, dimension, 5);
- BoundingBoxSerializer.serialize(key, buf);
- if (boundingBoxes != null &&
- boundingBoxes.size() > 1) {
- for (BoundingBox boundingBox : boundingBoxes) {
- BoundingBoxSerializer.serialize(boundingBox, buf);
- }
- }
- }
-
- public int getDimension() {
- return dimension;
- }
-
- public BoundingBox getKey() {
- return key;
- }
-
- public Set<BoundingBox> getBoundingBoxes() {
- return boundingBoxes;
- }
-}
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.BoundingBoxCache;
-import com.irtimaled.bbor.BoundingBoxOutlineReloaded;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
-import net.minecraftforge.fml.common.network.simpleimpl.MessageContext;
-
-import java.util.Map;
-
-public class AddBoundingBoxMessageHandler implements IMessageHandler<AddBoundingBoxMessage, IMessage> {
- @Override
- public IMessage onMessage(AddBoundingBoxMessage message, MessageContext ctx) {
-
- Map<Integer, BoundingBoxCache> boundingBoxCacheMap = BoundingBoxOutlineReloaded.proxy.boundingBoxCacheMap;
- int dimension = message.getDimension();
- if (!boundingBoxCacheMap.containsKey(dimension)) {
- boundingBoxCacheMap.put(dimension, new BoundingBoxCache());
- }
-
- boundingBoxCacheMap.get(dimension).addBoundingBox(message.getKey(), message.getBoundingBoxes());
- return null;
- }
-}
\ No newline at end of file
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.BoundingBox;
-import com.irtimaled.bbor.BoundingBoxStructure;
-import com.irtimaled.bbor.BoundingBoxVillage;
-import io.netty.buffer.ByteBuf;
-import net.minecraft.util.BlockPos;
-import net.minecraftforge.fml.common.network.ByteBufUtils;
-
-import java.awt.*;
-
-public class BoundingBoxDeserializer {
- public static BoundingBox deserialize(ByteBuf buf) {
- char type = (char) ByteBufUtils.readVarShort(buf);
- switch (type) {
- case 'V':
- return deserializeVillage(buf);
- case 'S':
- return deserializeStructure(buf);
- }
- return null;
- }
-
- private static BoundingBox deserializeStructure(ByteBuf buf) {
- BlockPos minBlockPos = deserializeBlockPos(buf);
- BlockPos maxBlockPos = deserializeBlockPos(buf);
- Color color = new Color(ByteBufUtils.readVarInt(buf, 5));
- return BoundingBoxStructure.from(minBlockPos, maxBlockPos, color);
- }
-
- private static BoundingBox deserializeVillage(ByteBuf buf) {
- BlockPos center = deserializeBlockPos(buf);
- int radius = ByteBufUtils.readVarInt(buf, 5);
- boolean spawnsIronGolems = ByteBufUtils.readVarShort(buf) == 1;
- Color color = new Color(ByteBufUtils.readVarInt(buf, 5));
- return BoundingBoxVillage.from(center, radius, spawnsIronGolems, color);
- }
-
- private static BlockPos deserializeBlockPos(ByteBuf buf) {
- int x = ByteBufUtils.readVarInt(buf, 5);
- int y = ByteBufUtils.readVarInt(buf, 5);
- int z = ByteBufUtils.readVarInt(buf, 5);
- return new BlockPos(x, y, z);
- }
-}
\ No newline at end of file
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.BoundingBox;
-import com.irtimaled.bbor.BoundingBoxStructure;
-import com.irtimaled.bbor.BoundingBoxVillage;
-import io.netty.buffer.ByteBuf;
-import net.minecraft.util.BlockPos;
-import net.minecraftforge.fml.common.network.ByteBufUtils;
-
-import java.awt.*;
-
-public class BoundingBoxSerializer {
-
- public static void serialize(BoundingBox boundingBox, ByteBuf buf) {
- if (boundingBox instanceof BoundingBoxVillage) {
- serializeVillage((BoundingBoxVillage) boundingBox, buf);
- }
- if (boundingBox instanceof BoundingBoxStructure) {
- serializeStructure((BoundingBoxStructure) boundingBox, buf);
- }
- }
-
-
- private static void serializeVillage(BoundingBoxVillage boundingBox, ByteBuf buf) {
- ByteBufUtils.writeVarShort(buf, 'V');
- serializeBlockPos(boundingBox.getCenter(), buf);
- ByteBufUtils.writeVarInt(buf, boundingBox.getRadius(), 5);
- ByteBufUtils.writeVarShort(buf, boundingBox.getSpawnsIronGolems() ? 1 : 0);
- serializeColor(boundingBox.getColor(), buf);
- }
-
- private static void serializeStructure(BoundingBoxStructure boundingBox, ByteBuf buf) {
- ByteBufUtils.writeVarShort(buf, 'S');
- serializeCuboid(boundingBox, buf);
- serializeColor(boundingBox.getColor(), buf);
- }
-
- private static void serializeColor(Color color, ByteBuf buf) {
- ByteBufUtils.writeVarInt(buf, color.getRGB(), 5);
- }
-
- private static void serializeCuboid(BoundingBox boundingBox, ByteBuf buf) {
- serializeBlockPos(boundingBox.getMinBlockPos(), buf);
- serializeBlockPos(boundingBox.getMaxBlockPos(), buf);
- }
-
- private static void serializeBlockPos(BlockPos blockPos, ByteBuf buf) {
- ByteBufUtils.writeVarInt(buf, blockPos.getX(), 5);
- ByteBufUtils.writeVarInt(buf, blockPos.getY(), 5);
- ByteBufUtils.writeVarInt(buf, blockPos.getZ(), 5);
- }
-}
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.IWorldData;
-import io.netty.buffer.ByteBuf;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
-
-public class InitializeClientMessage implements IMessage, IWorldData {
-
- private long seed;
- private int spawnX;
- private int spawnZ;
-
- public static InitializeClientMessage from(long seed, int spawnX, int spawnZ) {
- InitializeClientMessage message = new InitializeClientMessage();
- message.seed = seed;
- message.spawnX = spawnX;
- message.spawnZ = spawnZ;
- return message;
- }
-
- @Override
- public void fromBytes(ByteBuf buf) {
- seed = buf.readLong();
- spawnX = buf.readInt();
- spawnZ = buf.readInt();
- }
-
- @Override
- public void toBytes(ByteBuf buf) {
- buf.writeLong(seed);
- buf.writeInt(spawnX);
- buf.writeInt(spawnZ);
- }
-
- @Override
- public long getSeed() {
- return seed;
- }
-
- @Override
- public int getSpawnX() { return spawnX; }
-
- @Override
- public int getSpawnZ() { return spawnZ; }
-}
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.BoundingBoxOutlineReloaded;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
-import net.minecraftforge.fml.common.network.simpleimpl.MessageContext;
-
-public class InitializeClientMessageHandler implements IMessageHandler<InitializeClientMessage, IMessage> {
- @Override
- public IMessage onMessage(InitializeClientMessage message, MessageContext ctx) {
- BoundingBoxOutlineReloaded.proxy.setWorldData(message);
- return null;
- }
-}
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.BoundingBox;
-import io.netty.buffer.ByteBuf;
-import net.minecraftforge.fml.common.network.ByteBufUtils;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
-
-public class RemoveBoundingBoxMessage implements IMessage {
- private int dimension;
- private BoundingBox key;
-
- public static RemoveBoundingBoxMessage from(int dimension, BoundingBox key) {
- RemoveBoundingBoxMessage message = new RemoveBoundingBoxMessage();
- message.dimension = dimension;
- message.key = key;
- return message;
- }
-
- @Override
- public void fromBytes(ByteBuf buf) {
- dimension = ByteBufUtils.readVarInt(buf, 5);
- key = BoundingBoxDeserializer.deserialize(buf);
- }
-
- @Override
- public void toBytes(ByteBuf buf) {
- ByteBufUtils.writeVarInt(buf, dimension, 5);
- BoundingBoxSerializer.serialize(key, buf);
- }
-
- public int getDimension() {
- return dimension;
- }
-
- public BoundingBox getKey() {
- return key;
- }
-}
+++ /dev/null
-package com.irtimaled.bbor.messages;
-
-import com.irtimaled.bbor.BoundingBoxCache;
-import com.irtimaled.bbor.BoundingBoxOutlineReloaded;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
-import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
-import net.minecraftforge.fml.common.network.simpleimpl.MessageContext;
-
-import java.util.Map;
-
-public class RemoveBoundingBoxMessageHandler implements IMessageHandler<RemoveBoundingBoxMessage, IMessage> {
- @Override
- public IMessage onMessage(RemoveBoundingBoxMessage message, MessageContext ctx) {
-
- Map<Integer, BoundingBoxCache> boundingBoxCacheMap = BoundingBoxOutlineReloaded.proxy.boundingBoxCacheMap;
- int dimension = message.getDimension();
- if (boundingBoxCacheMap.containsKey(dimension)) {
- boundingBoxCacheMap.get(dimension).removeBoundingBox(message.getKey());
- }
- return null;
- }
-}
\ No newline at end of file
+++ /dev/null
-language.name=English
-language.region=US
-language.code=en_US
-
-key.bbor.hotKey=Toggle On/Off
-key.categories.bbor=Bounding Box Outline Reloaded