Merge pull request #64 from sdburns1998/InventorySetup

Inventory setup plugin
This commit is contained in:
James
2019-04-22 19:08:19 -07:00
committed by GitHub
13 changed files with 1189 additions and 0 deletions

View File

@@ -0,0 +1,14 @@
package net.runelite.client.plugins.inventorysetups;
import java.util.ArrayList;
import lombok.AllArgsConstructor;
import lombok.Getter;
@AllArgsConstructor
public class InventorySetup
{
@Getter
private ArrayList<InventorySetupItem> inventory;
@Getter
private ArrayList<InventorySetupItem> equipment;
}

View File

@@ -0,0 +1,76 @@
package net.runelite.client.plugins.inventorysetups;
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.image.BufferedImage;
import java.util.stream.IntStream;
import javax.inject.Inject;
import lombok.extern.slf4j.Slf4j;
import net.runelite.api.widgets.WidgetItem;
import net.runelite.client.game.ItemManager;
import net.runelite.client.ui.FontManager;
import net.runelite.client.ui.overlay.WidgetItemOverlay;
@Slf4j
public class InventorySetupBankOverlay extends WidgetItemOverlay
{
private final ItemManager itemManager;
private final InventorySetupPlugin plugin;
private final InventorySetupConfig config;
@Inject
public InventorySetupBankOverlay(ItemManager itemManager, InventorySetupPlugin plugin, InventorySetupConfig config)
{
this.itemManager = itemManager;
this.plugin = plugin;
this.config = config;
showOnBank();
}
@Override
public void renderItemOverlay(Graphics2D graphics, int itemId, WidgetItem itemWidget)
{
if (config.getBankHighlight())
{
int[] ids = plugin.getCurrentInventorySetupIds();
if (ids == null)
{
return;
}
if (IntStream.of(ids).noneMatch(x -> x == itemId))
{
return;
}
final Color color = config.getBankHighlightColor();
if (color != null)
{
Rectangle bounds = itemWidget.getCanvasBounds();
final BufferedImage outline = itemManager.getItemOutline(itemId, itemWidget.getQuantity(), color);
graphics.drawImage(outline, (int) bounds.getX() + 1, (int) bounds.getY() + 1, null);
if (itemWidget.getQuantity() > 1)
{
drawQuantity(graphics, itemWidget, Color.YELLOW);
}
else if (itemWidget.getQuantity() == 0)
{
drawQuantity(graphics, itemWidget, Color.YELLOW.darker());
}
}
}
}
private void drawQuantity(Graphics2D graphics, WidgetItem item, Color darker)
{
graphics.setColor(Color.BLACK);
graphics.drawString(String.valueOf(item.getQuantity()), item.getCanvasLocation().getX() + 2, item.getCanvasLocation().getY() + 11);
graphics.setColor(darker);
graphics.setFont(FontManager.getRunescapeSmallFont());
graphics.drawString(String.valueOf(item.getQuantity()), item.getCanvasLocation().getX() + 1, item.getCanvasLocation().getY() + 10);
}
}

View File

@@ -0,0 +1,82 @@
package net.runelite.client.plugins.inventorysetups;
import java.awt.Color;
import net.runelite.client.config.Config;
import net.runelite.client.config.ConfigGroup;
import net.runelite.client.config.ConfigItem;
@ConfigGroup("inventorysetups")
public interface InventorySetupConfig extends Config
{
@ConfigItem(
keyName = "highlightDifferences",
name = "Highlight Differences",
description = "Highlight slots that don't match the selected setup",
position = 0
)
default boolean getHighlightDifferences()
{
return false;
}
@ConfigItem(
keyName = "highlightDifferenceColor",
name = "Highlight Color",
description = "The color used to highlight differences between setups",
position = 1
)
default Color getHighlightColor()
{
return Color.RED;
}
@ConfigItem(
keyName = "stackDifference",
name = "Stack Difference",
description = "Differences between setups will be highlighted if the stack size is different",
position = 2
)
default boolean getStackDifference()
{
return false;
}
@ConfigItem(
keyName = "variationDifference",
name = "Variation Difference",
description = "Variations of items (E.g., charged jewellery) will be counted as different",
position = 2
)
default boolean getVariationDifference()
{
return false;
}
@ConfigItem(
keyName = "bankHighlight",
name = "Bank Highlight",
description = "Highlight setup items in bank",
position = 4
)
default boolean getBankHighlight()
{
return false;
}
@ConfigItem(
keyName = "bankHighlightColor",
name = "Bank Highlight Color",
description = "The color used to highlight setup items in bank",
position = 5
)
default Color getBankHighlightColor()
{
return Color.RED;
}
}

