Skip to content

Commit

Permalink
add features to nickname (#9)
Browse files Browse the repository at this point in the history
  • Loading branch information
Boy0000 authored Jul 21, 2022
1 parent 48ff420 commit ddb2a6f
Show file tree
Hide file tree
Showing 12 changed files with 253 additions and 73 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import com.mineinabyss.idofront.commands.arguments.stringArg
import com.mineinabyss.idofront.commands.execution.IdofrontCommandExecutor
import com.mineinabyss.idofront.commands.extensions.actions.ensureSenderIsPlayer
import com.mineinabyss.idofront.messaging.miniMsg
import org.bukkit.Bukkit
import org.bukkit.command.Command
import org.bukkit.command.CommandSender
import org.bukkit.command.TabCompleter
Expand Down Expand Up @@ -44,13 +45,56 @@ class ChattyCommands : IdofrontCommandExecutor(), TabCompleter {
}
}
"nickname" {
val nickname by stringArg()
ensureSenderIsPlayer()
action {
val player = sender as? Player ?: return@action
if (nickname.isEmpty()) player.displayName(player.name.miniMsg())
else player.displayName(arguments.joinToString().replace(", ", " ").miniMsg())
player.sendFormattedMessage(chattyMessages.other.nickNameChanged)
val nickMessage = chattyMessages.nicknames
val nickConfig = chattyConfig.nicknames
val nick = arguments.joinToString(" ")
val player = sender as? Player
val bypassFormatPerm = player?.hasPermission(nickConfig.bypassFormatPermission) == true

when {
player is Player && !player.hasPermission(nickConfig.permission) ->
player.sendFormattedMessage(nickMessage.selfDenied)
arguments.isEmpty() -> {
// Removes players displayname or sends error if sender is console
player?.displayName(player.name.miniMsg())
player?.sendFormattedMessage(nickMessage.selfEmpty)
?: sender.sendConsoleMessage(nickMessage.consoleNicknameSelf)
}
arguments.first().startsWith(nickConfig.nickNameOtherPrefix) -> {
val otherPlayer = arguments.getPlayerToNick()
val otherNick = nick.removePlayerToNickFromString()

when {
player?.hasPermission(nickConfig.nickOtherPermission) == false ->
player.sendFormattedMessage(nickMessage.otherDenied, otherPlayer)
!Bukkit.getOnlinePlayers().contains(otherPlayer) ->
player?.sendFormattedMessage(nickMessage.invalidPlayer, otherPlayer)
otherNick.isEmpty() -> {
otherPlayer?.displayName(otherPlayer.name.miniMsg())
player?.sendFormattedMessage(nickMessage.otherEmpty, otherPlayer)
}
!bypassFormatPerm && !otherNick.verifyNickStyling() ->
player?.sendFormattedMessage(nickMessage.disallowedStyling)
!bypassFormatPerm && !otherNick.verifyNickLength() ->
player?.sendFormattedMessage(nickMessage.tooLong)
otherNick.isNotEmpty() -> {
otherPlayer?.displayName(otherNick.miniMsg())
player?.sendFormattedMessage(nickMessage.otherSuccess, otherPlayer)
}
}
}
else -> {
if (!bypassFormatPerm && !nick.verifyNickStyling()) {
player?.sendFormattedMessage(nickMessage.disallowedStyling)
} else if (!bypassFormatPerm && !nick.verifyNickLength()) {
player?.sendFormattedMessage(nickMessage.tooLong)
} else {
player?.displayName(nick.miniMsg())
player?.sendFormattedMessage(nickMessage.selfSuccess)
}
}
}
}
}
"reload" {
Expand All @@ -59,15 +103,15 @@ class ChattyCommands : IdofrontCommandExecutor(), TabCompleter {
ChattyConfig.reload()
ChattyConfig.load()
(sender as? Player)?.sendFormattedMessage(chattyMessages.other.configReloaded)
?: sender.sendMessage(chattyMessages.other.configReloaded.miniMsg())
?: sender.sendConsoleMessage(chattyMessages.other.configReloaded)
}
}
"messages" {
action {
ChattyMessages.reload()
ChattyMessages.load()
(sender as? Player)?.sendFormattedMessage(chattyMessages.other.messagesReloaded)
?: sender.sendMessage(chattyMessages.other.messagesReloaded.miniMsg())
?: sender.sendConsoleMessage(chattyMessages.other.messagesReloaded)
}
}

