@@ -283,7 +283,7 @@ public class InterfacesListeners private constructor(private val plugin: Plugin)
283
283
saveInventoryContentsIfOpened(event.player)
284
284
285
285
val holder = event.inventory.getHolder(false )
286
- val view = convertHolderToInterfaceView(holder) ? : return
286
+ val view = convertHolderToInterfaceView(holder)
287
287
288
288
// Close the previous view first with open new as the reason, unless we
289
289
// are currently opening this view!
@@ -309,17 +309,19 @@ public class InterfacesListeners private constructor(private val plugin: Plugin)
309
309
}
310
310
}
311
311
312
- // Set the new open inventory
313
- openInventory[event.player] = view
314
-
315
- // If there is an open view left, destroy it as something went wrong!
316
- withoutReopen {
317
- openPlayerInterfaceViews.remove( event.player.uniqueId)?.markClosed( SCOPE , Reason . OPEN_NEW )
312
+ // If the view is not owned by interfaces, deal with that properly!
313
+ if (view == null ) {
314
+ openInventory - = event.player
315
+ } else {
316
+ // Set the new open inventory
317
+ openInventory[ event.player] = view
318
318
}
319
319
320
320
// Abort any previous query the player had
321
321
abortQuery(event.player.uniqueId, null )
322
- view.onOpen()
322
+
323
+ // Handle opening the new view
324
+ view?.onOpen()
323
325
}
324
326
325
327
@EventHandler
@@ -344,16 +346,23 @@ public class InterfacesListeners private constructor(private val plugin: Plugin)
344
346
if (opened != null ) {
345
347
opened.markClosed(SCOPE , reason)
346
348
} else if (reason in REOPEN_REASONS && ! event.player.isDead) {
347
- // If the opened menu didn't trigger a re-open, do it manually!
349
+ // If the opened menu didn't trigger a re-open, do it manually! This is necessary if it wasn't
350
+ // an interfaces inventory but instead a crafting table, furnace, horse, etc.
348
351
reopenInventory(event.player as Player )
349
352
}
350
353
}
351
354
352
355
@EventHandler(priority = EventPriority .LOW , ignoreCancelled = true )
353
356
public fun onClick (event : InventoryClickEvent ) {
354
- val holder = event.inventory.getHolder(false )
355
- val view = convertHolderToInterfaceView(holder) ? : return
356
- val clickedPoint = view.backing.mapper.toGridPoint(event.rawSlot) ? : return
357
+ // Try to get the view of the top inventory first but fall back to the clicked inventory in specific
358
+ val mainView = convertHolderToInterfaceView(event.inventory.getHolder(false ))
359
+ val view = mainView ? : convertHolderToInterfaceView(
360
+ (event.clickedInventory ? : event.inventory).getHolder(false ),
361
+ ) ? : return
362
+
363
+ // If we are using a fallback player view we need to adjust the raw slot to include the 9 regular player inventory top slots
364
+ val clickedPoint =
365
+ view.backing.mapper.toGridPoint(if (mainView == null ) (event.rawSlot - event.inventory.size + 9 ) else event.rawSlot) ? : return
357
366
val isPlayerInventory = (event.clickedInventory ? : event.inventory).getHolder(false ) is Player
358
367
359
368
// Run base click handling
@@ -396,7 +405,7 @@ public class InterfacesListeners private constructor(private val plugin: Plugin)
396
405
val bottomInventory = event.view.bottomInventory
397
406
if (event.click == ClickType .DOUBLE_CLICK ) {
398
407
val clickedItem = event.cursor
399
- val isInPlayerInventory = holder is Player
408
+ val isInPlayerInventory = event.inventory.getHolder( false ) is Player
400
409
401
410
// Don't check top inventory if we're in the player inventory!
402
411
if (
@@ -666,14 +675,6 @@ public class InterfacesListeners private constructor(private val plugin: Plugin)
666
675
event.isCancelled = true
667
676
}
668
677
669
- /* * Extracts the clicked point from an inventory click event. */
670
- private fun clickedPoint (view : AbstractInterfaceView <* , * , * >, event : InventoryClickEvent ): GridPoint ? {
671
- if (event.inventory.getHolder(false ) is Player ) {
672
- return GridPoint .fromBukkitPlayerSlot(event.slot)?.let { view.backing.relativizePlayerInventorySlot(it) }
673
- }
674
- return GridPoint .fromBukkitChestSlot(event.rawSlot)
675
- }
676
-
677
678
/* *
678
679
* Converts an inventory holder to an [AbstractInterfaceView] if possible. If the holder is a player
679
680
* their currently open player interface is returned.
@@ -684,8 +685,9 @@ public class InterfacesListeners private constructor(private val plugin: Plugin)
684
685
// If it's an abstract view use that one
685
686
if (holder is AbstractInterfaceView <* , * , * >) return holder
686
687
687
- // If it's the player's own inventory use the held one
688
- if (holder is HumanEntity ) return getOpenPlayerInterface(holder.uniqueId)
688
+ // If it's the player's own inventory use the held one, it might be the background one if
689
+ // this is the bottom of a combined inventory
690
+ if (holder is HumanEntity ) return getOpenPlayerInterface(holder.uniqueId) ? : getBackgroundPlayerInterface(holder.uniqueId)
689
691
690
692
return null
691
693
}
0 commit comments