View File

@@ -0,0 +1,15 @@
package net.runelite.client.plugins.inventorysetups;
import lombok.AllArgsConstructor;
import lombok.Getter;
@AllArgsConstructor
public class InventorySetupItem
{
@Getter
private final int id;
@Getter
private final String name;
@Getter
private final int quantity;
}

View File

@@ -0,0 +1,407 @@
package net.runelite.client.plugins.inventorysetups;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.google.inject.Provides;
import java.awt.image.BufferedImage;
import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Objects;
import javax.inject.Inject;
import javax.swing.JOptionPane;
import javax.swing.SwingUtilities;
import lombok.extern.slf4j.Slf4j;
import net.runelite.api.Client;
import net.runelite.api.GameState;
import net.runelite.api.InventoryID;
import net.runelite.api.Item;
import net.runelite.api.ItemComposition;
import net.runelite.api.ItemContainer;
import net.runelite.api.events.ConfigChanged;
import net.runelite.api.events.GameStateChanged;
import net.runelite.api.events.ItemContainerChanged;
import net.runelite.client.callback.ClientThread;
import net.runelite.client.config.ConfigManager;
import net.runelite.client.eventbus.Subscribe;
import net.runelite.client.game.ItemManager;
import net.runelite.client.game.ItemVariationMapping;
import net.runelite.client.plugins.Plugin;
import net.runelite.client.plugins.PluginDescriptor;
import net.runelite.client.plugins.PluginType;
import net.runelite.client.plugins.inventorysetups.ui.InventorySetupPluginPanel;
import net.runelite.client.ui.ClientToolbar;
import net.runelite.client.ui.NavigationButton;
import net.runelite.client.ui.overlay.OverlayManager;
import net.runelite.client.util.ImageUtil;
@PluginDescriptor(
name = "Inventory Setups",
description = "Save inventory setups",
tags = {"items", "inventory", "setups"},
enabledByDefault = false,
type = PluginType.UTILITY
)
@Slf4j
public class InventorySetupPlugin extends Plugin
{
private static final String CONFIG_GROUP = "inventorysetups";
private static final String CONFIG_KEY = "setups";
private static final int NUM_INVENTORY_ITEMS = 28;
private static final int NUM_EQUIPMENT_ITEMS = 14;
@Inject
private Client client;
@Inject
private ItemManager itemManager;
@Inject
private InventorySetupBankOverlay overlay;
@Inject
private ClientToolbar clientToolbar;
@Inject
private InventorySetupConfig config;
@Inject
private OverlayManager overlayManager;
@Inject
private ClientThread clientThread;
@Inject
private ConfigManager configManager;
private InventorySetupPluginPanel panel;
private HashMap<String, InventorySetup> inventorySetups;
private NavigationButton navButton;
private boolean highlightDifference;
@Override
public void startUp()
{
overlayManager.add(overlay);
panel = new InventorySetupPluginPanel(this, itemManager);
final BufferedImage icon = ImageUtil.getResourceStreamFromClass(getClass(), "inventorysetups_icon.png");
navButton = NavigationButton.builder()
.tooltip("Inventory Setups")
.icon(icon)
.priority(9)
.panel(panel)
.build();
clientToolbar.addNavigation(navButton);
// load all the inventory setups from the config file
clientThread.invokeLater(() ->
{
if (client.getGameState() != GameState.LOGIN_SCREEN)
{
return false;
}
loadConfig();
panel.showNoSetupsPanel();
return true;
});
}
public void addInventorySetup()
{
final String name = JOptionPane.showInputDialog(panel,
"Enter the name of this setup.",
"Add New Setup",
JOptionPane.PLAIN_MESSAGE);
// cancel button was clicked
if (name == null)
{
return;
}
if (name.isEmpty())
{
JOptionPane.showMessageDialog(panel,
"Invalid Setup Name",
"Names must not be empty.",
JOptionPane.PLAIN_MESSAGE);
return;
}
if (inventorySetups.containsKey(name))
{
String builder = "The setup " + name + " already exists. " +
"Would you like to replace it with the current setup?";
int confirm = JOptionPane.showConfirmDialog(panel,
builder,
"Warning",
JOptionPane.OK_CANCEL_OPTION,
JOptionPane.PLAIN_MESSAGE);
if (confirm == JOptionPane.CANCEL_OPTION)
{
return;
}
// delete the old setup, no need to ask for confirmation
// because the user confirmed above
removeInventorySetup(name, false);
}
clientThread.invoke(() ->
{
ArrayList<InventorySetupItem> inv = getNormalizedContainer(InventoryID.INVENTORY);
ArrayList<InventorySetupItem> eqp = getNormalizedContainer(InventoryID.EQUIPMENT);
final InventorySetup invSetup = new InventorySetup(inv, eqp);
SwingUtilities.invokeLater(() ->
{
inventorySetups.put(name, invSetup);
panel.addInventorySetup(name);
panel.setCurrentInventorySetup(name);
updateConfig();
});
});
}
public void removeInventorySetup(final String name, boolean askForConfirmation)
{
if (inventorySetups.containsKey(name))
{
int confirm = JOptionPane.YES_OPTION;
if (askForConfirmation)
{
confirm = JOptionPane.showConfirmDialog(panel,
"Are you sure you want to remove this setup?",
"Warning",
JOptionPane.YES_NO_OPTION,
JOptionPane.PLAIN_MESSAGE);
}
if (confirm == JOptionPane.YES_OPTION)
{
inventorySetups.remove(name);
panel.removeInventorySetup(name);
}
updateConfig();
}
}
public final InventorySetup getInventorySetup(final String name)
{
return inventorySetups.get(name);
}
@Provides
InventorySetupConfig provideConfig(ConfigManager configManager)
{
return configManager.getConfig(InventorySetupConfig.class);
}
@Subscribe
public void onConfigChanged(ConfigChanged event)
{
if (event.getGroup().equals(CONFIG_GROUP))
{
// only allow highlighting if the config is enabled and the player is logged in
highlightDifference = config.getHighlightDifferences() && client.getGameState() == GameState.LOGGED_IN;
final String setupName = panel.getSelectedInventorySetup();
if (highlightDifference && !setupName.isEmpty())
{
panel.setCurrentInventorySetup(setupName);
}
}
}
private void updateConfig()
{
if (inventorySetups.isEmpty())
{
configManager.unsetConfiguration(CONFIG_GROUP, CONFIG_KEY);
return;
}
final Gson gson = new Gson();
final String json = gson.toJson(inventorySetups);
configManager.setConfiguration(CONFIG_GROUP, CONFIG_KEY, json);
}
private void loadConfig()
{
// serialize the internal data structure from the json in the configuration
final String json = configManager.getConfiguration(CONFIG_GROUP, CONFIG_KEY);
if (json == null || json.isEmpty())
{
inventorySetups = new HashMap<>();
}
else
{
// TODO add last resort?, serialize exception just make empty map
final Gson gson = new Gson();
Type type = new TypeToken<HashMap<String, InventorySetup>>()
{
}.getType();
inventorySetups = gson.fromJson(json, type);
}
for (final String key : inventorySetups.keySet())
{
panel.addInventorySetup(key);
}
highlightDifference = false;
}
@Subscribe
public void onItemContainerChanged(ItemContainerChanged event)
{
if (!highlightDifference || client.getGameState() != GameState.LOGGED_IN)
{
return;
}
// empty entry, no need to compare anything
final String selectedInventorySetup = panel.getSelectedInventorySetup();
if (selectedInventorySetup.isEmpty())
{
return;
}
// check to see that the container is the equipment or inventory
ItemContainer container = event.getItemContainer();
if (container == client.getItemContainer(InventoryID.INVENTORY))
{
ArrayList<InventorySetupItem> normContainer = getNormalizedContainer(InventoryID.INVENTORY);
final InventorySetup setup = inventorySetups.get(selectedInventorySetup);
panel.highlightDifferences(normContainer, setup, InventoryID.INVENTORY);
}
else if (container == client.getItemContainer(InventoryID.EQUIPMENT))
{
ArrayList<InventorySetupItem> normContainer = getNormalizedContainer(InventoryID.EQUIPMENT);
final InventorySetup setup = inventorySetups.get(selectedInventorySetup);
panel.highlightDifferences(normContainer, setup, InventoryID.EQUIPMENT);
}
}
@Subscribe
public void onGameStateChanged(GameStateChanged event)
{
switch (event.getGameState())
{
// set the highlighting off if login screen shows up
case LOGIN_SCREEN:
highlightDifference = false;
final String setupName = panel.getSelectedInventorySetup();
if (!setupName.isEmpty())
{
panel.setCurrentInventorySetup(setupName);
}
break;
// set highlighting
case LOGGED_IN:
highlightDifference = config.getHighlightDifferences();
break;
}
}
public ArrayList<InventorySetupItem> getNormalizedContainer(final InventoryID id)
{
assert id == InventoryID.INVENTORY || id == InventoryID.EQUIPMENT : "invalid inventory ID";
final ItemContainer container = client.getItemContainer(id);
ArrayList<InventorySetupItem> newContainer = new ArrayList<>();
Item[] items = null;
if (container != null)
{
items = container.getItems();
}
int size = id == InventoryID.INVENTORY ? NUM_INVENTORY_ITEMS : NUM_EQUIPMENT_ITEMS;
for (int i = 0; i < size; i++)
{
if (items == null || i >= items.length)
{
newContainer.add(new InventorySetupItem(-1, "", 0));
}
else
{
final Item item = items[i];
String itemName = "";
if (client.isClientThread())
{
itemName = itemManager.getItemComposition(item.getId()).getName();
}
newContainer.add(new InventorySetupItem(item.getId(), itemName, item.getQuantity()));
}
}
return newContainer;
}
public final InventorySetupConfig getConfig()
{
return config;
}
public boolean getHighlightDifference()
{
return highlightDifference;
}
@Override
public void shutDown()
{
overlayManager.remove(overlay);
clientToolbar.removeNavigation(navButton);
}
final int[] getCurrentInventorySetupIds()
{
InventorySetup setup = inventorySetups.get(panel.getSelectedInventorySetup());
if (setup == null)
{
return null;
}
ArrayList<InventorySetupItem> items = new ArrayList<>();
items.addAll(setup.getEquipment());
items.addAll(setup.getInventory());
ArrayList<Integer> itemIds = new ArrayList<>();
for (InventorySetupItem item : items)
{
int id = item.getId();
ItemComposition itemComposition = itemManager.getItemComposition(id);
if (id > 0)
{
itemIds.add(ItemVariationMapping.map(id));
itemIds.add(itemComposition.getPlaceholderId());
}
}
return itemIds.stream()
.mapToInt(i -> i)
.filter(Objects::nonNull)
.filter(id -> id != -1)
.toArray();
}
}

