diff --git a/src/main/java/net/minecraft/world/World.java b/src/main/java/net/minecraft/world/World.java index aca852d..c1eb002 100644 --- a/src/main/java/net/minecraft/world/World.java +++ b/src/main/java/net/minecraft/world/World.java @@ -449,25 +449,27 @@ if ((p_147465_6_ & 1) != 0) { block1 = chunk.getBlock(p_147465_1_ & 15, p_147465_2_, p_147465_3_ & 15); - if (this.captureBlockSnapshots && block1 != null && !this.isRemote) - { - blockSnapshot = net.minecraftforge.common.util.BlockSnapshot.getBlockSnapshot(this, p_147465_1_, p_147465_2_, p_147465_3_, p_147465_6_); - this.capturedBlockSnapshots.add(blockSnapshot); - } + } + + if (this.captureBlockSnapshots && !this.isRemote) + { + blockSnapshot = net.minecraftforge.common.util.BlockSnapshot.getBlockSnapshot(this, p_147465_1_, p_147465_2_, p_147465_3_, p_147465_6_); + this.capturedBlockSnapshots.add(blockSnapshot); } boolean flag = chunk.func_150807_a(p_147465_1_ & 15, p_147465_2_, p_147465_3_ & 15, p_147465_4_, p_147465_5_); - if (!flag && this.captureBlockSnapshots && block1 != null && !this.isRemote) + if (!flag && blockSnapshot != null) { this.capturedBlockSnapshots.remove(blockSnapshot); + blockSnapshot = null; } this.theProfiler.startSection("checkLight"); this.func_147451_t(p_147465_1_, p_147465_2_, p_147465_3_); this.theProfiler.endSection(); - if (flag && !this.captureBlockSnapshots) // Don't notify clients or update physics while capturing blockstates + if (flag && blockSnapshot == null) // Don't notify clients or update physics while capturing blockstates { // Modularize client and physic updates this.markAndNotifyBlock(p_147465_1_, p_147465_2_, p_147465_3_, chunk, block1, p_147465_4_, p_147465_6_); diff --git a/src/main/java/net/minecraft/world/gen/layer/GenLayerBiome.java b/src/main/java/net/minecraft/world/gen/layer/GenLayerBiome.java index 5690396..631c88a 100644 --- a/src/main/java/net/minecraft/world/gen/layer/GenLayerBiome.java +++ b/src/main/java/net/minecraft/world/gen/layer/GenLayerBiome.java @@ -129,9 +129,7 @@ { List biomeList = biomes[type.ordinal()]; int totalWeight = WeightedRandom.getTotalWeight(biomeList); - int rand = nextInt(totalWeight / 10) * 10; - int weight = rand + (BiomeManager.isTypeListModded(type) ? nextInt(Math.min(10, totalWeight - rand)) : 0); - + int weight = BiomeManager.isTypeListModded(type)?nextInt(totalWeight):nextInt(totalWeight / 10) * 10; return (BiomeEntry)WeightedRandom.getItem(biomeList, weight); } } \ No newline at end of file diff --git a/src/main/java/net/minecraftforge/client/ForgeHooksClient.java b/src/main/java/net/minecraftforge/client/ForgeHooksClient.java index bd6f5ca..b796150 100644 --- a/src/main/java/net/minecraftforge/client/ForgeHooksClient.java +++ b/src/main/java/net/minecraftforge/client/ForgeHooksClient.java @@ -325,7 +325,7 @@ //According to ChickenBones, Mumfrey and Pig The only real use is in the FBO. //So lets default to normal init to fix the issues yet add the bits to the FBO. Display.create(format); - stencilBits = 8; + stencilBits = 0; return; } try diff --git a/src/main/java/net/minecraftforge/common/BiomeManager.java b/src/main/java/net/minecraftforge/common/BiomeManager.java index a08dbe3..53da850 100644 --- a/src/main/java/net/minecraftforge/common/BiomeManager.java +++ b/src/main/java/net/minecraftforge/common/BiomeManager.java @@ -75,6 +75,8 @@ currentBiomes[BiomeType.ICY.ordinal()] = new TrackedList(list); list.clear(); + currentBiomes[BiomeType.DESERT.ordinal()] = new TrackedList(list); + return currentBiomes; } @@ -292,4 +294,4 @@ return isModded; } } -} \ No newline at end of file +} diff --git a/src/main/java/net/minecraftforge/common/ForgeModContainer.java b/src/main/java/net/minecraftforge/common/ForgeModContainer.java index 3731f8b..a423d06 100644 --- a/src/main/java/net/minecraftforge/common/ForgeModContainer.java +++ b/src/main/java/net/minecraftforge/common/ForgeModContainer.java @@ -51,6 +51,7 @@ import cpw.mods.fml.common.event.FMLPreInitializationEvent; import cpw.mods.fml.common.event.FMLServerStartingEvent; import cpw.mods.fml.common.eventhandler.SubscribeEvent; +import cpw.mods.fml.common.gameevent.PlayerEvent; import cpw.mods.fml.common.network.NetworkRegistry; public class ForgeModContainer extends DummyModContainer implements WorldAccessContainer @@ -252,6 +253,12 @@ } } } + + @SubscribeEvent + public void playerLogin(PlayerEvent.PlayerLoggedInEvent event) + { + UsernameCache.setUsername(event.player.getGameProfile().getId(), event.player.getGameProfile().getName()); + } @Override public boolean registerBus(EventBus bus, LoadController controller) diff --git a/src/main/java/net/minecraftforge/common/ForgeVersion.java b/src/main/java/net/minecraftforge/common/ForgeVersion.java index 7529af3..d0f29bd 100644 --- a/src/main/java/net/minecraftforge/common/ForgeVersion.java +++ b/src/main/java/net/minecraftforge/common/ForgeVersion.java @@ -23,7 +23,7 @@ //This number is incremented every minecraft release, never reset public static final int minorVersion = 13; //This number is incremented every time a interface changes or new major feature is added, and reset every Minecraft version - public static final int revisionVersion = 1; + public static final int revisionVersion = 2; //This number is incremented every time Jenkins builds Forge, and never reset. Should always be 0 in the repo code. public static final int buildVersion = 0; diff --git a/src/main/java/net/minecraftforge/common/MinecraftForge.java b/src/main/java/net/minecraftforge/common/MinecraftForge.java index 4deeaa1..3979a7f 100644 --- a/src/main/java/net/minecraftforge/common/MinecraftForge.java +++ b/src/main/java/net/minecraftforge/common/MinecraftForge.java @@ -53,6 +53,8 @@ //Force these classes to be defined, Should prevent derp error hiding. new CrashReport("ThisIsFake", new Exception("Not real")); + + UsernameCache.load(); } public static String getBrandingVersion() diff --git a/src/main/java/net/minecraftforge/common/UsernameCache.java b/src/main/java/net/minecraftforge/common/UsernameCache.java new file mode 100644 index 0000000..c170347 --- /dev/null +++ b/src/main/java/net/minecraftforge/common/UsernameCache.java @@ -0,0 +1,202 @@ +package net.minecraftforge.common; + +import static com.google.common.base.Preconditions.checkNotNull; + +import java.io.File; +import java.io.IOException; +import java.lang.reflect.Type; +import java.nio.charset.Charset; +import java.util.Map; +import java.util.UUID; + +import javax.annotation.Nullable; + +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +import com.google.common.base.Charsets; +import com.google.common.collect.ImmutableMap; +import com.google.common.collect.Maps; +import com.google.common.io.Files; +import com.google.common.reflect.TypeToken; +import com.google.gson.Gson; +import com.google.gson.GsonBuilder; +import com.google.gson.JsonSyntaxException; + +import cpw.mods.fml.relauncher.FMLInjectionData; + +/** + * Caches player's last known usernames + *

