238 lines
8.3 KiB
Java
238 lines
8.3 KiB
Java
package eu.univento.core.api.items;
|
|
|
|
import eu.univento.core.api.items.events.NamedCloseEvent;
|
|
import eu.univento.core.api.items.events.PageCloseEvent;
|
|
import eu.univento.core.api.player.CustomPlayer;
|
|
import org.bukkit.Bukkit;
|
|
import org.bukkit.Material;
|
|
import org.bukkit.event.inventory.InventoryClickEvent;
|
|
import org.bukkit.event.inventory.InventoryDragEvent;
|
|
import org.bukkit.inventory.Inventory;
|
|
import org.bukkit.inventory.ItemStack;
|
|
import org.bukkit.metadata.FixedMetadataValue;
|
|
import org.bukkit.plugin.java.JavaPlugin;
|
|
|
|
import java.lang.reflect.Array;
|
|
import java.util.HashMap;
|
|
|
|
/**
|
|
* @author joethei
|
|
* @version 0.1
|
|
*/
|
|
public abstract class ClickInventory<E>{
|
|
|
|
protected static JavaPlugin plugin;
|
|
protected Inventory currentInventory;
|
|
protected boolean inventoryInUse;
|
|
private boolean modifiable;
|
|
private CustomPlayer player;
|
|
private boolean playerInventoryUsed;
|
|
private ItemStack[] previousContents;
|
|
private String inventoryName;
|
|
private HashMap<Object, Object> savedData;
|
|
|
|
protected void saveContents() {
|
|
this.previousContents = this.getPlayer().getInventory().getContents().clone();
|
|
}
|
|
|
|
public Object getData(final Object key) {
|
|
return this.savedData.get(key);
|
|
}
|
|
|
|
public ClickInventory setData(final Object key, final Object obj) {
|
|
if (obj == null) {
|
|
this.savedData.remove(key);
|
|
}
|
|
else {
|
|
this.savedData.put(key, obj);
|
|
}
|
|
return this;
|
|
}
|
|
|
|
public ClickInventory(String inventoryName, final CustomPlayer player) {
|
|
this.savedData = new HashMap<>();
|
|
this.player = player;
|
|
if (inventoryName == null) {
|
|
inventoryName = this.getClass().getSimpleName();
|
|
}
|
|
this.inventoryName = inventoryName;
|
|
}
|
|
|
|
public String getName() {
|
|
return this.inventoryName;
|
|
}
|
|
|
|
public ClickInventory setPlayerInventory() {
|
|
if (!this.isInUse()) {
|
|
this.playerInventoryUsed = true;
|
|
}
|
|
return this;
|
|
}
|
|
|
|
public void closeInventory() {
|
|
this.closeInventory(true);
|
|
}
|
|
|
|
protected void onInventoryDrag(final InventoryDragEvent event) {
|
|
if (!this.isModifiable()) {
|
|
event.getRawSlots().stream().filter(this::checkInMenu).forEachOrdered(slot -> event.setCancelled(true));
|
|
}
|
|
}
|
|
|
|
protected boolean checkInMenu(int rawSlot) {
|
|
if (this.isPlayerInventory()) {
|
|
if (this.getPlayer().getOpenInventory().getTopInventory().getHolder() != this.getPlayer()) {
|
|
rawSlot -= this.getPlayer().getOpenInventory().getTopInventory().getSize();
|
|
}
|
|
return rawSlot >= 0 && rawSlot < this.currentInventory.getSize();
|
|
}
|
|
return rawSlot < this.currentInventory.getSize();
|
|
}
|
|
|
|
public boolean isPlayerInventory() {
|
|
return this.playerInventoryUsed;
|
|
}
|
|
|
|
protected abstract void onInventoryClick(final InventoryClickEvent e);
|
|
|
|
private void closeInventory(final boolean forceClose, final boolean restoreInventory) {
|
|
InventoryManager.removeInventory(this);
|
|
this.inventoryInUse = false;
|
|
if (this.getPlayer().hasMetadata(this.getClass().getSimpleName())) {
|
|
final E[] invs = (E[])this.getPlayer().getMetadata(this.getClass().getSimpleName()).get(0).value();
|
|
if (invs[isPlayerInventory() ? 1 : 0] == this)
|
|
invs[isPlayerInventory() ? 1 : 0] = null;
|
|
}
|
|
if (this instanceof NamedInventory) {
|
|
Bukkit.getPluginManager().callEvent(new NamedCloseEvent((NamedInventory) this));
|
|
}
|
|
if (this instanceof PageInventory) {
|
|
Bukkit.getPluginManager().callEvent(new PageCloseEvent((PageInventory) this));
|
|
}
|
|
if (forceClose && (!this.isPlayerInventory() || this.getPlayer().getOpenInventory().getTopInventory().equals(this.currentInventory))) {
|
|
this.getPlayer().closeInventory();
|
|
}
|
|
if (this.isPlayerInventory() && restoreInventory) {
|
|
this.getPlayer().getInventory().clear();
|
|
this.getPlayer().getInventory().setContents(this.previousContents);
|
|
Bukkit.getScheduler().scheduleSyncDelayedTask(ClickInventory.plugin, () -> ClickInventory.this.getPlayer().updateInventory());
|
|
}
|
|
}
|
|
|
|
public void closeInventory(final boolean forceClose) {
|
|
this.closeInventory(forceClose, true);
|
|
}
|
|
|
|
public ItemStack getItem(int slot) {
|
|
if (this.isPlayerInventory()) {
|
|
slot += 9;
|
|
if (slot >= 36) {
|
|
slot -= 36;
|
|
}
|
|
}
|
|
if (this.currentInventory != null && this.currentInventory.getSize() > slot) {
|
|
return this.currentInventory.getItem(slot);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
protected void setItems(final ItemStack[] items) {
|
|
if (this.isPlayerInventory()) {
|
|
for (int i = 0; i < items.length; ++i) {
|
|
this.setItem(i, items[i]);
|
|
}
|
|
}
|
|
else {
|
|
this.currentInventory.setContents(items);
|
|
}
|
|
}
|
|
|
|
protected void setItem(int slot, final ItemStack item) {
|
|
if (this.isPlayerInventory()) {
|
|
slot += 9;
|
|
if (slot >= 36) {
|
|
slot -= 36;
|
|
}
|
|
}
|
|
this.currentInventory.setItem(slot, item);
|
|
}
|
|
|
|
public CustomPlayer getPlayer() {
|
|
return this.player;
|
|
}
|
|
|
|
public boolean isInUse() {
|
|
return this.inventoryInUse;
|
|
}
|
|
|
|
public boolean isModifiable() {
|
|
return this.modifiable;
|
|
}
|
|
|
|
protected void openInventory() {
|
|
final boolean isSwitchingInventory = this.isInUse();
|
|
ItemStack heldItem = null;
|
|
final ClickInventory[] invs = new ClickInventory[2];
|
|
for (final String inv : new String[] { "PageInventory", "NamedInventory", "AnvilInventory" }) {
|
|
if (this.getPlayer().hasMetadata(inv)) {
|
|
final E[] invss = (E[])(this.getPlayer().hasMetadata(inv) ? this.getPlayer().getMetadata(inv).get(0).value() : null);
|
|
if (invss != null) {
|
|
for (int i = 0; i < 2; ++i) {
|
|
if (invss[i] != null) {
|
|
invs[i] = (ClickInventory)invss[i];
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
if (!this.isPlayerInventory()) {
|
|
this.inventoryInUse = false;
|
|
boolean previous = false;
|
|
if (invs[1] != null) {
|
|
previous = invs[1].inventoryInUse;
|
|
invs[1].inventoryInUse = false;
|
|
}
|
|
if (isSwitchingInventory) {
|
|
heldItem = this.getPlayer().getItemOnCursor();
|
|
this.getPlayer().setItemOnCursor(new ItemStack(Material.AIR));
|
|
}
|
|
if (invs[1] != null) {
|
|
invs[1].inventoryInUse = previous;
|
|
}
|
|
}
|
|
else {
|
|
this.getPlayer().updateInventory();
|
|
if (!isSwitchingInventory && this.getPlayer().getOpenInventory().getTopInventory().getHolder() == this.getPlayer()) {
|
|
this.getPlayer().openInventory(Bukkit.createInventory(null, 0, this.getTitle()));
|
|
}
|
|
}
|
|
if (!isSwitchingInventory) {
|
|
InventoryManager.addInventory(this);
|
|
final int slot = this.isPlayerInventory() ? 1 : 0;
|
|
if (invs[slot] != null) {
|
|
if (invs[slot].inventoryInUse) {
|
|
invs[slot].closeInventory(false, false);
|
|
}
|
|
if (this.isPlayerInventory()) {
|
|
this.previousContents = invs[1].previousContents;
|
|
}
|
|
}
|
|
final E[] inv2 = (E[])(this.getPlayer().hasMetadata(this.getClass().getSimpleName()) ? this.getPlayer().getMetadata(this.getClass().getSimpleName()).get(0).value() : ((Object[]) Array.newInstance(this.getClass(), 2)));
|
|
inv2[slot] = (E)this;
|
|
this.getPlayer().setMetadata(this.getClass().getSimpleName(), new FixedMetadataValue(ClickInventory.plugin, inv2));
|
|
}
|
|
else if (heldItem != null && heldItem.getType() != Material.AIR) {
|
|
this.getPlayer().setItemOnCursor(heldItem);
|
|
this.getPlayer().updateInventory();
|
|
}
|
|
this.inventoryInUse = true;
|
|
}
|
|
|
|
public abstract String getTitle();
|
|
|
|
public void setModifiable(final boolean modifiable) {
|
|
this.modifiable = modifiable;
|
|
}
|
|
|
|
public abstract void setTitle(final String p0);
|
|
} |