View File

@@ -0,0 +1,106 @@
package net.runelite.client.plugins.inventorysetups.ui;
import java.awt.BorderLayout;
import java.awt.Color;
import java.util.ArrayList;
import javax.swing.JLabel;
import javax.swing.JPanel;
import net.runelite.client.game.AsyncBufferedImage;
import net.runelite.client.game.ItemManager;
import net.runelite.client.game.ItemVariationMapping;
import net.runelite.client.plugins.inventorysetups.InventorySetupConfig;
import net.runelite.client.plugins.inventorysetups.InventorySetupItem;
import net.runelite.client.plugins.inventorysetups.InventorySetupPlugin;
import net.runelite.client.ui.ColorScheme;
public abstract class InventorySetupContainerPanel extends JPanel
{
protected ItemManager itemManager;
private final InventorySetupPlugin plugin;
InventorySetupContainerPanel(final ItemManager itemManager, final InventorySetupPlugin plugin, String captionText)
{
this.itemManager = itemManager;
this.plugin = plugin;
JPanel containerPanel = new JPanel();
final JPanel containerSlotsPanel = new JPanel();
setupContainerPanel(containerSlotsPanel);
// caption
final JLabel caption = new JLabel(captionText);
caption.setHorizontalAlignment(JLabel.CENTER);
caption.setVerticalAlignment(JLabel.CENTER);
// panel that holds the caption and any other graphics
final JPanel captionPanel = new JPanel();
captionPanel.add(caption);
containerPanel.setLayout(new BorderLayout());
containerPanel.add(captionPanel, BorderLayout.NORTH);
containerPanel.add(containerSlotsPanel, BorderLayout.CENTER);
add(containerPanel);
}
void setContainerSlot(int index,
final InventorySetupSlot containerSlot,
final ArrayList<InventorySetupItem> items)
{
if (index >= items.size() || items.get(index).getId() == -1)
{
containerSlot.setImageLabel(null, null);
return;
}
int itemId = items.get(index).getId();
int quantity = items.get(index).getQuantity();
final String itemName = items.get(index).getName();
AsyncBufferedImage itemImg = itemManager.getImage(itemId, quantity, quantity > 1);
String toolTip = itemName;
if (quantity > 1)
{
toolTip += " (" + quantity + ")";
}
containerSlot.setImageLabel(toolTip, itemImg);
}
void highlightDifferentSlotColor(InventorySetupItem savedItem,
InventorySetupItem currItem,
final InventorySetupSlot containerSlot)
{
// important note: do not use item names for comparisons
// they are all empty to avoid clientThread usage when highlighting
final InventorySetupConfig config = plugin.getConfig();
final Color highlightColor = config.getHighlightColor();
if (config.getStackDifference() && currItem.getQuantity() != savedItem.getQuantity())
{
containerSlot.setBackground(highlightColor);
return;
}
int currId = currItem.getId();
int checkId = savedItem.getId();
if (!config.getVariationDifference())
{
currId = ItemVariationMapping.map(currId);
checkId = ItemVariationMapping.map(checkId);
}
if (currId != checkId)
{
containerSlot.setBackground(highlightColor);
return;
}
// set the color back to the original, because they match
containerSlot.setBackground(ColorScheme.DARKER_GRAY_COLOR);
}
abstract public void setupContainerPanel(final JPanel containerSlotsPanel);
}

