From 6049d0e9c336cd712914c50c1922b1e3db71f383 Mon Sep 17 00:00:00 2001 From: slprime <31038811+slprime@users.noreply.github.com> Date: Thu, 5 Dec 2024 21:25:17 +0200 Subject: [PATCH] Fix restoring collapsible items state (#564) Co-authored-by: slprime --- .../codechicken/nei/CollapsibleItems.java | 129 +++++++++--------- src/main/java/codechicken/nei/ItemList.java | 7 +- src/main/java/codechicken/nei/ItemPanel.java | 18 +-- .../java/codechicken/nei/NEIClientConfig.java | 92 +++++++------ .../java/codechicken/nei/PresetsList.java | 3 +- .../java/codechicken/nei/api/ItemInfo.java | 1 - .../nei/config/preset/RightPanel.java | 4 +- .../assets/nei/cfg/collapsibleitems.cfg | 8 +- 8 files changed, 136 insertions(+), 126 deletions(-) diff --git a/src/main/java/codechicken/nei/CollapsibleItems.java b/src/main/java/codechicken/nei/CollapsibleItems.java index ad1a5a9ab..cbbe9d943 100644 --- a/src/main/java/codechicken/nei/CollapsibleItems.java +++ b/src/main/java/codechicken/nei/CollapsibleItems.java @@ -52,40 +52,15 @@ public boolean matches(ItemStack stack) { private static final String STATE_KEY = "collapsibleitems"; - protected File statesFile; - protected final List groups = new ArrayList<>(); - protected final Map cache = new ConcurrentHashMap<>(); + protected static File statesFile; + protected static final List groups = new ArrayList<>(); + protected static final Map cache = new ConcurrentHashMap<>(); - public void load() { - try { + private CollapsibleItems() {} - if (NEIClientConfig.world.nbt.hasKey(STATE_KEY)) { - NBTTagCompound states = NEIClientConfig.world.nbt.getCompoundTag(STATE_KEY); - @SuppressWarnings("unchecked") - final Map list = (Map) states.tagMap; - final Map mapping = new HashMap<>(); - - for (GroupItem group : this.groups) { - mapping.put(group.guid, group); - } - - for (Map.Entry nbtEntry : list.entrySet()) { - if (mapping.containsKey(nbtEntry.getKey())) { - mapping.get(nbtEntry.getKey()).expanded = nbtEntry.getValue().func_150290_f() == 1; - } - } - } - - } catch (Exception e) { - NEIClientConfig.logger.error("Error loading collapsible items states", e); - } - - reloadGroups(); - } - - public void reloadGroups() { - this.groups.clear(); - this.cache.clear(); + public static void load() { + CollapsibleItems.groups.clear(); + CollapsibleItems.cache.clear(); for (int i = PresetsList.presets.size() - 1; i >= 0; i--) { Preset preset = PresetsList.presets.get(i); @@ -102,9 +77,11 @@ public void reloadGroups() { "collapsibleitems.cfg", lines -> parseFile(lines.collect(Collectors.toCollection(ArrayList::new)))); } + + loadStates(); } - private void parseFile(List itemStrings) { + private static void parseFile(List itemStrings) { final JsonParser parser = new JsonParser(); GroupItem group = new GroupItem(); @@ -146,38 +123,39 @@ private void parseFile(List itemStrings) { } } - protected void addGroup(GroupItem group) { + private static void addGroup(GroupItem group) { if (group == null || group.filter == null || group.filter instanceof EverythingItemFilter || group.filter instanceof NothingItemFilter) return; - this.groups.add(group); + CollapsibleItems.groups.add(group); } - public boolean isEmpty() { - return this.groups.isEmpty(); + public static boolean isEmpty() { + return CollapsibleItems.groups.isEmpty(); } - public ItemFilter getItemFilter() { + public static ItemFilter getItemFilter() { AnyMultiItemFilter filter = new AnyMultiItemFilter(); - for (GroupItem group : this.groups) { + for (GroupItem group : CollapsibleItems.groups) { filter.filters.add(group.filter); } return filter; } - public void updateCache(final List items) { - this.cache.clear(); + public static void updateCache(final List items) { + CollapsibleItems.cache.clear(); try { ItemList.forkJoinPool.submit(() -> items.parallelStream().forEach(stack -> { - GroupItem group = this.groups.stream().filter(g -> g.matches(stack)).findFirst().orElse(null); + GroupItem group = CollapsibleItems.groups.stream().filter(g -> g.matches(stack)).findFirst() + .orElse(null); if (group != null) { - this.cache.put(stack, this.groups.indexOf(group)); + CollapsibleItems.cache.put(stack, CollapsibleItems.groups.indexOf(group)); } })).get(); @@ -187,62 +165,89 @@ public void updateCache(final List items) { } - public int getGroupIndex(ItemStack stack) { + public static int getGroupIndex(ItemStack stack) { if (stack == null) { return -1; } - return this.cache.getOrDefault(stack, -1); + return CollapsibleItems.cache.getOrDefault(stack, -1); } - public String getDisplayName(int groupIndex) { + public static String getDisplayName(int groupIndex) { - if (groupIndex < this.groups.size()) { - return this.groups.get(groupIndex).displayName; + if (groupIndex < CollapsibleItems.groups.size()) { + return CollapsibleItems.groups.get(groupIndex).displayName; } return null; } - public boolean isExpanded(int groupIndex) { + public static boolean isExpanded(int groupIndex) { - if (groupIndex < this.groups.size()) { - return this.groups.get(groupIndex).expanded; + if (groupIndex < CollapsibleItems.groups.size()) { + return CollapsibleItems.groups.get(groupIndex).expanded; } return true; } - public void setExpanded(int groupIndex, boolean expanded) { + public static void setExpanded(int groupIndex, boolean expanded) { - if (groupIndex < this.groups.size()) { - this.groups.get(groupIndex).expanded = expanded; - saveStates(); + if (groupIndex < CollapsibleItems.groups.size()) { + CollapsibleItems.groups.get(groupIndex).expanded = expanded; } } - public void toggleGroups(Boolean expanded) { + public static void toggleGroups(Boolean expanded) { if (expanded == null) { - expanded = this.groups.stream().noneMatch(g -> g.expanded); + expanded = CollapsibleItems.groups.stream().noneMatch(g -> g.expanded); } - for (GroupItem group : this.groups) { + for (GroupItem group : CollapsibleItems.groups) { group.expanded = expanded; } - saveStates(); } - private void saveStates() { + public static void saveStates() { NBTTagCompound list = new NBTTagCompound(); - for (GroupItem group : this.groups) { + for (GroupItem group : CollapsibleItems.groups) { list.setBoolean(group.guid, group.expanded); } - NEIClientConfig.world.nbt.setTag(STATE_KEY, list); + if (NEIClientConfig.world != null) { + NEIClientConfig.world.nbt.setTag(STATE_KEY, list); + } + } + + private static void loadStates() { + + try { + + if (NEIClientConfig.world.nbt.hasKey(STATE_KEY)) { + NBTTagCompound states = NEIClientConfig.world.nbt.getCompoundTag(STATE_KEY); + @SuppressWarnings("unchecked") + final Map list = (Map) states.tagMap; + final Map mapping = new HashMap<>(); + + for (GroupItem group : CollapsibleItems.groups) { + mapping.put(group.guid, group); + } + + for (Map.Entry nbtEntry : list.entrySet()) { + if (mapping.containsKey(nbtEntry.getKey())) { + mapping.get(nbtEntry.getKey()).expanded = nbtEntry.getValue().func_150290_f() == 1; + } + } + } + + } catch (Exception e) { + NEIClientConfig.logger.error("Error loading collapsible items states", e); + } + } } diff --git a/src/main/java/codechicken/nei/ItemList.java b/src/main/java/codechicken/nei/ItemList.java index 1dee2d44b..4044ba658 100644 --- a/src/main/java/codechicken/nei/ItemList.java +++ b/src/main/java/codechicken/nei/ItemList.java @@ -41,7 +41,6 @@ public class ItemList { */ public static final List itemFilterers = new LinkedList<>(); public static final List loadCallbacks = new LinkedList<>(); - public static final CollapsibleItems collapsibleItems = new CollapsibleItems(); private static final HashSet erroredItems = new HashSet<>(); private static final HashSet stackTraces = new HashSet<>(); @@ -239,12 +238,12 @@ private void updateOrdering(List items) { ItemSorter.sort(items); - if (!ItemList.collapsibleItems.isEmpty()) { + if (!CollapsibleItems.isEmpty()) { HashMap groups = new HashMap<>(); int orderIndex = 0; for (ItemStack stack : items) { - final int groupIndex = ItemList.collapsibleItems.getGroupIndex(stack); + final int groupIndex = CollapsibleItems.getGroupIndex(stack); if (groupIndex == -1) { ItemList.ordering.put(stack, orderIndex++); @@ -318,7 +317,7 @@ public void execute() { for (ItemsLoadedCallback callback : loadCallbacks) callback.itemsLoaded(); if (interrupted()) return; - ItemList.collapsibleItems.updateCache(items); + CollapsibleItems.updateCache(items); updateOrdering(items); loadFinished = true; diff --git a/src/main/java/codechicken/nei/ItemPanel.java b/src/main/java/codechicken/nei/ItemPanel.java index 31f110409..aa0a065ac 100644 --- a/src/main/java/codechicken/nei/ItemPanel.java +++ b/src/main/java/codechicken/nei/ItemPanel.java @@ -98,7 +98,7 @@ public void refresh(GuiContainer gui) { this.groupItems.clear(); this.forceExpand = false; - if (!ItemList.collapsibleItems.isEmpty() && !this.newItems.isEmpty()) { + if (!CollapsibleItems.isEmpty() && !this.newItems.isEmpty()) { final Set groups = new HashSet<>(); boolean outsideGroup = false; @@ -106,14 +106,14 @@ public void refresh(GuiContainer gui) { this.rawItems = new ArrayList<>(this.newItems); for (ItemStack stack : this.newItems) { - final int groupIndex = ItemList.collapsibleItems.getGroupIndex(stack); + final int groupIndex = CollapsibleItems.getGroupIndex(stack); if (groupIndex == -1) { this.realItems.add(stack); outsideGroup = true; } else { - if (!groups.contains(groupIndex) || ItemList.collapsibleItems.isExpanded(groupIndex)) { + if (!groups.contains(groupIndex) || CollapsibleItems.isExpanded(groupIndex)) { this.realItems.add(stack); groups.add(groupIndex); } @@ -175,7 +175,7 @@ protected void calculateGroupBorders(List mask) { } int idx = mask.get(slotIndex); - maskGroup.put(idx, ItemList.collapsibleItems.getGroupIndex(getItem(idx))); + maskGroup.put(idx, CollapsibleItems.getGroupIndex(getItem(idx))); } for (int slotIndex = 0; slotIndex < mask.size(); slotIndex++) { @@ -197,8 +197,8 @@ protected void calculateGroupBorders(List mask) { MaskMetadata metadata = new MaskMetadata(); metadata.groupIndex = groupIndex; - metadata.displayName = ItemList.collapsibleItems.getDisplayName(groupIndex); - metadata.extended = this.forceExpand || ItemList.collapsibleItems.isExpanded(groupIndex); + metadata.displayName = CollapsibleItems.getDisplayName(groupIndex); + metadata.extended = this.forceExpand || CollapsibleItems.isExpanded(groupIndex); metadata.bgColor = metadata.extended ? expandedColor : collapsedColor; metadata.color = darkerColor(metadata.bgColor); metadata.left = column == 0 || idx == 0 @@ -339,7 +339,7 @@ public String getButtonTip() { @Override public boolean onButtonPress(boolean rightclick) { - ItemList.collapsibleItems.toggleGroups(rightclick ? false : null); + CollapsibleItems.toggleGroups(rightclick ? false : null); ItemList.updateFilter.restart(); return true; } @@ -482,7 +482,7 @@ public void setVisible() { LayoutManager.addWidget(quantity); } - if (!ItemList.collapsibleItems.isEmpty()) { + if (!CollapsibleItems.isEmpty()) { LayoutManager.addWidget(toggleGroups); } @@ -560,7 +560,7 @@ public boolean handleClick(int mousex, int mousey, int button) { final MaskMetadata metadata = panelGrid.maskMetadata.get(hoverSlot.slotIndex); if (metadata != null) { - ItemList.collapsibleItems.setExpanded(metadata.groupIndex, !metadata.extended); + CollapsibleItems.setExpanded(metadata.groupIndex, !metadata.extended); panelGrid.setItems(panelGrid.rawItems); return true; } diff --git a/src/main/java/codechicken/nei/NEIClientConfig.java b/src/main/java/codechicken/nei/NEIClientConfig.java index 4b9ffd999..2e414fc63 100644 --- a/src/main/java/codechicken/nei/NEIClientConfig.java +++ b/src/main/java/codechicken/nei/NEIClientConfig.java @@ -255,7 +255,8 @@ public boolean onClick(int button) { @Override public boolean onClick(int button) { super.onClick(button); - ItemList.collapsibleItems.reloadGroups(); + CollapsibleItems.saveStates(); + CollapsibleItems.load(); LayoutManager.markItemsDirty(); return true; } @@ -650,6 +651,7 @@ public static void loadWorld(String worldPath) { world = new ConfigSet(new File(specificDir, "NEI.dat"), new ConfigFile(new File(specificDir, "NEI.cfg"))); bootNEI(ClientUtils.getWorld()); + CollapsibleItems.load(); ItemPanels.bookmarkPanel.load(); onWorldLoad(newWorld); } @@ -688,6 +690,8 @@ public static void unloadWorld() { ItemPanels.bookmarkPanel.saveBookmarks(); } + CollapsibleItems.saveStates(); + if (world != null) { world.saveNBT(); } @@ -720,48 +724,50 @@ public static String getKeyName(String keyBind) { } public static void bootNEI(World world) { - if (mainNEIConfigLoaded) return; - - // main NEI config loading - ItemInfo.load(world); - GuiInfo.load(); - RecipeInfo.load(); - HeldItemHandler.load(); - LayoutManager.load(); - NEIController.load(); - BookmarkContainerInfo.load(); - mainNEIConfigLoaded = true; - - new Thread("NEI Plugin Loader") { - - @Override - public void run() { - - NEIClientConfig.pluginsList.parallelStream().forEach(clazz -> { - try { - IConfigureNEI config = (IConfigureNEI) clazz.getConstructor().newInstance(); - config.loadConfig(); - NEIModContainer.plugins.add(config); - logger.debug("Loaded {}", clazz.getName()); - } catch (Throwable e) { - logger.error("Failed to Load {}", clazz.getName(), e); - } - }); - - RecipeCatalysts.loadCatalystInfo(); - ItemSorter.loadConfig(); - - // Set pluginNEIConfigLoaded here before posting the NEIConfigsLoadedEvent. This used to be the other - // way around, but apparently if your modpack includes 800 mods the event poster might not return in - // time and cause issues when loading a world for a second time as configLoaded is still false. This may - // cause issues in case one of the event handler calls the (non-thread-safe) NEI API. I don't expect any - // handler to do this, but who knows what modders have come up with... - pluginNEIConfigLoaded = true; - MinecraftForge.EVENT_BUS.post(new NEIConfigsLoadedEvent()); - - ItemList.loadItems.restart(); - } - }.start(); + if (!mainNEIConfigLoaded) { + // main NEI config loading + ItemInfo.load(world); + GuiInfo.load(); + RecipeInfo.load(); + HeldItemHandler.load(); + LayoutManager.load(); + NEIController.load(); + BookmarkContainerInfo.load(); + mainNEIConfigLoaded = true; + + new Thread("NEI Plugin Loader") { + + @Override + public void run() { + + NEIClientConfig.pluginsList.parallelStream().forEach(clazz -> { + try { + IConfigureNEI config = (IConfigureNEI) clazz.getConstructor().newInstance(); + config.loadConfig(); + NEIModContainer.plugins.add(config); + logger.debug("Loaded {}", clazz.getName()); + } catch (Throwable e) { + logger.error("Failed to Load {}", clazz.getName(), e); + } + }); + + RecipeCatalysts.loadCatalystInfo(); + ItemSorter.loadConfig(); + + // Set pluginNEIConfigLoaded here before posting the NEIConfigsLoadedEvent. This used to be the + // other way around, but apparently if your modpack includes 800 mods the event poster might not + // return in time and cause issues when loading a world for a second time as configLoaded is still + // false. This may cause issues in case one of the event handler calls the (non-thread-safe) NEI + // API. I don't expect any handler to do this, but who knows what modders have come up with... + pluginNEIConfigLoaded = true; + MinecraftForge.EVENT_BUS.post(new NEIConfigsLoadedEvent()); + + ItemList.loadItems.restart(); + } + }.start(); + } else { + ItemList.loadItems.restart(); + } } public static boolean isWorldSpecific(String setting) { diff --git a/src/main/java/codechicken/nei/PresetsList.java b/src/main/java/codechicken/nei/PresetsList.java index 50528a2c5..ae504a73f 100644 --- a/src/main/java/codechicken/nei/PresetsList.java +++ b/src/main/java/codechicken/nei/PresetsList.java @@ -241,7 +241,8 @@ public static void savePresets() { recipeFilter.cache = null; itemFilter.cache = null; - ItemList.collapsibleItems.reloadGroups(); + CollapsibleItems.saveStates(); + CollapsibleItems.load(); LayoutManager.markItemsDirty(); } diff --git a/src/main/java/codechicken/nei/api/ItemInfo.java b/src/main/java/codechicken/nei/api/ItemInfo.java index 256a2625d..1ccdccd5e 100644 --- a/src/main/java/codechicken/nei/api/ItemInfo.java +++ b/src/main/java/codechicken/nei/api/ItemInfo.java @@ -136,7 +136,6 @@ public static void load(World world) { addIDDumps(); addSearchProviders(); PresetsList.load(); - ItemList.collapsibleItems.load(); ItemList.loadCallbacks.add(TooltipFilter::populateSearchMap); } diff --git a/src/main/java/codechicken/nei/config/preset/RightPanel.java b/src/main/java/codechicken/nei/config/preset/RightPanel.java index 6793fd8b8..1cc01db43 100644 --- a/src/main/java/codechicken/nei/config/preset/RightPanel.java +++ b/src/main/java/codechicken/nei/config/preset/RightPanel.java @@ -15,7 +15,7 @@ import codechicken.core.gui.GuiWidget; import codechicken.lib.gui.GuiDraw; import codechicken.lib.vec.Rectangle4i; -import codechicken.nei.ItemList; +import codechicken.nei.CollapsibleItems; import codechicken.nei.ItemList.AllMultiItemFilter; import codechicken.nei.ItemList.AnyMultiItemFilter; import codechicken.nei.ItemList.NegatedItemFilter; @@ -142,7 +142,7 @@ protected ItemFilter getFilter() { .collect(Collectors.toSet()); andFilter.filters.add(item -> !identifiers.contains(Preset.getIdentifier(item))); - andFilter.filters.add(new NegatedItemFilter(ItemList.collapsibleItems.getItemFilter())); + andFilter.filters.add(new NegatedItemFilter(CollapsibleItems.getItemFilter())); if (slotIndex != -1) { orFilter.filters.add(PresetsList.presets.get(slotIndex)); diff --git a/src/main/resources/assets/nei/cfg/collapsibleitems.cfg b/src/main/resources/assets/nei/cfg/collapsibleitems.cfg index ac7b4de2e..7a3e0b047 100644 --- a/src/main/resources/assets/nei/cfg/collapsibleitems.cfg +++ b/src/main/resources/assets/nei/cfg/collapsibleitems.cfg @@ -21,7 +21,7 @@ minecraft:spawn_egg minecraft:mob_spawner minecraft:record_ -#splash -minecraft:potion >16000 -#lingering -minecraft:potion >8000 <9000 \ No newline at end of file +#splash potion +minecraft:potion 16000-17000 +#lingering potion +minecraft:potion 8000-9000 \ No newline at end of file