Expand Down Expand Up @@ -104,7 +148,11 @@ class ChattyCommands : IdofrontCommandExecutor(), TabCompleter {
return if (command.name == "chatty") {
when (args.size) {
1 -> listOf("ping", "reload", "channels", "nickname")
2 -> if (args[0] == "ping") listOf("toggle", "sound") else emptyList()
2 -> when (args[0]) {
"ping" -> listOf("toggle", "sound")
"reload" -> listOf("config", "messages")
else -> emptyList()
}
3 ->
if (args[0] == "ping" && args[1] == "sound") getAlternativePingSounds
else emptyList()
Expand Down
32 changes: 21 additions & 11 deletions chatty-paper/src/main/kotlin/com/mineinabyss/chatty/ChattyConfig.kt
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.mineinabyss.chatty

import com.mineinabyss.chatty.components.ChannelType
import com.mineinabyss.chatty.helpers.ChattyTags
import com.mineinabyss.idofront.config.IdofrontConfig
import kotlinx.serialization.Serializable

Expand All @@ -9,30 +10,39 @@ object ChattyConfig : IdofrontConfig<ChattyConfig.Data>(chattyPlugin, Data.seria
data class Data(
val useChattyCommandPrefix: Boolean = true,
val playerHeadFont: String = "minecraft:chatty_heads",
val ping: Ping,
val join: Join,
val leave: Leave,
val proxy: Proxy,
val channels: Map<String, ChattyChannel>,
val nicknames: Nickname = Nickname(),
val ping: Ping = Ping(),
val join: Join = Join(),
val leave: Leave = Leave(),
val proxy: Proxy = Proxy(),
val channels: Map<String, ChattyChannel> = mutableMapOf("global" to ChattyChannel(ChannelType.GLOBAL)),
)

@Serializable
data class Nickname(
val permission: String = "chatty.nickname",
val nickOtherPermission: String = "chatty.nickname.other",
val bypassFormatPermission: String = "chatty.nickname.bypassformat",
val maxLength: Int = 32,
val countColorsInLength: Boolean = false,
val nickNameOtherPrefix: Char = '@',
val allowedTags: List<ChattyTags> = emptyList()
)

@Serializable
data class Join(
val enabled: Boolean = true,
val sendAcrossProxy: Boolean = true,
val firstJoin: FirstJoin,
val firstJoin: FirstJoin = FirstJoin(),
)

@Serializable
data class FirstJoin(
val enabled: Boolean = true,
val sendAcrossProxy: Boolean = true,
)

@Serializable
data class Leave(
val enabled: Boolean,
val sendAcrossProxy: Boolean = true,
val enabled: Boolean = true,
)

@Serializable
Expand All @@ -47,7 +57,7 @@ object ChattyConfig : IdofrontConfig<ChattyConfig.Data>(chattyPlugin, Data.seria
val proxy: Boolean = false,
val discordsrv: Boolean = true,
val isDefaultChannel: Boolean = false,
val format: Format,
val format: Format = Format(),
val channelRadius: Int = 0,
val channelAliases: List<String> = listOf(),
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,28 @@ object ChattyMessages : IdofrontConfig<ChattyMessages.Messages>(chattyPlugin, Me

@Serializable
data class Messages(
val nicknames: Nicknames,
val ping: Pings,
val channels: Channels,
val proxies: Proxies,
val joinLeave: JoinLeave,
val other: Other
)

@Serializable
data class Nicknames(
val selfSuccess: String = "<green>You changed your nickname to <i>%player_displayname%</i>!",
val selfDenied: String = "<red>You can't change your nickname!",
val selfEmpty: String = "<yellow>Removed nickname!",
val otherSuccess: String = "<green>You changed %player_name%'s nickname to <i>%player_displayname%</i>!",
val otherDenied: String = "<red>You can't change %player_name%'s nickname!",
val otherEmpty: String = "<yellow>Removed nickname for %player_name%!",
val invalidPlayer: String = "<red>That player doesn't exist!",
val consoleNicknameSelf: String = "<red>Sadly console cannot have cool nickname :(",
val disallowedStyling: String = "<red>This nickname contains formatting that are not allowed!",
val tooLong: String = "<red>The nickname was too long!",
)

@Serializable
data class Pings(
val toggledPingSound: String = "Ping sound is now <i>%chatty_player_ping_toggle%</i>.",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ class ChattyPlugin : JavaPlugin() {
server.messenger.registerIncomingPluginChannel(this, chattyProxyChannel, ChattyProxyListener())
server.messenger.registerOutgoingPluginChannel(this, chattyProxyChannel)

DiscordSRV.api.subscribe(DiscordListener())
if (Bukkit.getPluginManager().getPlugin("DiscordSRV") != null) DiscordSRV.api.subscribe(DiscordListener())

gearyAddon {
autoscan("com.mineinabyss") {
Expand All @@ -59,7 +59,7 @@ class ChattyPlugin : JavaPlugin() {
}

override fun onDisable() {
DiscordSRV.api.unsubscribe(DiscordListener())
if (Bukkit.getPluginManager().getPlugin("DiscordSRV") != null) DiscordSRV.api.unsubscribe(DiscordListener())
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
package com.mineinabyss.chatty.helpers

import com.destroystokyo.paper.ClientOption
import com.mineinabyss.chatty.ChattyConfig
import com.mineinabyss.chatty.components.ChannelType
import com.mineinabyss.chatty.components.playerData
import com.mineinabyss.idofront.font.Space
Expand All @@ -13,18 +12,29 @@ import net.kyori.adventure.text.Component
import net.kyori.adventure.text.TextReplacementConfig
import net.kyori.adventure.text.format.TextColor
import net.kyori.adventure.text.minimessage.MiniMessage
import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer
import org.bukkit.Bukkit
import org.bukkit.ChatColor
import org.bukkit.Sound
import org.bukkit.command.CommandSender
import org.bukkit.entity.Player
import java.awt.Color
import javax.imageio.ImageIO

val ping = chattyConfig.ping
val getAlternativePingSounds: List<String> =
if ("*" in ping.alternativePingSounds || "all" in ping.alternativePingSounds)
Sound.values().map { it.key.toString() }.toList() else ping.alternativePingSounds

val getPingEnabledChannels: List<String> =
if ("*" in ping.enabledChannels || "all" in ping.enabledChannels) getAllChannelNames() else ping.enabledChannels

fun String.checkForPlayerPings(channelId: String): Player? {
val ping = chattyConfig.ping
if (channelId !in getPingEnabledChannels || ping.pingPrefix == "" || ping.pingPrefix !in this) return null
if (channelId !in getPingEnabledChannels || ping.pingPrefix.isEmpty() || ping.pingPrefix !in this) return null
val pingedName = this.substringAfter(ping.pingPrefix).split(" ")[0]
return Bukkit.getOnlinePlayers().firstOrNull {
it.name == pingedName || it.displayName().deserialize() == pingedName
it.name == pingedName || it.displayName().serialize() == pingedName
}
}

Expand Down Expand Up @@ -56,27 +66,21 @@ fun Component.handlePlayerPings(player: Player, pingedPlayer: Player) {
player.sendMessage(pingerMessage)
}

fun getGlobalChat(): Map.Entry<String, ChattyConfig.ChattyChannel>? {
return chattyConfig.channels.entries.firstOrNull { it.value.channelType == ChannelType.GLOBAL }
}
fun getGlobalChat() =
chattyConfig.channels.entries.firstOrNull { it.value.channelType == ChannelType.GLOBAL }

fun getDefaultChat(): Map.Entry<String, ChattyConfig.ChattyChannel> {
return chattyConfig.channels.entries.firstOrNull { it.value.isDefaultChannel }
fun getDefaultChat() =
chattyConfig.channels.entries.firstOrNull { it.value.isDefaultChannel }
?: getGlobalChat()
?: throw IllegalStateException("No Default or Global channel found")
}

fun getChannelFromId(channelId: String) : ChattyConfig.ChattyChannel? {
return chattyConfig.channels.entries.firstOrNull { it.key == channelId }?.value
}
fun getChannelFromId(channelId: String) =
chattyConfig.channels.entries.firstOrNull { it.key == channelId }?.value

fun Player.getChannelFromPlayer() : ChattyConfig.ChattyChannel? {
return chattyConfig.channels.entries.firstOrNull { it.key == this.playerData.channelId }?.value
}
fun Player.getChannelFromPlayer() =
chattyConfig.channels.entries.firstOrNull { it.key == this.playerData.channelId }?.value

fun Player.channelIsProxyEnabled() : Boolean {
return getChannelFromPlayer()?.proxy ?: false
}
fun Player.channelIsProxyEnabled() = getChannelFromPlayer()?.proxy ?: false

fun Player.verifyPlayerChannel() {
if (playerData.channelId !in chattyConfig.channels)
Expand All @@ -95,7 +99,7 @@ fun translatePlaceholders(player: Player, message: String): Component {
.match("%chatty_playerhead%")
.replacement(player.translatePlayerHeadComponent()).build()
)
return PlaceholderAPI.setPlaceholders(player, msg.deserialize()).miniMsg()
return PlaceholderAPI.setPlaceholders(player, msg.serialize()).serializeLegacy()
}

//TODO Convert to using BLHE
Expand Down Expand Up @@ -157,21 +161,49 @@ fun setAudienceForChannelType(player: Player): Set<Audience> {
}
return audiences
}
val ping = chattyConfig.ping
val getAlternativePingSounds: List<String> =
if ("*" in ping.alternativePingSounds || "all" in ping.alternativePingSounds)
Sound.values().map { it.key.toString() }.toList() else ping.alternativePingSounds

val getPingEnabledChannels: List<String> =
if ("*" in ping.enabledChannels || "all" in ping.enabledChannels) getAllChannelNames() else ping.enabledChannels


fun Component.deserialize(): String {
return MiniMessage.builder().build().serialize(this)
fun String.serializeLegacy() = LegacyComponentSerializer.legacy('§').deserialize(this).fixLegacy()

fun Component.fixLegacy() : Component =
this.serialize().replace("\\<", "<").replace("\\>", ">").miniMsg()

fun Component.serialize() = MiniMessage.builder().build().serialize(this)

fun Component.stripTags() = MiniMessage.builder().build().stripTags(this.serialize())

fun String.getTags(): List<ChattyTags> {
val tags = mutableListOf<ChattyTags>()
if (" " in this) tags.add(ChattyTags.SPACES)
MiniMessage.builder().build().deserializeToTree(this).toString()
.split("TagNode(",") {").filter { "Node" !in it && it.isNotBlank() }.toList().forEach {
val tag = it.replace("'", "").replace(",", "")
when {
tag in ChatColor.values().toString().lowercase() -> tags.add(ChattyTags.TEXTCOLOR)
tag.startsWith("gradient") -> tags.add(ChattyTags.GRADIENT)
tag.startsWith("#") -> tags.add(ChattyTags.HEXCOLOR)
tag.startsWith("i") || tag.startsWith("italic") -> tags.add(ChattyTags.ITALIC)
tag.startsWith("b") || tag.startsWith("bold") -> tags.add(ChattyTags.BOLD)
tag.startsWith("u") || tag.startsWith("underline") -> tags.add(ChattyTags.UNDERLINE)
tag.startsWith("st") || tag.startsWith("strikethrough") -> tags.add(ChattyTags.STRIKETHROUGH)
tag.startsWith("obf") || tag.startsWith("obfuscated") -> tags.add(ChattyTags.OBFUSCATED)
tag.startsWith("click") -> tags.add(ChattyTags.CLICK)
tag.startsWith("hover") -> tags.add(ChattyTags.HOVER)
tag.startsWith("insert") -> tags.add(ChattyTags.INSERTION)
tag.startsWith("rainbow") -> tags.add(ChattyTags.RAINBOW)
tag.startsWith("transition") -> tags.add(ChattyTags.TRANSITION)
tag.startsWith("reset") -> tags.add(ChattyTags.RESET)
tag.startsWith("font") -> tags.add(ChattyTags.FONT)
tag.startsWith("key") -> tags.add(ChattyTags.KEYBIND)
tag.startsWith("lang") -> tags.add(ChattyTags.TRANSLATABLE)
}
}
return tags.toList()
}

fun Component.stripTags(): String {
return MiniMessage.builder().build().stripTags(this.deserialize())
}
fun Player.sendFormattedMessage(message: String) =
this.sendMessage(translatePlaceholders(this, message).serialize().miniMsg())

fun Player.sendFormattedMessage(message: String, optionalPlayer: Player? = null) =
this.sendMessage(translatePlaceholders((optionalPlayer ?: this), message))

fun Player.sendFormattedMessage(message: String) = this.sendMessage(translatePlaceholders(this, message))
fun CommandSender.sendConsoleMessage(message: String) = this.sendMessage(message.miniMsg())
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package com.mineinabyss.chatty.helpers

import com.mineinabyss.idofront.messaging.miniMsg
import org.bukkit.Bukkit
import org.bukkit.entity.Player

fun String.verifyNickLength(): Boolean {
return when (chattyConfig.nicknames.countColorsInLength) {
true -> this.length <= chattyConfig.nicknames.maxLength
false -> this.miniMsg().stripTags().length <= chattyConfig.nicknames.maxLength
}
}

// Splits <color> and <gradient:...> tags and checks if theyre allowed
fun String.verifyNickStyling(): Boolean {
return this.getTags().all { tag -> tag in chattyConfig.nicknames.allowedTags }
}

fun List<String>.getPlayerToNick(): Player? = Bukkit.getPlayer(
this.first().replace(chattyConfig.nicknames.nickNameOtherPrefix.toString(), "")
)

fun String.removePlayerToNickFromString(): String =
this.split(" ").filter { it != this.split(" ").first() }.joinToString(" ")
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ fun chattyPlaceholders(player: Player, string: String) : Map<String, String> {
"player_ping_sound" to data.pingSound.toString(),
"player_ping_toggle" to (!data.disablePingSound).toString(),

"player_head" to player.translatePlayerHeadComponent().deserialize(),
"player_head" to player.translatePlayerHeadComponent().serialize(),
"shift_$shift" to shift.toString()
)
}
Loading

0 comments on commit ddb2a6f

Please sign in to comment.