+ * Modders should use {@link #getLastKnownUsername(UUID)} to determine a players + * last known username.
+ * For convenience, {@link #getMap()} is provided to get an immutable copy of + * the caches underlying map. + */ +public final class UsernameCache { + + private static Map map = Maps.newHashMap(); + + private static final Charset charset = Charsets.UTF_8; + + private static final File saveFile = new File( /* The minecraft dir */(File) FMLInjectionData.data()[6], "usernamecache.json"); + private static final Gson gson = new GsonBuilder().setPrettyPrinting().create(); + + private static final Logger log = LogManager.getLogger(UsernameCache.class); + + private UsernameCache() {} + + /** + * Set a player's current username + * + * @param uuid + * the player's {@link java.util.UUID UUID} + * @param username + * the player's username + */ + protected static void setUsername(UUID uuid, String username) + { + checkNotNull(uuid); + checkNotNull(username); + + if (username.equals(map.get(uuid))) return; + + map.put(uuid, username); + save(); + } + + /** + * Remove a player's username from the cache + * + * @param uuid + * the player's {@link java.util.UUID UUID} + * @return if the cache contained the user + */ + protected static boolean removeUsername(UUID uuid) + { + checkNotNull(uuid); + + if (map.remove(uuid) != null) + { + save(); + return true; + } + + return false; + } + + /** + * Get the player's last known username + *

+ * May be null + * + * @param uuid + * the player's {@link java.util.UUID UUID} + * @return the player's last known username, or null if the + * cache doesn't have a record of the last username + */ + @Nullable + public static String getLastKnownUsername(UUID uuid) + { + checkNotNull(uuid); + return map.get(uuid); + } + + /** + * Check if the cache contains the given player's username + * + * @param uuid + * the player's {@link java.util.UUID UUID} + * @return if the cache contains a username for the given player + */ + public static boolean containsUUID(UUID uuid) + { + checkNotNull(uuid); + return map.containsKey(uuid); + } + + /** + * Get an immutable copy of the cache's underlying map + * + * @return the map + */ + public static Map getMap() + { + return ImmutableMap.copyOf(map); + } + + /** + * Save the cache to file + */ + protected static void save() + { + new SaveThread(gson.toJson(map)).start(); + } + + /** + * Load the cache from file + */ + protected static void load() + { + if (!saveFile.exists()) return; + + try + { + + String json = Files.toString(saveFile, charset); + Type type = new TypeToken>() {}.getType(); + + map = gson.fromJson(json, type); + } + catch (JsonSyntaxException e) + { + log.error("Could not parse username cache file as valid json, deleting file", e); + saveFile.delete(); + } + catch (IOException e) + { + log.error("Failed to read username cache file from disk, deleting file", e); + saveFile.delete(); + } + finally + { + // Can sometimes occur when the json file is malformed + if (map == null) + { + map = Maps.newHashMap(); + } + } + } + + /** + * Used for saving the {@link com.google.gson.Gson#toJson(Object) Gson} + * representation of the cache to disk + */ + private static class SaveThread extends Thread { + + /** The data that will be saved to disk */ + private final String data; + + public SaveThread(String data) + { + this.data = data; + } + + @Override + public void run() + { + try + { + // Make sure we don't save when another thread is still saving + synchronized (saveFile) + { + Files.write(data, saveFile, charset); + } + } + catch (IOException e) + { + log.error("Failed to save username cache to file!", e); + } + } + } +} \ No newline at end of file diff --git a/src/main/resources/fmlversion.properties b/src/main/resources/fmlversion.properties index 7c75027..966762a 100644 --- a/src/main/resources/fmlversion.properties +++ b/src/main/resources/fmlversion.properties @@ -1,6 +1,6 @@ fmlbuild.major.number=7 fmlbuild.minor.number=10 fmlbuild.revision.number=85 -fmlbuild.build.number=6 +fmlbuild.build.number=19 fmlbuild.mcversion=1.7.10 fmlbuild.mcpversion=9.05