diff --git a/src/main/java/cpw/mods/fml/common/FMLCommonHandler.java b/src/main/java/cpw/mods/fml/common/FMLCommonHandler.java index 40c2c96971..0ea0c04ba7 100644 --- a/src/main/java/cpw/mods/fml/common/FMLCommonHandler.java +++ b/src/main/java/cpw/mods/fml/common/FMLCommonHandler.java @@ -324,7 +324,7 @@ public class FMLCommonHandler public void onPlayerPostTick(EntityPlayer player) { - bus().post(new TickEvent.PlayerTickEvent(Phase.START, player)); + bus().post(new TickEvent.PlayerTickEvent(Phase.END, player)); } public void registerCrashCallable(ICrashCallable callable) diff --git a/src/main/java/cpw/mods/fml/common/Loader.java b/src/main/java/cpw/mods/fml/common/Loader.java index 912d30b77e..d92efa0b13 100644 --- a/src/main/java/cpw/mods/fml/common/Loader.java +++ b/src/main/java/cpw/mods/fml/common/Loader.java @@ -53,6 +53,8 @@ import cpw.mods.fml.common.ModContainer.Disableable; import cpw.mods.fml.common.discovery.ModDiscoverer; import cpw.mods.fml.common.event.FMLInterModComms; import cpw.mods.fml.common.event.FMLLoadEvent; +import cpw.mods.fml.common.event.FMLMissingMappingsEvent; +import cpw.mods.fml.common.event.FMLMissingMappingsEvent.MissingMapping; import cpw.mods.fml.common.event.FMLModIdMappingEvent; import cpw.mods.fml.common.functions.ArtifactVersionNameFunction; import cpw.mods.fml.common.functions.ModIdFunction; @@ -840,6 +842,28 @@ public class Loader return true; } + public void fireMissingMappingEvent(ArrayListMultimap missing) + { + if (!missing.isEmpty()) + { + FMLLog.fine("There are %d mappings missing - attempting a mod remap", missing.size()); + ArrayListMultimap missingMappings = ArrayListMultimap.create(); + List remaps = Lists.newArrayList(); + for (Map.Entry mapping : missing.entries()) + { + MissingMapping m = new MissingMapping(mapping.getValue(), remaps); + missingMappings.put(mapping.getKey(), m); + } + FMLMissingMappingsEvent missingEvent = new FMLMissingMappingsEvent(missingMappings); + modController.propogateStateMessage(missingEvent); + if (!missingMappings.isEmpty()) + { + FMLLog.severe("There are unidentified mappings in this world - it cannot be loaded"); + throw new RuntimeException("Mod IDs are missing"); + } + GameData.processIdRematches(remaps); + } + } public void fireRemapEvent(Map remaps) { if (remaps.isEmpty()) diff --git a/src/main/java/cpw/mods/fml/common/event/FMLMissingMappingsEvent.java b/src/main/java/cpw/mods/fml/common/event/FMLMissingMappingsEvent.java new file mode 100644 index 0000000000..5634c5f3d0 --- /dev/null +++ b/src/main/java/cpw/mods/fml/common/event/FMLMissingMappingsEvent.java @@ -0,0 +1,70 @@ +package cpw.mods.fml.common.event; + +import java.util.List; + +import com.google.common.collect.ImmutableList; +import com.google.common.collect.ListMultimap; + +import cpw.mods.fml.common.ModContainer; + +/** + * This event is fired if a world is loaded that has block and item mappings referring the mod that are not + * in existence. + * These can be remapped to other existing objects, or simply discarded. + * + * @author cpw + * + */ +public class FMLMissingMappingsEvent extends FMLEvent { + public static enum Type { BLOCK, ITEM } + public static class MissingMapping { + public final Type type; + public final String name; + private String remapTarget; + private List remaps; + public MissingMapping(String name, List remaps) + { + this.type = name.charAt(0) == '\u0001' ? Type.BLOCK : Type.ITEM; + this.name = name; + this.remaps = remaps; + } + public void remapTo(String target) + { + this.remapTarget = target; + remaps.add(this); + } + + public String getRemapTarget() + { + return this.remapTarget; + } + } + private ListMultimap missing; + private ModContainer activeContainer; + private List currentList; + + public FMLMissingMappingsEvent(ListMultimap missingMappings) + { + this.missing = missingMappings; + } + @Override + public void applyModContainer(ModContainer activeContainer) + { + super.applyModContainer(activeContainer); + this.activeContainer = activeContainer; + this.currentList = null; + } + + /** + * Get the list of missing mappings for the active mod. + * @return + */ + public List get() + { + if (currentList == null) + { + currentList = ImmutableList.copyOf(missing.removeAll(activeContainer.getModId())); + } + return currentList; + } +} diff --git a/src/main/java/cpw/mods/fml/common/registry/GameData.java b/src/main/java/cpw/mods/fml/common/registry/GameData.java index 8d785602d9..a3d5ef90e8 100644 --- a/src/main/java/cpw/mods/fml/common/registry/GameData.java +++ b/src/main/java/cpw/mods/fml/common/registry/GameData.java @@ -14,6 +14,7 @@ package cpw.mods.fml.common.registry; import java.io.File; import java.io.IOException; +import java.util.List; import java.util.Map; import java.util.Map.Entry; import org.apache.logging.log4j.Level; @@ -35,6 +36,7 @@ import com.google.common.io.Files; import cpw.mods.fml.common.FMLLog; import cpw.mods.fml.common.Loader; import cpw.mods.fml.common.ModContainer; +import cpw.mods.fml.common.event.FMLMissingMappingsEvent.MissingMapping; import cpw.mods.fml.common.registry.GameRegistry.UniqueIdentifier; public class GameData { @@ -212,6 +214,7 @@ public class GameData { public static void injectWorldIDMap(Map dataList) { Map remaps = Maps.newHashMap(); + Map missing = Maps.newHashMap(); blockRegistry.beginIdSwap(); itemRegistry.beginIdSwap(); for (Entry entry : dataList.entrySet()) @@ -231,7 +234,12 @@ public class GameData { currId = itemRegistry.getId(itemName); } - if (currId != newId) + if (currId == -1) + { + FMLLog.info("Found a missing id from the world %s", itemName); + missing.put(itemName.substring(0, itemName.indexOf(':')), itemName); + } + else if (currId != newId) { FMLLog.info("Found %s id mismatch %s : %d %d", isBlock ? "block" : "item", itemName, currId, newId); remaps.put(itemName, new Integer[] { currId, newId }); @@ -251,4 +259,12 @@ public class GameData { itemRegistry.completeIdSwap(); Loader.instance().fireRemapEvent(remaps); } + public static void processIdRematches(List remaps) + { + for (MissingMapping remap : remaps) + { + // what to do here + remap.getRemapTarget(); + } + } } diff --git a/src/main/java/cpw/mods/fml/common/registry/GameRegistry.java b/src/main/java/cpw/mods/fml/common/registry/GameRegistry.java index f18ca22e29..b2dd603b46 100644 --- a/src/main/java/cpw/mods/fml/common/registry/GameRegistry.java +++ b/src/main/java/cpw/mods/fml/common/registry/GameRegistry.java @@ -383,4 +383,5 @@ public class GameRegistry { return GameData.getUniqueName(item); } + }