Skip to content

Commit

Permalink
Show a larger view if player has many unique cards, and support dropp…
Browse files Browse the repository at this point in the history
…ing multiple cards
  • Loading branch information
4Ply committed Aug 10, 2024
1 parent 7a031f3 commit d121507
Show file tree
Hide file tree
Showing 6 changed files with 87 additions and 34 deletions.
3 changes: 3 additions & 0 deletions src/main/kotlin/org/trackedout/citadel/Citadel.kt
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import org.trackedout.citadel.commands.ListScoresCommand
import org.trackedout.citadel.commands.LogEventCommand
import org.trackedout.citadel.commands.ManageDeckCommand
import org.trackedout.citadel.commands.SavePlayerDeckCommand
import org.trackedout.citadel.commands.ShutdownDungeonsCommand
import org.trackedout.citadel.commands.StatusCommand
import org.trackedout.citadel.commands.TakeShulkerCommand
import org.trackedout.citadel.inventory.AddACardView
Expand Down Expand Up @@ -102,6 +103,8 @@ class Citadel : JavaPlugin() {
manager.registerCommand(SavePlayerDeckCommand(inventoryApi))
manager.registerCommand(StatusCommand())
manager.registerCommand(ListScoresCommand(this, scoreApi))
manager.registerCommand(ShutdownDungeonsCommand(this, eventsApi))

manager.setDefaultExceptionHandler { _, _, sender, _, throwable ->
sender.sendMessage("Error executing command: ${throwable.message}")

Expand Down
19 changes: 13 additions & 6 deletions src/main/kotlin/org/trackedout/citadel/PlayerExtensions.kt
Original file line number Diff line number Diff line change
Expand Up @@ -54,15 +54,22 @@ fun ItemStack.withTags(tags: Map<String, String>): ItemStack {
fun ItemStack.preventRemoval(): Boolean = RtagItem(this).get<String>("prevent-removal") == "1"

fun ItemStack.isDeckedOutCard(): Boolean {
val text = this.itemMeta?.displayName() as TextComponent?
val name = text?.content()
return Cards.findCard(name ?: "") !== null
if (this.itemMeta?.displayName() is TextComponent?) {
val text = this.itemMeta?.displayName() as TextComponent?
val name = text?.content()
return Cards.findCard(name ?: "") !== null
}

return false
}

fun ItemStack.getCard(): Cards.Companion.Card? {
val text = this.itemMeta.displayName() as TextComponent
val name = text.content()
return Cards.findCard(name)
if (this.itemMeta?.displayName() is TextComponent?) {
val text = this.itemMeta?.displayName() as TextComponent?
return text?.content()?.let { Cards.findCard(it) }
}

return null
}

fun ItemStack.name(): String? {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package org.trackedout.citadel.commands

import co.aikar.commands.BaseCommand
import co.aikar.commands.annotation.CommandAlias
import co.aikar.commands.annotation.CommandPermission
import co.aikar.commands.annotation.Description
import co.aikar.commands.annotation.Subcommand
import org.bukkit.command.CommandSender
import org.trackedout.citadel.Citadel
import org.trackedout.citadel.async
import org.trackedout.client.apis.EventsApi
import org.trackedout.client.models.Event

@CommandAlias("decked-out|do")
class ShutdownDungeonsCommand(
private val plugin: Citadel,
private val eventsApi: EventsApi,
) : BaseCommand() {
@Subcommand("shutdown-all-empty-dungeons")
@CommandPermission("decked-out.inventory.admin")
@Description("Shutdown all empty dungeons")
fun shutdownEmptyDungeons(source: CommandSender) {
plugin.async(source) {
eventsApi.eventsPost(
Event(
name = "shutdown-all-empty-dungeons",
server = plugin.serverName,
count = 1,
x = 0.0,
y = 0.0,
z = 0.0,
)
)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import org.trackedout.citadel.getCard
import org.trackedout.citadel.getDeckId
import org.trackedout.citadel.isDeckedOutCard
import org.trackedout.citadel.preventRemoval
import org.trackedout.client.models.Card
import org.trackedout.data.Cards
import java.util.function.BiConsumer

Expand All @@ -28,11 +29,12 @@ open class DeckInventoryView : DeckManagementView() {
}

override fun onOpen(context: OpenContext) {
val player = context.player
val deckId = deckIdState[context]
val cards = getCards(context, deckId)

context
.modifyConfig()
.title("Hi, ${player.name}! Editing ${playerName[context]}'s Deck")
.size(rowCount())
.size(rowCount(cards))
}

override fun onClose(event: CloseContext) {
Expand All @@ -50,28 +52,26 @@ open class DeckInventoryView : DeckManagementView() {
player.inventory.addItem(item)
}

if (player.itemOnCursor.isDeckedOutCard()) {
player.itemOnCursor.amount = 0
}

// For each card in the player's inventory, hide it from the deck
val cardsToHide = (0 until player.inventory.size).asSequence()
.map(player.inventory::getItem)
.filter { it != null && it.isDeckedOutCard() && it.getDeckId() == deckId }
.map { it!!.getCard()!! to it.amount }
// Count the total number of cards in the player's inventory across all stacks
.map { it!!.getCard()!! to player.inventory.filter { p -> p?.getCard()?.name == it.getCard()?.name }.sumOf { p -> p.amount } }
.onEach { pair: Pair<Cards.Companion.Card, Int> ->
val card = pair.first
val amount = pair.second
println("Player's inventory contains ${amount}x${card.name} - hiding it from Deck $deckId")
}
.associate {
// val card = Card(
// player = player.name,
// name = it.first.key,
// deckType = deckId.shortRunType(),
// server = plugin[event].serverName,
// )
it.first.key to it.second
}

println("Updating deck visibility for Deck ID #${deckId}, hiding: ${cardsToHide.map { "${it.value}x${it.key.uppercase()}" }}")

updateCardVisibilityFunc[event].accept(deckId, cardsToHide)
}

Expand All @@ -80,7 +80,7 @@ open class DeckInventoryView : DeckManagementView() {
val cards = getCards(render, deckId)

if (showBackButton()) {
render.slot(rowCount(), 1)
render.slot(rowCount(cards), 1)
.cancelOnClick()
.withItem(namedItem(Material.GOLD_INGOT, "Go back"))
.onClick { _: StateValueHost? ->
Expand All @@ -89,7 +89,7 @@ open class DeckInventoryView : DeckManagementView() {
}

if (deckId.shortRunType() == "p") {
render.slot(rowCount(), 9)
render.slot(rowCount(cards), 9)
.cancelOnClick()
.withItem(namedItem(Material.SLIME_BLOCK, "Add a card"))
.onClick { _: StateValueHost? -> render.openForPlayer(AddACardView::class.java, getContext(render)) }
Expand Down Expand Up @@ -133,7 +133,14 @@ open class DeckInventoryView : DeckManagementView() {
return true
}

private fun rowCount() = if (showBackButton()) 6 else 3
private fun rowCount(cards: List<Card>): Int {
val uniqueCardCount = cards.distinctBy { it.name }.size
return if (uniqueCardCount > 25 || showBackButton()) {
6
} else {
3
}
}
}

class DeckInventoryViewWithoutBack : DeckInventoryView() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package org.trackedout.citadel.inventory

import me.devnatan.inventoryframework.View
import me.devnatan.inventoryframework.ViewConfigBuilder
import me.devnatan.inventoryframework.context.Context
import me.devnatan.inventoryframework.context.RenderContext
import me.devnatan.inventoryframework.state.State
import me.devnatan.inventoryframework.state.StateValueHost
Expand Down Expand Up @@ -129,7 +130,7 @@ open class DeckManagementView : View() {
return itemStack.withTags(mapOf("prevent-removal" to "1"))
}

internal fun getCards(render: RenderContext, deckId: DeckId): List<Card> {
internal fun getCards(render: Context, deckId: DeckId): List<Card> {
var cards = deckMap[render][deckId.shortRunType()]
if (cards == null) {
cards = emptyList()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -217,8 +217,8 @@ class EchoShardListener(
val item = event.itemDrop.itemStack
if (isPracticeCard(item)) {
event.isCancelled = true
player.debug("Replacing item drop event with card delete (for practice card)")
deleteCard(player, item)
player.debug("Replacing item drop event with card delete (for ${item.amount}x practice card)")
deleteCard(player, item.clone())
item.amount = 0
} else if (isRestrictedItem(item)) {
player.debug("Blocking item drop event")
Expand Down Expand Up @@ -433,10 +433,6 @@ class EchoShardListener(
if (event.action in actionsToBlockRegardlessOfInventoryType && itemsToCheck.all { isPracticeCard(it) }) {
// Allow players to drop practice cards, but just delete it
player.debug("Allowing click action ${event.action} for practice card")
itemsToCheck.forEach {
player.inventory.removeItemAnySlot(it)
deleteCard(player, it)
}
} else {
player.debug("Blocking click action ${event.action}")
event.isCancelled = true
Expand All @@ -454,14 +450,17 @@ class EchoShardListener(
}

plugin.async(player) {
inventoryApi.inventoryDeleteCardPost(
Card(
player = player.name,
name = card.key,
deckType = deckType,
server = plugin.serverName,
for (i in 1..it.amount) {
println("Deleting ${card.key} (loop iteration ${i})")
inventoryApi.inventoryDeleteCardPost(
Card(
player = player.name,
name = card.key,
deckType = deckType,
server = plugin.serverName,
)
)
)
}
}
}

Expand Down

0 comments on commit d121507

Please sign in to comment.