InventoryGUI GUI change with transition
This commit is contained in:
@@ -17,7 +17,7 @@ fun HumanEntity.openGUI(gui: InventoryGUI<*>, page: Int? = null): InventoryView?
|
|||||||
closeInventory()
|
closeInventory()
|
||||||
|
|
||||||
if (page != null)
|
if (page != null)
|
||||||
gui.loadPage(page)
|
gui.loadPageUnsafe(page)
|
||||||
|
|
||||||
return openInventory(gui.bukkitInventory)
|
return openInventory(gui.bukkitInventory)
|
||||||
|
|
||||||
@@ -42,7 +42,7 @@ class InventoryGUIHolder(kSpigot: KSpigot) : AutoCloseable {
|
|||||||
kSpigot.listen<InventoryClickEvent> {
|
kSpigot.listen<InventoryClickEvent> {
|
||||||
|
|
||||||
val inv = registered.find { search -> search.isThisInv(it.inventory) } ?: return@listen
|
val inv = registered.find { search -> search.isThisInv(it.inventory) } ?: return@listen
|
||||||
val invPage = inv.currentPage
|
val invPage = inv.currentPageInt
|
||||||
|
|
||||||
val slot = inv.data.pages[invPage]?.slots?.get(it.slot)
|
val slot = inv.data.pages[invPage]?.slots?.get(it.slot)
|
||||||
if (slot != null)
|
if (slot != null)
|
||||||
@@ -77,28 +77,59 @@ class InventoryGUIData<T : ForInventory>(
|
|||||||
val plugin: KSpigot,
|
val plugin: KSpigot,
|
||||||
val inventoryType: InventoryType<T>,
|
val inventoryType: InventoryType<T>,
|
||||||
val title: String?,
|
val title: String?,
|
||||||
val pages: Map<Int, InventoryGUIPage<T>>
|
internal val pages: Map<Int, InventoryGUIPage<T>>,
|
||||||
|
val transitionTo: InventoryGUIPageChangeEffect?,
|
||||||
|
val transitionFrom: InventoryGUIPageChangeEffect?,
|
||||||
|
internal val generalOnClick: ((InventoryGUIClickEvent<T>) -> Unit)?
|
||||||
)
|
)
|
||||||
|
|
||||||
abstract class InventoryGUI<T : ForInventory>(
|
abstract class InventoryGUI<T : ForInventory>(
|
||||||
val data: InventoryGUIData<T>
|
val data: InventoryGUIData<T>
|
||||||
) {
|
) {
|
||||||
|
|
||||||
var currentPage: Int = DEFAULT_PAGE; protected set
|
var currentPageInt: Int = DEFAULT_PAGE; protected set
|
||||||
|
val currentPage get() = getPage(currentPageInt)
|
||||||
|
?: throw IllegalStateException("The currentPageInt has no associated page!")
|
||||||
|
|
||||||
abstract val bukkitInventory: Inventory
|
internal abstract val bukkitInventory: Inventory
|
||||||
|
|
||||||
abstract fun loadPage(page: Int, offsetHorizontally: Int = 0, offsetVertically: Int = 0)
|
internal abstract fun loadPageUnsafe(page: InventoryGUIPage<*>?, offsetHorizontally: Int = 0, offsetVertically: Int = 0)
|
||||||
|
internal abstract fun loadPageUnsafe(page: Int, offsetHorizontally: Int = 0, offsetVertically: Int = 0)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return True, if the [inventory] belongs to this GUI.
|
||||||
|
*/
|
||||||
abstract fun isThisInv(inventory: Inventory): Boolean
|
abstract fun isThisInv(inventory: Inventory): Boolean
|
||||||
|
|
||||||
abstract operator fun set(slot: InventorySlotCompound<T>, value: ItemStack)
|
/**
|
||||||
|
* Registers this InventoryGUI.
|
||||||
|
* (KSpigot will listen for actions in the inventory.)
|
||||||
|
*/
|
||||||
@Suppress("UNCHECKED_CAST")
|
@Suppress("UNCHECKED_CAST")
|
||||||
fun register() = data.plugin.inventoryGUIHolder.register(this as InventoryGUI<ForInventory>)
|
fun register() = data.plugin.inventoryGUIHolder.register(this as InventoryGUI<ForInventory>)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Stops KSpigot from listening to actions in this
|
||||||
|
* InventoryGUI anymore.
|
||||||
|
*/
|
||||||
@Suppress("UNCHECKED_CAST")
|
@Suppress("UNCHECKED_CAST")
|
||||||
fun unregister() = data.plugin.inventoryGUIHolder.unregister(this as InventoryGUI<ForInventory>)
|
fun unregister() = data.plugin.inventoryGUIHolder.unregister(this as InventoryGUI<ForInventory>)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Loads the specified page in order to display it in the GUI.
|
||||||
|
*/
|
||||||
|
fun loadPage(page: InventoryGUIPage<T>) = loadPageUnsafe(page)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Temporarily sets the given item at the given slots.
|
||||||
|
*/
|
||||||
|
abstract operator fun set(slot: InventorySlotCompound<T>, value: ItemStack)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Searches for a page associated to the given [page] index.
|
||||||
|
*/
|
||||||
|
fun getPage(page: Int?) = data.pages[page]
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Inventory GUI implementations
|
// Inventory GUI implementations
|
||||||
@@ -109,21 +140,24 @@ class InventoryGUIShared<T : ForInventory>(
|
|||||||
|
|
||||||
override val bukkitInventory = data.inventoryType.createBukkitInv(null, data.title)
|
override val bukkitInventory = data.inventoryType.createBukkitInv(null, data.title)
|
||||||
|
|
||||||
init { loadPage(DEFAULT_PAGE) }
|
init { loadPageUnsafe(DEFAULT_PAGE) }
|
||||||
|
|
||||||
override fun isThisInv(inventory: Inventory) = inventory == bukkitInventory
|
override fun isThisInv(inventory: Inventory) = inventory == bukkitInventory
|
||||||
|
|
||||||
override fun loadPage(page: Int, offsetHorizontally: Int, offsetVertically: Int) {
|
override fun loadPageUnsafe(page: InventoryGUIPage<*>?, offsetHorizontally: Int, offsetVertically: Int) {
|
||||||
|
|
||||||
fun ifOffset(): Boolean = offsetHorizontally != 0 || offsetVertically != 0
|
if (page == null) return
|
||||||
|
|
||||||
currentPage = page
|
val ifOffset = offsetHorizontally != 0 || offsetVertically != 0
|
||||||
|
|
||||||
data.pages[page]?.slots?.let { slots ->
|
if (!ifOffset)
|
||||||
|
currentPageInt = page.number
|
||||||
|
|
||||||
|
page.slots.let { slots ->
|
||||||
|
|
||||||
val dimensions = data.inventoryType.dimensions
|
val dimensions = data.inventoryType.dimensions
|
||||||
|
|
||||||
if (ifOffset()) {
|
if (ifOffset) {
|
||||||
dimensions.invSlots.forEach {
|
dimensions.invSlots.forEach {
|
||||||
dimensions.invSlotsWithRealSlots[it.add(offsetHorizontally, offsetVertically)]?.let { slotToClear ->
|
dimensions.invSlotsWithRealSlots[it.add(offsetHorizontally, offsetVertically)]?.let { slotToClear ->
|
||||||
if (dimensions.realSlots.contains(slotToClear))
|
if (dimensions.realSlots.contains(slotToClear))
|
||||||
@@ -138,7 +172,7 @@ class InventoryGUIShared<T : ForInventory>(
|
|||||||
val slot = it.value
|
val slot = it.value
|
||||||
if (slot is InventoryGUIElement) {
|
if (slot is InventoryGUIElement) {
|
||||||
|
|
||||||
if (ifOffset()) {
|
if (ifOffset) {
|
||||||
val invSlot = InventorySlot.fromRealSlot(it.key, dimensions)
|
val invSlot = InventorySlot.fromRealSlot(it.key, dimensions)
|
||||||
if (invSlot != null) {
|
if (invSlot != null) {
|
||||||
val offsetSlot = invSlot.add(offsetHorizontally, offsetVertically).realSlotIn(dimensions)
|
val offsetSlot = invSlot.add(offsetHorizontally, offsetVertically).realSlotIn(dimensions)
|
||||||
@@ -157,6 +191,10 @@ class InventoryGUIShared<T : ForInventory>(
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun loadPageUnsafe(page: Int, offsetHorizontally: Int, offsetVertically: Int) {
|
||||||
|
data.pages[page]?.let { loadPageUnsafe(it, offsetHorizontally, offsetVertically) }
|
||||||
|
}
|
||||||
|
|
||||||
override operator fun set(slot: InventorySlotCompound<T>, value: ItemStack) {
|
override operator fun set(slot: InventorySlotCompound<T>, value: ItemStack) {
|
||||||
slot.realSlotsWithInvType(data.inventoryType).forEach {
|
slot.realSlotsWithInvType(data.inventoryType).forEach {
|
||||||
bukkitInventory.setItem(it, value)
|
bukkitInventory.setItem(it, value)
|
||||||
@@ -166,10 +204,8 @@ class InventoryGUIShared<T : ForInventory>(
|
|||||||
}
|
}
|
||||||
|
|
||||||
class InventoryGUIPage<T : ForInventory>(
|
class InventoryGUIPage<T : ForInventory>(
|
||||||
val slots: Map<Int, InventoryGUISlot<T>>,
|
val number: Int,
|
||||||
transitionTo: InventoryGUIPageChangeEffect?,
|
internal val slots: Map<Int, InventoryGUISlot<T>>,
|
||||||
transitionFrom: InventoryGUIPageChangeEffect?
|
val transitionTo: InventoryGUIPageChangeEffect?,
|
||||||
) {
|
val transitionFrom: InventoryGUIPageChangeEffect?
|
||||||
val pageChangerTo = transitionTo?.let { InventoryGUIPageChanger(it) }
|
)
|
||||||
val pageChangerFrom = transitionFrom?.let { InventoryGUIPageChanger(it) }
|
|
||||||
}
|
|
@@ -5,7 +5,7 @@ package net.axay.kspigot.inventory
|
|||||||
import net.axay.kspigot.main.KSpigot
|
import net.axay.kspigot.main.KSpigot
|
||||||
import org.bukkit.inventory.ItemStack
|
import org.bukkit.inventory.ItemStack
|
||||||
|
|
||||||
inline fun <T : ForInventory> KSpigot.inventoryGUI(
|
fun <T : ForInventory> KSpigot.inventoryGUI(
|
||||||
type: InventoryType<T>,
|
type: InventoryType<T>,
|
||||||
builder: InventoryGUIBuilder<T>.() -> Unit,
|
builder: InventoryGUIBuilder<T>.() -> Unit,
|
||||||
) = InventoryGUIBuilder(this, type).apply(builder).build()
|
) = InventoryGUIBuilder(this, type).apply(builder).build()
|
||||||
@@ -17,16 +17,29 @@ class InventoryGUIBuilder<T : ForInventory>(
|
|||||||
|
|
||||||
var title: String = ""
|
var title: String = ""
|
||||||
|
|
||||||
|
var transitionTo: InventoryGUIPageChangeEffect? = null
|
||||||
|
var transitionFrom: InventoryGUIPageChangeEffect? = null
|
||||||
|
|
||||||
private val guiSlots = HashMap<Int, InventoryGUIPage<T>>()
|
private val guiSlots = HashMap<Int, InventoryGUIPage<T>>()
|
||||||
|
|
||||||
|
private var onClickElement: ((InventoryGUIClickEvent<T>) -> Unit)? = null
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
* Opens the builder for a new page and adds
|
||||||
|
* the new page to the GUI.
|
||||||
|
* @param page The index of the page.
|
||||||
*/
|
*/
|
||||||
fun page(page: Int, builder: InventoryGUIPageBuilder<T>.() -> Unit) {
|
fun page(page: Int, builder: InventoryGUIPageBuilder<T>.() -> Unit) {
|
||||||
guiSlots[page] = InventoryGUIPageBuilder(type, page).apply(builder).build()
|
guiSlots[page] = InventoryGUIPageBuilder(type, page).apply(builder).build()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun build() = InventoryGUIShared(InventoryGUIData(kSpigot, type, title, guiSlots)).apply { register() }
|
fun onClickElement(onClick: (InventoryGUIClickEvent<T>) -> Unit) {
|
||||||
|
onClickElement = onClick
|
||||||
|
}
|
||||||
|
|
||||||
|
internal fun build() = InventoryGUIShared(
|
||||||
|
InventoryGUIData(kSpigot, type, title, guiSlots, transitionTo, transitionFrom, onClickElement)
|
||||||
|
).apply { register() }
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -40,20 +53,22 @@ class InventoryGUIPageBuilder<T : ForInventory>(
|
|||||||
var transitionTo: InventoryGUIPageChangeEffect? = null
|
var transitionTo: InventoryGUIPageChangeEffect? = null
|
||||||
var transitionFrom: InventoryGUIPageChangeEffect? = null
|
var transitionFrom: InventoryGUIPageChangeEffect? = null
|
||||||
|
|
||||||
|
internal fun build() = InventoryGUIPage(page, guiSlots, transitionTo, transitionFrom)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A button is an item protected from any player
|
* A button is an item protected from any player
|
||||||
* actions. If clicked, the specified [onClick]
|
* actions. If clicked, the specified [onClick]
|
||||||
* function is invoked.
|
* function is invoked.
|
||||||
*/
|
*/
|
||||||
fun button(slots: InventorySlotCompound<T>, itemStack: ItemStack, onClick: (InventoryGUIClickEvent<T>) -> Unit)
|
fun button(slots: InventorySlotCompound<T>, itemStack: ItemStack, onClick: (InventoryGUIClickEvent<T>) -> Unit)
|
||||||
= slots(slots, InventoryGUIButton(InventoryGUIElementData(itemStack), onClick))
|
= defineSlots(slots, InventoryGUIButton(InventoryGUIElementData(itemStack), onClick))
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An item protected from any player actions.
|
* An item protected from any player actions.
|
||||||
* This is not a button.
|
* This is not a button.
|
||||||
*/
|
*/
|
||||||
fun placeholder(slots: InventorySlotCompound<T>, itemStack: ItemStack)
|
fun placeholder(slots: InventorySlotCompound<T>, itemStack: ItemStack)
|
||||||
= slots(slots, InventoryGUIPlaceholder(InventoryGUIElementData(itemStack)))
|
= defineSlots(slots, InventoryGUIPlaceholder(InventoryGUIElementData(itemStack)))
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A free slot does not block any player actions.
|
* A free slot does not block any player actions.
|
||||||
@@ -61,14 +76,14 @@ class InventoryGUIPageBuilder<T : ForInventory>(
|
|||||||
* items out of it.
|
* items out of it.
|
||||||
*/
|
*/
|
||||||
fun freeSlot(slots: InventorySlotCompound<T>)
|
fun freeSlot(slots: InventorySlotCompound<T>)
|
||||||
= slots(slots, InventoryGUIFreeSlot())
|
= defineSlots(slots, InventoryGUIFreeSlot())
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This is a button which loads the specified
|
* This is a button which loads the specified
|
||||||
* [toPage] if clicked.
|
* [toPage] if clicked.
|
||||||
*/
|
*/
|
||||||
fun pageChanger(slots: InventorySlotCompound<T>, itemStack: ItemStack, toPage: Int, onChange: ((InventoryGUIClickEvent<T>) -> Unit)? = null)
|
fun pageChanger(slots: InventorySlotCompound<T>, itemStack: ItemStack, toPage: Int, onChange: ((InventoryGUIClickEvent<T>) -> Unit)? = null)
|
||||||
= slots(slots, InventoryGUIButtonPageChange(
|
= defineSlots(slots, InventoryGUIButtonPageChange(
|
||||||
InventoryGUIElementData(itemStack),
|
InventoryGUIElementData(itemStack),
|
||||||
InventoryGUIPageChangeCalculator.InventoryGUIConsistentPageCalculator(toPage),
|
InventoryGUIPageChangeCalculator.InventoryGUIConsistentPageCalculator(toPage),
|
||||||
onChange
|
onChange
|
||||||
@@ -80,7 +95,7 @@ class InventoryGUIPageBuilder<T : ForInventory>(
|
|||||||
* exists it is loaded.
|
* exists it is loaded.
|
||||||
*/
|
*/
|
||||||
fun previousPage(slots: InventorySlotCompound<T>, itemStack: ItemStack, onChange: ((InventoryGUIClickEvent<T>) -> Unit)? = null)
|
fun previousPage(slots: InventorySlotCompound<T>, itemStack: ItemStack, onChange: ((InventoryGUIClickEvent<T>) -> Unit)? = null)
|
||||||
= slots(slots, InventoryGUIButtonPageChange(
|
= defineSlots(slots, InventoryGUIButtonPageChange(
|
||||||
InventoryGUIElementData(itemStack),
|
InventoryGUIElementData(itemStack),
|
||||||
InventoryGUIPageChangeCalculator.InventoryGUIPreviousPageCalculator,
|
InventoryGUIPageChangeCalculator.InventoryGUIPreviousPageCalculator,
|
||||||
onChange
|
onChange
|
||||||
@@ -92,17 +107,27 @@ class InventoryGUIPageBuilder<T : ForInventory>(
|
|||||||
* exists it is loaded.
|
* exists it is loaded.
|
||||||
*/
|
*/
|
||||||
fun nextPage(slots: InventorySlotCompound<T>, itemStack: ItemStack, onChange: ((InventoryGUIClickEvent<T>) -> Unit)? = null)
|
fun nextPage(slots: InventorySlotCompound<T>, itemStack: ItemStack, onChange: ((InventoryGUIClickEvent<T>) -> Unit)? = null)
|
||||||
= slots(slots, InventoryGUIButtonPageChange(
|
= defineSlots(slots, InventoryGUIButtonPageChange(
|
||||||
InventoryGUIElementData(itemStack),
|
InventoryGUIElementData(itemStack),
|
||||||
InventoryGUIPageChangeCalculator.InventoryGUINextPageCalculator,
|
InventoryGUIPageChangeCalculator.InventoryGUINextPageCalculator,
|
||||||
onChange
|
onChange
|
||||||
))
|
))
|
||||||
|
|
||||||
private fun slots(slots: InventorySlotCompound<T>, element: InventoryGUISlot<T>)
|
/**
|
||||||
|
* By pressing this button, the player switches to another
|
||||||
|
* InventoryGUI. The transition effect is applied.
|
||||||
|
*/
|
||||||
|
fun changeGUI(slots: InventorySlotCompound<T>, itemStack: ItemStack, newGUI: InventoryGUI<*>, newPage: Int? = null, onChange: ((InventoryGUIClickEvent<T>) -> Unit)? = null)
|
||||||
|
= defineSlots(slots, InventoryGUIButtonInventoryChange(
|
||||||
|
InventoryGUIElementData(itemStack),
|
||||||
|
newGUI,
|
||||||
|
newPage,
|
||||||
|
onChange
|
||||||
|
))
|
||||||
|
|
||||||
|
private fun defineSlots(slots: InventorySlotCompound<T>, element: InventoryGUISlot<T>)
|
||||||
= slots.withInvType(type).forEach { curSlot ->
|
= slots.withInvType(type).forEach { curSlot ->
|
||||||
curSlot.realSlotIn(type.dimensions)?.let { guiSlots[it] = element }
|
curSlot.realSlotIn(type.dimensions)?.let { guiSlots[it] = element }
|
||||||
}
|
}
|
||||||
|
|
||||||
fun build() = InventoryGUIPage(guiSlots, transitionTo, transitionFrom)
|
|
||||||
|
|
||||||
}
|
}
|
@@ -2,8 +2,8 @@ package net.axay.kspigot.inventory
|
|||||||
|
|
||||||
import org.bukkit.inventory.ItemStack
|
import org.bukkit.inventory.ItemStack
|
||||||
|
|
||||||
interface InventoryGUISlot<T : ForInventory> {
|
abstract class InventoryGUISlot<T : ForInventory> {
|
||||||
fun onClick(clickEvent: InventoryGUIClickEvent<T>)
|
abstract fun onClick(clickEvent: InventoryGUIClickEvent<T>)
|
||||||
}
|
}
|
||||||
|
|
||||||
// ELEMENT
|
// ELEMENT
|
||||||
@@ -14,7 +14,16 @@ class InventoryGUIElementData(
|
|||||||
|
|
||||||
abstract class InventoryGUIElement<T : ForInventory>(
|
abstract class InventoryGUIElement<T : ForInventory>(
|
||||||
val inventoryGUIElementData: InventoryGUIElementData
|
val inventoryGUIElementData: InventoryGUIElementData
|
||||||
) : InventoryGUISlot<T>
|
) : InventoryGUISlot<T>() {
|
||||||
|
|
||||||
|
final override fun onClick(clickEvent: InventoryGUIClickEvent<T>) {
|
||||||
|
clickEvent.gui.data.generalOnClick?.invoke(clickEvent)
|
||||||
|
onClickElement(clickEvent)
|
||||||
|
}
|
||||||
|
|
||||||
|
protected abstract fun onClickElement(clickEvent: InventoryGUIClickEvent<T>)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
// Element implementations
|
// Element implementations
|
||||||
|
|
||||||
@@ -23,7 +32,7 @@ open class InventoryGUIButton<T : ForInventory>(
|
|||||||
val action: (InventoryGUIClickEvent<T>) -> Unit,
|
val action: (InventoryGUIClickEvent<T>) -> Unit,
|
||||||
) : InventoryGUIElement<T>(inventoryGUIElementData) {
|
) : InventoryGUIElement<T>(inventoryGUIElementData) {
|
||||||
|
|
||||||
override fun onClick(clickEvent: InventoryGUIClickEvent<T>) {
|
override fun onClickElement(clickEvent: InventoryGUIClickEvent<T>) {
|
||||||
clickEvent.bukkitEvent.isCancelled = true
|
clickEvent.bukkitEvent.isCancelled = true
|
||||||
action(clickEvent)
|
action(clickEvent)
|
||||||
}
|
}
|
||||||
@@ -34,7 +43,7 @@ class InventoryGUIPlaceholder<T : ForInventory>(
|
|||||||
inventoryGUIElementData: InventoryGUIElementData
|
inventoryGUIElementData: InventoryGUIElementData
|
||||||
) : InventoryGUIElement<T>(inventoryGUIElementData) {
|
) : InventoryGUIElement<T>(inventoryGUIElementData) {
|
||||||
|
|
||||||
override fun onClick(clickEvent: InventoryGUIClickEvent<T>) {
|
override fun onClickElement(clickEvent: InventoryGUIClickEvent<T>) {
|
||||||
clickEvent.bukkitEvent.isCancelled = true
|
clickEvent.bukkitEvent.isCancelled = true
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -48,24 +57,44 @@ class InventoryGUIButtonPageChange<T : ForInventory>(
|
|||||||
: InventoryGUIButton<T>(inventoryGUIElementData, {
|
: InventoryGUIButton<T>(inventoryGUIElementData, {
|
||||||
|
|
||||||
val currentPage = it.gui.currentPage
|
val currentPage = it.gui.currentPage
|
||||||
|
val newPage = it.gui.getPage(calculator.calculateNewPage(it.gui.currentPageInt, it.gui.data.pages.keys))
|
||||||
|
if (newPage != null) {
|
||||||
|
|
||||||
val newPageInt = calculator.calculateNewPage(currentPage, it.gui.data.pages.keys)
|
val effect = (newPage.transitionTo ?: currentPage.transitionFrom)
|
||||||
if (newPageInt != null) {
|
?: InventoryGUIPageChangeEffect.INSTANT
|
||||||
|
|
||||||
|
it.gui.changePage(effect, currentPage, newPage)
|
||||||
|
|
||||||
onChange?.invoke(it)
|
onChange?.invoke(it)
|
||||||
|
|
||||||
val pageChanger
|
|
||||||
= (it.gui.data.pages[newPageInt]?.pageChangerTo ?: it.gui.data.pages[currentPage]?.pageChangerFrom)
|
|
||||||
?: InventoryGUIPageChanger(InventoryGUIPageChangeEffect.INSTANT)
|
|
||||||
|
|
||||||
pageChanger.changePage(it.gui, currentPage, newPageInt)
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
|
class InventoryGUIButtonInventoryChange<T : ForInventory>(
|
||||||
|
inventoryGUIElementData: InventoryGUIElementData,
|
||||||
|
changeToGUI: InventoryGUI<*>,
|
||||||
|
changeToPageInt: Int?,
|
||||||
|
onChange: ((InventoryGUIClickEvent<T>) -> Unit)?
|
||||||
|
)
|
||||||
|
: InventoryGUIButton<T>(inventoryGUIElementData, {
|
||||||
|
|
||||||
|
val effect = (changeToGUI.data.transitionTo ?: it.gui.data.transitionFrom)
|
||||||
|
?: InventoryGUIPageChangeEffect.INSTANT
|
||||||
|
|
||||||
|
val changeToPage = changeToGUI.getPage(changeToPageInt) ?: changeToGUI.currentPage
|
||||||
|
|
||||||
|
changeToGUI.changePage(effect, it.gui.currentPage, changeToPage)
|
||||||
|
|
||||||
|
it.bukkitEvent.whoClicked.openGUI(changeToGUI)
|
||||||
|
|
||||||
|
onChange?.invoke(it)
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
|
|
||||||
// FREE SLOT
|
// FREE SLOT
|
||||||
|
|
||||||
class InventoryGUIFreeSlot<T : ForInventory> : InventoryGUISlot<T> {
|
class InventoryGUIFreeSlot<T : ForInventory> : InventoryGUISlot<T>() {
|
||||||
override fun onClick(clickEvent: InventoryGUIClickEvent<T>) { /* do nothing */ }
|
override fun onClick(clickEvent: InventoryGUIClickEvent<T>) { /* do nothing */ }
|
||||||
}
|
}
|
@@ -8,11 +8,13 @@ abstract class InventoryGUIPageChangeCalculator {
|
|||||||
abstract fun calculateNewPage(currentPage: Int, pages: Collection<Int>): Int?
|
abstract fun calculateNewPage(currentPage: Int, pages: Collection<Int>): Int?
|
||||||
|
|
||||||
object InventoryGUIPreviousPageCalculator : InventoryGUIPageChangeCalculator() {
|
object InventoryGUIPreviousPageCalculator : InventoryGUIPageChangeCalculator() {
|
||||||
override fun calculateNewPage(currentPage: Int, pages: Collection<Int>) = pages.sortedDescending().find { it < currentPage }
|
override fun calculateNewPage(currentPage: Int, pages: Collection<Int>)
|
||||||
|
= pages.sortedDescending().find { it < currentPage }
|
||||||
}
|
}
|
||||||
|
|
||||||
object InventoryGUINextPageCalculator : InventoryGUIPageChangeCalculator() {
|
object InventoryGUINextPageCalculator : InventoryGUIPageChangeCalculator() {
|
||||||
override fun calculateNewPage(currentPage: Int, pages: Collection<Int>) = pages.sorted().find { it > currentPage }
|
override fun calculateNewPage(currentPage: Int, pages: Collection<Int>)
|
||||||
|
= pages.sorted().find { it > currentPage }
|
||||||
}
|
}
|
||||||
|
|
||||||
class InventoryGUIConsistentPageCalculator(private val toPage: Int) : InventoryGUIPageChangeCalculator() {
|
class InventoryGUIConsistentPageCalculator(private val toPage: Int) : InventoryGUIPageChangeCalculator() {
|
||||||
@@ -29,102 +31,98 @@ enum class InventoryGUIPageChangeEffect {
|
|||||||
SWIPE_VERTICALLY,
|
SWIPE_VERTICALLY,
|
||||||
}
|
}
|
||||||
|
|
||||||
class InventoryGUIPageChanger(private val effect: InventoryGUIPageChangeEffect) {
|
internal fun InventoryGUI<*>.changePage(effect: InventoryGUIPageChangeEffect, fromPage: InventoryGUIPage<*>?, toPage: InventoryGUIPage<*>?) {
|
||||||
|
|
||||||
fun changePage(gui: InventoryGUI<*>, fromPage: Int, toPage: Int) {
|
val fromPageInt = fromPage?.number ?: 0
|
||||||
when (effect) {
|
val toPageInt = toPage?.number ?: 0
|
||||||
|
|
||||||
InventoryGUIPageChangeEffect.INSTANT -> gui.loadPage(toPage)
|
when (effect) {
|
||||||
|
|
||||||
InventoryGUIPageChangeEffect.SLIDE_HORIZONTALLY -> {
|
InventoryGUIPageChangeEffect.INSTANT -> loadPageUnsafe(toPage)
|
||||||
|
|
||||||
val width = gui.data.inventoryType.dimensions.width
|
InventoryGUIPageChangeEffect.SLIDE_HORIZONTALLY -> {
|
||||||
|
|
||||||
changePageEffect(gui.data.plugin, fromPage, toPage, width) { currentOffset, ifInverted ->
|
val width = data.inventoryType.dimensions.width
|
||||||
if (ifInverted) {
|
|
||||||
gui.loadPage(fromPage, offsetHorizontally = currentOffset)
|
changePageEffect(data.plugin, fromPageInt, toPageInt, width) { currentOffset, ifInverted ->
|
||||||
gui.loadPage(toPage, offsetHorizontally = -(width - currentOffset))
|
if (ifInverted) {
|
||||||
} else {
|
loadPageUnsafe(fromPage, offsetHorizontally = currentOffset)
|
||||||
gui.loadPage(fromPage, offsetHorizontally = -currentOffset)
|
loadPageUnsafe(toPage, offsetHorizontally = -(width - currentOffset))
|
||||||
gui.loadPage(toPage, offsetHorizontally = width - currentOffset)
|
} else {
|
||||||
}
|
loadPageUnsafe(fromPage, offsetHorizontally = -currentOffset)
|
||||||
|
loadPageUnsafe(toPage, offsetHorizontally = width - currentOffset)
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
InventoryGUIPageChangeEffect.SLIDE_VERTICALLY -> {
|
|
||||||
|
|
||||||
val height = gui.data.inventoryType.dimensions.heigth
|
|
||||||
|
|
||||||
changePageEffect(gui.data.plugin, fromPage, toPage, height) { currentOffset, ifInverted ->
|
|
||||||
if (ifInverted) {
|
|
||||||
gui.loadPage(fromPage, offsetVertically = currentOffset)
|
|
||||||
gui.loadPage(toPage, offsetVertically = -(height - currentOffset))
|
|
||||||
} else {
|
|
||||||
gui.loadPage(fromPage, offsetVertically = -currentOffset)
|
|
||||||
gui.loadPage(toPage, offsetVertically = height - currentOffset)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
InventoryGUIPageChangeEffect.SWIPE_HORIZONTALLY -> {
|
|
||||||
|
|
||||||
val width = gui.data.inventoryType.dimensions.width
|
|
||||||
|
|
||||||
changePageEffect(gui.data.plugin, fromPage, toPage, width) { currentOffset, ifInverted ->
|
|
||||||
if (ifInverted) {
|
|
||||||
gui.loadPage(toPage, offsetHorizontally = -(width - currentOffset))
|
|
||||||
} else {
|
|
||||||
gui.loadPage(toPage, offsetHorizontally = width - currentOffset)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
InventoryGUIPageChangeEffect.SWIPE_VERTICALLY -> {
|
|
||||||
|
|
||||||
val height = gui.data.inventoryType.dimensions.heigth
|
|
||||||
|
|
||||||
changePageEffect(gui.data.plugin, fromPage, toPage, height) { currentOffset, ifInverted ->
|
|
||||||
if (ifInverted) {
|
|
||||||
gui.loadPage(toPage, offsetVertically = -(height - currentOffset))
|
|
||||||
} else {
|
|
||||||
gui.loadPage(toPage, offsetVertically = height - currentOffset)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
InventoryGUIPageChangeEffect.SLIDE_VERTICALLY -> {
|
||||||
|
|
||||||
|
val height = data.inventoryType.dimensions.heigth
|
||||||
|
|
||||||
|
changePageEffect(data.plugin, fromPageInt, toPageInt, height) { currentOffset, ifInverted ->
|
||||||
|
if (ifInverted) {
|
||||||
|
loadPageUnsafe(fromPage, offsetVertically = currentOffset)
|
||||||
|
loadPageUnsafe(toPage, offsetVertically = -(height - currentOffset))
|
||||||
|
} else {
|
||||||
|
loadPageUnsafe(fromPage, offsetVertically = -currentOffset)
|
||||||
|
loadPageUnsafe(toPage, offsetVertically = height - currentOffset)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
InventoryGUIPageChangeEffect.SWIPE_HORIZONTALLY -> {
|
||||||
|
|
||||||
|
val width = data.inventoryType.dimensions.width
|
||||||
|
|
||||||
|
changePageEffect(data.plugin, fromPageInt, toPageInt, width) { currentOffset, ifInverted ->
|
||||||
|
if (ifInverted) {
|
||||||
|
loadPageUnsafe(toPage, offsetHorizontally = -(width - currentOffset))
|
||||||
|
} else {
|
||||||
|
loadPageUnsafe(toPage, offsetHorizontally = width - currentOffset)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
InventoryGUIPageChangeEffect.SWIPE_VERTICALLY -> {
|
||||||
|
|
||||||
|
val height = data.inventoryType.dimensions.heigth
|
||||||
|
|
||||||
|
changePageEffect(data.plugin, fromPageInt, toPageInt, height) { currentOffset, ifInverted ->
|
||||||
|
if (ifInverted) {
|
||||||
|
loadPageUnsafe(toPage, offsetVertically = -(height - currentOffset))
|
||||||
|
} else {
|
||||||
|
loadPageUnsafe(toPage, offsetVertically = height - currentOffset)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
companion object {
|
private inline fun changePageEffect(
|
||||||
|
kSpigot: KSpigot,
|
||||||
|
fromPage: Int,
|
||||||
|
toPage: Int,
|
||||||
|
doFor: Int,
|
||||||
|
crossinline effect: (currentOffset: Int, ifInverted: Boolean) -> Unit,
|
||||||
|
) {
|
||||||
|
|
||||||
private inline fun changePageEffect(
|
val ifInverted = fromPage >= toPage
|
||||||
kSpigot: KSpigot,
|
|
||||||
fromPage: Int,
|
|
||||||
toPage: Int,
|
|
||||||
doFor: Int,
|
|
||||||
crossinline effect: (currentOffset: Int, ifInverted: Boolean) -> Unit,
|
|
||||||
) {
|
|
||||||
|
|
||||||
val ifInverted = fromPage >= toPage
|
var currentOffset = 1
|
||||||
|
kSpigot.task(
|
||||||
|
sync = true,
|
||||||
|
period = 1,
|
||||||
|
howOften = doFor.toLong()
|
||||||
|
) {
|
||||||
|
|
||||||
var currentOffset = 1
|
effect.invoke(currentOffset, ifInverted)
|
||||||
kSpigot.task(
|
|
||||||
sync = true,
|
|
||||||
period = 1,
|
|
||||||
howOften = doFor.toLong()
|
|
||||||
) {
|
|
||||||
|
|
||||||
effect.invoke(currentOffset, ifInverted)
|
currentOffset++
|
||||||
|
|
||||||
currentOffset++
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user