View File

@@ -0,0 +1,90 @@
package net.runelite.client.plugins.inventorysetups.ui;
import java.awt.GridLayout;
import java.util.ArrayList;
import java.util.HashMap;
import javax.swing.JPanel;
import net.runelite.api.EquipmentInventorySlot;
import net.runelite.client.game.ItemManager;
import net.runelite.client.plugins.inventorysetups.InventorySetup;
import net.runelite.client.plugins.inventorysetups.InventorySetupItem;
import net.runelite.client.plugins.inventorysetups.InventorySetupPlugin;
import net.runelite.client.ui.ColorScheme;
public class InventorySetupEquipmentPanel extends InventorySetupContainerPanel
{
private HashMap<EquipmentInventorySlot, InventorySetupSlot> equipmentSlots;
InventorySetupEquipmentPanel(final ItemManager itemManager, final InventorySetupPlugin plugin)
{
super(itemManager, plugin, "Equipment");
}
@Override
public void setupContainerPanel(final JPanel containerSlotsPanel)
{
this.equipmentSlots = new HashMap<>();
for (EquipmentInventorySlot slot : EquipmentInventorySlot.values())
{
equipmentSlots.put(slot, new InventorySetupSlot(ColorScheme.DARKER_GRAY_COLOR));
}
final GridLayout gridLayout = new GridLayout(5, 3, 1, 1);
containerSlotsPanel.setLayout(gridLayout);
// add the grid layouts, including invisible ones
containerSlotsPanel.add(new InventorySetupSlot(ColorScheme.DARK_GRAY_COLOR));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.HEAD));
containerSlotsPanel.add(new InventorySetupSlot(ColorScheme.DARK_GRAY_COLOR));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.CAPE));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.AMULET));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.AMMO));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.WEAPON));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.BODY));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.SHIELD));
containerSlotsPanel.add(new InventorySetupSlot(ColorScheme.DARK_GRAY_COLOR));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.LEGS));
containerSlotsPanel.add(new InventorySetupSlot(ColorScheme.DARK_GRAY_COLOR));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.GLOVES));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.BOOTS));
containerSlotsPanel.add(equipmentSlots.get(EquipmentInventorySlot.RING));
}
void setEquipmentSetupSlots(final InventorySetup setup)
{
final ArrayList<InventorySetupItem> equipment = setup.getEquipment();
for (final EquipmentInventorySlot slot : EquipmentInventorySlot.values())
{
int i = slot.getSlotIdx();
super.setContainerSlot(i, equipmentSlots.get(slot), equipment);
}
validate();
repaint();
}
void highlightDifferences(final ArrayList<InventorySetupItem> currEquipment, final InventorySetup inventorySetup)
{
final ArrayList<InventorySetupItem> equipToCheck = inventorySetup.getEquipment();
assert currEquipment.size() == equipToCheck.size() : "size mismatch";
for (final EquipmentInventorySlot slot : EquipmentInventorySlot.values())
{
int slotIdx = slot.getSlotIdx();
super.highlightDifferentSlotColor(equipToCheck.get(slotIdx), currEquipment.get(slotIdx), equipmentSlots.get(slot));
}
}
void resetEquipmentSlotsColor()
{
for (final EquipmentInventorySlot slot : EquipmentInventorySlot.values())
{
equipmentSlots.get(slot).setBackground(ColorScheme.DARKER_GRAY_COLOR);
}
}
}

View File

@@ -0,0 +1,76 @@
package net.runelite.client.plugins.inventorysetups.ui;
import java.awt.GridLayout;
import java.util.ArrayList;
import javax.swing.JPanel;
import net.runelite.client.game.ItemManager;
import net.runelite.client.plugins.inventorysetups.InventorySetup;
import net.runelite.client.plugins.inventorysetups.InventorySetupItem;
import net.runelite.client.plugins.inventorysetups.InventorySetupPlugin;
import net.runelite.client.ui.ColorScheme;
public class InventorySetupInventoryPanel extends InventorySetupContainerPanel
{
private static final int ITEMS_PER_ROW = 4;
private static final int NUM_INVENTORY_ITEMS = 28;
private ArrayList<InventorySetupSlot> inventorySlots;
InventorySetupInventoryPanel(final ItemManager itemManager, final InventorySetupPlugin plugin)
{
super(itemManager, plugin, "Inventory");
}
@Override
public void setupContainerPanel(final JPanel containerSlotsPanel)
{
this.inventorySlots = new ArrayList<>();
for (int i = 0; i < NUM_INVENTORY_ITEMS; i++)
{
inventorySlots.add(new InventorySetupSlot(ColorScheme.DARKER_GRAY_COLOR));
}
int numRows = (NUM_INVENTORY_ITEMS + ITEMS_PER_ROW - 1) / ITEMS_PER_ROW;
containerSlotsPanel.setLayout(new GridLayout(numRows, ITEMS_PER_ROW, 1, 1));
for (int i = 0; i < NUM_INVENTORY_ITEMS; i++)
{
containerSlotsPanel.add(inventorySlots.get(i));
}
}
void setInventorySetupSlots(final InventorySetup setup)
{
ArrayList<InventorySetupItem> inventory = setup.getInventory();
for (int i = 0; i < NUM_INVENTORY_ITEMS; i++)
{
super.setContainerSlot(i, inventorySlots.get(i), inventory);
}
validate();
repaint();
}
void highlightDifferentSlots(final ArrayList<InventorySetupItem> currInventory, final InventorySetup inventorySetup)
{
final ArrayList<InventorySetupItem> inventoryToCheck = inventorySetup.getInventory();
assert currInventory.size() == inventoryToCheck.size() : "size mismatch";
for (int i = 0; i < NUM_INVENTORY_ITEMS; i++)
{
super.highlightDifferentSlotColor(inventoryToCheck.get(i), currInventory.get(i), inventorySlots.get(i));
}
}
void resetInventorySlotsColor()
{
for (InventorySetupSlot inventorySlot : inventorySlots)
{
inventorySlot.setBackground(ColorScheme.DARKER_GRAY_COLOR);
}
}
}

View File

@@ -0,0 +1,283 @@
package net.runelite.client.plugins.inventorysetups.ui;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.event.ItemEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.image.BufferedImage;
import java.util.ArrayList;
import javax.swing.Box;
import javax.swing.BoxLayout;
import javax.swing.ImageIcon;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.border.EmptyBorder;
import net.runelite.api.InventoryID;
import net.runelite.client.game.ItemManager;
import net.runelite.client.plugins.inventorysetups.InventorySetup;
import net.runelite.client.plugins.inventorysetups.InventorySetupItem;
import net.runelite.client.plugins.inventorysetups.InventorySetupPlugin;
import net.runelite.client.ui.PluginPanel;
import net.runelite.client.ui.components.PluginErrorPanel;
import net.runelite.client.util.ImageUtil;
public class InventorySetupPluginPanel extends PluginPanel
{
private static ImageIcon ADD_ICON;
private static ImageIcon ADD_HOVER_ICON;
private static ImageIcon REMOVE_ICON;
private static ImageIcon REMOVE_HOVER_ICON;
private final JPanel noSetupsPanel;
private final JPanel invEqPanel;
private final InventorySetupInventoryPanel invPanel;
private final InventorySetupEquipmentPanel eqpPanel;
private final JComboBox<String> setupComboBox;
private final JLabel removeMarker;
private final InventorySetupPlugin plugin;
static
{
final BufferedImage addIcon = ImageUtil.getResourceStreamFromClass(InventorySetupPlugin.class, "add_icon.png");
ADD_ICON = new ImageIcon(addIcon);
ADD_HOVER_ICON = new ImageIcon(ImageUtil.alphaOffset(addIcon, 0.53f));
final BufferedImage removeIcon = ImageUtil.getResourceStreamFromClass(InventorySetupPlugin.class, "remove_icon.png");
REMOVE_ICON = new ImageIcon(removeIcon);
REMOVE_HOVER_ICON = new ImageIcon(ImageUtil.alphaOffset(removeIcon, 0.53f));
}
public InventorySetupPluginPanel(final InventorySetupPlugin plugin, final ItemManager itemManager)
{
super(false);
this.plugin = plugin;
this.removeMarker = new JLabel(REMOVE_ICON);
this.invPanel = new InventorySetupInventoryPanel(itemManager, plugin);
this.eqpPanel = new InventorySetupEquipmentPanel(itemManager, plugin);
this.noSetupsPanel = new JPanel();
this.invEqPanel = new JPanel();
this.setupComboBox = new JComboBox<>();
// setup the title
final JLabel addMarker = new JLabel(ADD_ICON);
final JLabel title = new JLabel();
title.setText("Inventory Setups");
title.setForeground(Color.WHITE);
// setup the add marker (+ sign in the top right)
addMarker.setToolTipText("Add a new inventory setup");
addMarker.addMouseListener(new MouseAdapter()
{
@Override
public void mouseClicked(MouseEvent e)
{
plugin.addInventorySetup();
}
@Override
public void mouseEntered(MouseEvent e)
{
addMarker.setIcon(ADD_HOVER_ICON);
}
@Override
public void mouseExited(MouseEvent e)
{
addMarker.setIcon(ADD_ICON);
}
});
// setup the remove marker (X sign in the top right)
removeMarker.setToolTipText("Remove the current inventory setup");
removeMarker.addMouseListener(new MouseAdapter()
{
@Override
public void mouseClicked(MouseEvent e)
{
final String name = (String) setupComboBox.getSelectedItem();
plugin.removeInventorySetup(name, true);
}
@Override
public void mouseEntered(MouseEvent e)
{
if (removeMarker.isEnabled())
{
removeMarker.setIcon(REMOVE_HOVER_ICON);
}
}
@Override
public void mouseExited(MouseEvent e)
{
removeMarker.setIcon(REMOVE_ICON);
}
});
// setup the combo box for selection switching
// add empty to indicate the empty position
setupComboBox.addItem("");
setupComboBox.setSelectedIndex(0);
setupComboBox.addItemListener(e ->
{
if (e.getStateChange() == ItemEvent.SELECTED)
{
String selection = (String) e.getItem();
setCurrentInventorySetup(selection);
}
});
// the panel on the top right that holds the add and delete buttons
final JPanel markersPanel = new JPanel();
markersPanel.setLayout(new FlowLayout(FlowLayout.RIGHT, 10, 0));
markersPanel.add(removeMarker);
markersPanel.add(addMarker);
// the top panel that has the title and the buttons
final JPanel titleAndMarkersPanel = new JPanel();
titleAndMarkersPanel.setLayout(new BorderLayout());
titleAndMarkersPanel.add(title, BorderLayout.WEST);
titleAndMarkersPanel.add(markersPanel, BorderLayout.EAST);
// the panel that stays at the top and doesn't scroll
// contains the title, buttons, and the combo box
final JPanel northAnchoredPanel = new JPanel();
northAnchoredPanel.setLayout(new BoxLayout(northAnchoredPanel, BoxLayout.Y_AXIS));
northAnchoredPanel.setBorder(new EmptyBorder(0, 0, 10, 0));
northAnchoredPanel.add(titleAndMarkersPanel);
northAnchoredPanel.add(Box.createRigidArea(new Dimension(0, 10)));
northAnchoredPanel.add(setupComboBox);
// the panel that holds the inventory and equipment panels
final BoxLayout invEqLayout = new BoxLayout(invEqPanel, BoxLayout.Y_AXIS);
invEqPanel.setLayout(invEqLayout);
invEqPanel.add(invPanel);
invEqPanel.add(Box.createRigidArea(new Dimension(0, 10)));
invEqPanel.add(eqpPanel);
// setup the error panel. It's wrapped around a normal panel
// so it doesn't stretch to fill the parent panel
final PluginErrorPanel errorPanel = new PluginErrorPanel();
errorPanel.setContent("Inventory Setups", "Select or create an inventory setup.");
noSetupsPanel.add(errorPanel);
// the panel that holds the inventory panels, and the error panel
final JPanel contentPanel = new JPanel();
final BoxLayout contentLayout = new BoxLayout(contentPanel, BoxLayout.Y_AXIS);
contentPanel.setLayout(contentLayout);
contentPanel.add(invEqPanel);
contentPanel.add(noSetupsPanel);
// wrapper for the main content panel to keep it from stretching
final JPanel contentWrapper = new JPanel(new BorderLayout());
contentWrapper.add(Box.createGlue(), BorderLayout.CENTER);
contentWrapper.add(contentPanel, BorderLayout.NORTH);
final JScrollPane contentWrapperPane = new JScrollPane(contentWrapper);
contentWrapperPane.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);
setLayout(new BorderLayout());
setBorder(new EmptyBorder(10, 10, 10, 10));
add(northAnchoredPanel, BorderLayout.NORTH);
add(contentWrapperPane, BorderLayout.CENTER);
// show the no setups panel on startup
showNoSetupsPanel();
}
public void showNoSetupsPanel()
{
setupComboBox.setSelectedIndex(0);
removeMarker.setEnabled(false);
noSetupsPanel.setVisible(true);
invEqPanel.setVisible(false);
}
private void showHasSetupPanel(final String name)
{
setupComboBox.setSelectedItem(name);
removeMarker.setEnabled(true);
noSetupsPanel.setVisible(false);
invEqPanel.setVisible(true);
}
public void setCurrentInventorySetup(final String name)
{
if (name.isEmpty())
{
showNoSetupsPanel();
return;
}
showHasSetupPanel(name);
final InventorySetup inventorySetup = plugin.getInventorySetup(name);
invPanel.setInventorySetupSlots(inventorySetup);
eqpPanel.setEquipmentSetupSlots(inventorySetup);
if (plugin.getHighlightDifference())
{
final ArrayList<InventorySetupItem> normInv = plugin.getNormalizedContainer(InventoryID.INVENTORY);
final ArrayList<InventorySetupItem> normEqp = plugin.getNormalizedContainer(InventoryID.EQUIPMENT);
highlightDifferences(normInv, inventorySetup, InventoryID.INVENTORY);
highlightDifferences(normEqp, inventorySetup, InventoryID.EQUIPMENT);
}
else
{
invPanel.resetInventorySlotsColor();
eqpPanel.resetEquipmentSlotsColor();
}
validate();
repaint();
}
public void addInventorySetup(final String name)
{
setupComboBox.addItem(name);
}
public void removeInventorySetup(final String name)
{
setupComboBox.removeItem(name);
showNoSetupsPanel();
invPanel.resetInventorySlotsColor();
eqpPanel.resetEquipmentSlotsColor();
validate();
repaint();
}
public void highlightDifferences(final ArrayList<InventorySetupItem> container,
final InventorySetup setupToCheck,
final InventoryID type)
{
switch (type)
{
case INVENTORY:
invPanel.highlightDifferentSlots(container, setupToCheck);
break;
case EQUIPMENT:
eqpPanel.highlightDifferences(container, setupToCheck);
break;
}
}
public final String getSelectedInventorySetup()
{
return (String) setupComboBox.getSelectedItem();
}
}

View File

@@ -0,0 +1,40 @@
package net.runelite.client.plugins.inventorysetups.ui;
import java.awt.Color;
import java.awt.Dimension;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingConstants;
import net.runelite.client.game.AsyncBufferedImage;
public class InventorySetupSlot extends JPanel
{
private final JLabel imageLabel;
public InventorySetupSlot(Color color)
{
imageLabel = new JLabel();
imageLabel.setVerticalAlignment(SwingConstants.CENTER);
setPreferredSize(new Dimension(46, 42));
setBackground(color);
add(imageLabel);
}
public void setImageLabel(String toolTip, AsyncBufferedImage itemImage)
{
if (itemImage == null || toolTip == null)
{
imageLabel.setToolTipText("");
imageLabel.setIcon(null);
imageLabel.revalidate();
return;
}
imageLabel.setToolTipText(toolTip);
itemImage.addTo(imageLabel);
validate();
repaint();
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 121 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 765 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 299 B