1
mirror of https://github.com/CarmJos/UserPrefix.git synced 2026-06-04 23:43:29 +08:00
1. 修复低版本可能无法读取物品的bug。
2. 分离配置文件,消息配置文件改为`messages.yml`,前缀配置文件改为`prefixes/*.yml`,便于配置和管理。
3. 允许配置GUI中上一页和下一页的物品。
4. 补全帮助文档,在插件首次加载将提供一份英文版的配置,以便使用。
This commit is contained in:
carm
2021-09-18 13:19:06 +08:00
parent 3a457082b1
commit 9cff1c03dc
23 changed files with 875 additions and 431 deletions
+132 -72
View File
@@ -16,6 +16,8 @@ This plugin is implemented based on Spigot ,**Theoretically** support ALL MineCr
The development of this plugin is based on Chinese which purpose is to help Chinese developers learn Bukkit plugin The development of this plugin is based on Chinese which purpose is to help Chinese developers learn Bukkit plugin
development. development.
This plugin has been published on [SpigotMC](https://www.spigotmc.org/resources/userprefix.96277/) .
本插件已在 [MCBBS](https://www.mcbbs.net/forum.php?mod=viewthread&tid=1261503) 上发布,欢迎中文用户来这里下载。 本插件已在 [MCBBS](https://www.mcbbs.net/forum.php?mod=viewthread&tid=1261503) 上发布,欢迎中文用户来这里下载。
## Examples ## Examples
@@ -52,11 +54,11 @@ For development dependencies, please see [Dependencies](https://github.com/Carm
This plugin theoretically supports all versions. This plugin theoretically supports all versions.
If the icon does not load, the sound cannot be played, etc., If the icon does not load, the sound cannot be played, etc., please check whether the type of the item and sound in the
please check whether the type of the item and sound in the configuration file exists in the current version. configuration file exists in the current version.
Take the SOUND as an example. Take the SOUND as an example. The sound that the villager said "OK" is "`VILLAGER_YES`" in the lower version, but it
The sound that the villager said "OK" is "`VILLAGER_YES`" in the lower version, but it becomes "`ENTITY_VILLAGER_YES`" in the higher version. becomes "`ENTITY_VILLAGER_YES`" in the higher version.
### 2. Scoreboard exception problem ### 2. Scoreboard exception problem
@@ -66,7 +68,8 @@ Please turn of the `functions.OnNamePrefix` in the configuration if there is a c
### 3. Item icon configuration problem ### 3. Item icon configuration problem
Items are read through the ItemStack serialization method provided by Bukkit. For related configuration methods, please refer to [ItemStack Serialization](https://www.spigotmc.org/wiki/itemstack-serialization/). Items are read through the ItemStack serialization method provided by Bukkit. For related configuration methods, please
refer to [ItemStack Serialization](https://www.spigotmc.org/wiki/itemstack-serialization/).
## Commands ## Commands
@@ -98,18 +101,41 @@ type `/papi info UserPrefix` to see all the placeholders.
- Determine whether the player has a certain prefix(true/false) - Determine whether the player has a certain prefix(true/false)
``` ```
## Sample [configuration file](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/config-en.yml) ## Configuration files
Notice: The default configuration is based on Chinese. ### [Plugin Configuration](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/en_US/config.yml) (config.yml)
You can find the [English Version here](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/config-en.yml).
Notice: The default configuration is based on Chinese. You can find
the [English Version here](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/en_US/config.yml).
```yaml ```yaml
version: 1.0.0-SNAPSHOT # DO NOT EDIT IT version: ${project.version} # DO NOT EDIT IT
debug: false #DEBUG OUT PUT debug: false #DEBUG OUT PUT
GUI: GUI:
title: "&f&lMy Prefixes List" # Title of the GUI title: "&f&lMy Prefixes List" # Title of the GUI
items:
next-page: # only show has next page
==: org.bukkit.inventory.ItemStack
type: ARROW
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fNext Page"
lore:
- ""
- "§fRight-Click to the last page"
previous-page: # only show has previous page
==: org.bukkit.inventory.ItemStack
type: ARROW
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fPrevious Page"
lore:
- ""
- "§fRight-Click to the first page"
functions: functions:
# Whether to add a prefix to the top of the head, # Whether to add a prefix to the top of the head,
@@ -121,27 +147,6 @@ functions:
# the prefix with the highest weight will be used automatically # the prefix with the highest weight will be used automatically
autoUsePrefix: true autoUsePrefix: true
messages:
selected:
- "&7You have selected the &f%(name) &7as current prefix."
expired:
- "&7Your prefix &f%(oldName) &7has expired,"
- "&7Now the prefix is changed to &f%(newName) &7."
reload:
- "&a&lReload completed&7costs &f%(time)ms&7."
help:
- "&3&lUserPrefixAdmin &fHelp"
- "&8#/upa&f list"
- "&8- &7Show configured prefixes."
- "&8#/upa&f reload"
- "&8- &7Reload configuration."
list-title:
- "&3&lUserPrefixAdmin &fList"
list-value:
- "&8#%(weight) &f%(identifier)"
- "&8- &7Name &r%(name) &7Perm &r%(permission)"
- "&8- &7Example&r %(content) %(sender_name)"
Sounds: Sounds:
# Format is [SOUND_NAME:Volume:Pitch] or [SOUND_NAME:Volume] or [SOUND_NAME] # Format is [SOUND_NAME:Volume:Pitch] or [SOUND_NAME:Volume] or [SOUND_NAME]
openGUI: "BLOCK_NOTE_BLOCK_PLING:1:1" openGUI: "BLOCK_NOTE_BLOCK_PLING:1:1"
@@ -173,21 +178,71 @@ defaultPrefix:
lore: lore:
- "" - ""
- "§a✔ Selected" - "§a✔ Selected"
```
prefixes: ### [Messages Configuration](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/en_US/messages.yml) (messages.yml)
VIP:
name: "&b&lPro&b" # [Necessary] Name (Using in messages) ```yaml
content: "§b§lPro §b" # [Necessary] What to display before the name selected:
# [Necessary] Weight, used for sorting in the GUI - "&7You have selected the &f%(name) &7as current prefix."
# (the larger is displayed at the back) and the automatic prefix display expired:
weight: 1 - "&7Your prefix &f%(oldName) &7has expired,"
# [Necessary] If there is no permission for detection, everyone can use it, - "&7Now the prefix is changed to &f%(newName) &7."
# which means there is no need to configure "itemNoPermission" reload:
# (because it is impossible to display items without permission at all) - "&a&lReload completed&7costs &f%(time)ms&7."
permission: "yc.pro" help:
itemHasPermission: - "&3&lUserPrefixAdmin &fHelp"
# [Necessary] This Item will be displayed when player has permission - "&8#/upa&f list"
==: org.bukkit.inventory.ItemStack - "&8- &7Show configured prefixes."
- "&8#/upa&f reload"
- "&8- &7Reload configuration."
list-title:
- "&3&lUserPrefixAdmin &fList"
list-value:
- "&8#%(weight) &f%(identifier)"
- "&8- &7Name &r%(name) &7Perm &r%(permission)"
- "&8- &7Example&r %(content) %(sender_name)"
```
### [Prefixes Configuration](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/en_US/example-prefix.yml) (/prefixes/*.yml)
All prefixes are separate configuration files, stored in the `<Data Folder>/prefixes/` for easy management.
Some symbols in file name may affect reading, please avoid using them.
```yaml
# identifier [Necessary]
# This will be used for data-storage.
identifier: "pro"
# Name [Necessary]
# Use in messages.
name: "&b&lPro&b"
# Content [Necessary]
# Use in Placeholders
content: "§b§lPro §b"
# Weight [Necessary]
# used for sorting in the GUI and TabList
# In GUI : the larger is displayed at the back
# At TabList : the larger is displayed at the top
weight: 1
# Permission [Unnecessary]
# If there is no permission for detection, everyone can use it,
# which means there is no need to configure "itemNoPermission"
# (because it is impossible to display items without permission at all)
permission: "yc.vip"
# itemHasPermission [Necessary]
# This Item will be displayed when player has permission
itemHasPermission:
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: org.bukkit.inventory.ItemStack
type: DIAMOND type: DIAMOND
meta: meta:
==: ItemMeta ==: ItemMeta
@@ -196,33 +251,37 @@ prefixes:
lore: lore:
- "" - ""
- "§a➥ Click to use" - "§a➥ Click to use"
itemUsing:
# [Not Necessary] This Item will be displayed when the prefix is selected. # itemUsing [Unnecessary]
# If there is no such configuration, it will automatically display "itemHasPermission". # This Item will be displayed when the prefix is selected.
==: org.bukkit.inventory.ItemStack # If there is no such configuration, it will automatically display "itemHasPermission".
type: DIAMOND itemUsing:
meta: ==: org.bukkit.inventory.ItemStack
==: ItemMeta type: DIAMOND
meta-type: UNSPECIFIC meta:
display-name: "§b§lVIP Prefix" ==: ItemMeta
enchants: meta-type: UNSPECIFIC
PROTECTION_ENVIRONMENTAL: 1 #Add an enchantment so it looks like its selected display-name: "§b§lVIP Prefix"
lore: enchants:
- "" PROTECTION_ENVIRONMENTAL: 1 #Add an enchantment so it looks like its selected
- "§a✔ Selected" lore:
itemNoPermission: - ""
# [Not Necessary] If player doesn't have the permission,this item will be displayed. - "§a✔ Selected"
# If this item is not configured, it will not be displayed in the GUI when the player does not have permission to use it.
==: org.bukkit.inventory.ItemStack # itemNoPermission [Unnecessary]
type: INK_SACK # If player doesn't have the permission,this item will be displayed.
damage: 8 # If this item is not configured, it will not be displayed in the GUI when the player does not have permission to use it.
meta: itemNoPermission:
==: ItemMeta ==: org.bukkit.inventory.ItemStack
meta-type: UNSPECIFIC type: INK_SACK
display-name: "§b§lVIP §c(Buy it!)" damage: 8
lore: meta:
- "" ==: ItemMeta
- "§e✯ Buy the VIP to use it!" meta-type: UNSPECIFIC
display-name: "§b§lVIP §c(Buy it!)"
lore:
- ""
- "§e✯ Buy the VIP to use it!"
``` ```
## Support and Donation ## Support and Donation
@@ -232,5 +291,6 @@ This project is support by the [YourCraft(你的世界)](https://www.ycraft.cn)
## Open source agreement ## Open source agreement
The source code of this project uses [GNU General Public License v3.0](https://opensource.org/licenses/GPL-3.0) License. The source code of this project uses [GNU General Public License v3.0](https://opensource.org/licenses/GPL-3.0)
License.
+137 -81
View File
@@ -36,14 +36,14 @@ The English version of the introduction is [here](https://github.com/CarmJos/Use
- 当玩家权限变更时会实时监测前缀,若权限不足则自动更换前缀并提示! - 当玩家权限变更时会实时监测前缀,若权限不足则自动更换前缀并提示!
- 可配置的声音、消息! - 可配置的声音、消息!
- 前缀图标可配置“选中”、“有权限”与“无权限”三种状态的物品 - 前缀图标可配置“选中”、“有权限”与“无权限”三种状态的物品
- 物品的配置通过ItemStack原生配置,支持MC所有的设定! - 物品的配置通过ItemStack原生配置,支持MC所有的设定!
- 具体的设定请参考其他文档哦~ - 具体的设定请参考其他文档哦~
- TabList自动按照前缀的权重排序 (如有冲突可关掉) - TabList自动按照前缀的权重排序 (如有冲突可关掉)
- 玩家头顶前缀显示 (如有冲突可关掉) - 玩家头顶前缀显示 (如有冲突可关掉)
- 自动排序,且可翻页的GUI - 自动排序,且可翻页的GUI
- 支持PlaceholderAPI变量!(凡支持的都可以使用,如BungeeTabListPlus) - 支持PlaceholderAPI变量!(凡支持的都可以使用,如BungeeTabListPlus)
- 支持Hex颜色!(1.16以上版本) 格式 `&(#颜色代码)` - 支持Hex颜色!(1.16以上版本) 格式 `&(#颜色代码)`
- 示例: LightSlateBlue `&(#8470FF)` 、 DarkSlateBlue `&(#483D8B)` - 示例: LightSlateBlue `&(#8470FF)` 、 DarkSlateBlue `&(#483D8B)`
## 注意事项 ## 注意事项
@@ -93,7 +93,9 @@ The English version of the introduction is [here](https://github.com/CarmJos/Use
- 判断玩家是否拥有某个前缀(true/false) - 判断玩家是否拥有某个前缀(true/false)
``` ```
## [配置文件](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/config.yml)示例 ## 配置文件示例
### [基础配置文件](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/config.yml) (config.yml)
```yaml ```yaml
version: 1.0.0-SNAPSHOT # 配置文件版本,一般不会动。 version: 1.0.0-SNAPSHOT # 配置文件版本,一般不会动。
@@ -106,27 +108,28 @@ functions:
GUI: GUI:
title: "&f&l我的前缀 &8| 列表" title: "&f&l我的前缀 &8| 列表"
items:
messages: # 【必须】 GUI中可能存在的其他物品
selected: next-page: # 下一页物品,如果没有下一页则不显示
- "&7您选择了 &f%(name) &7作为当前显示的前缀。" ==: org.bukkit.inventory.ItemStack
expired: type: ARROW
- "&7您先前使用的前缀 &f%(oldName) &7已到期。" meta:
- "&7现在已为您重新调整为 &f%(newName) &7。" ==: ItemMeta
reload: meta-type: UNSPECIFIC
- "&a&l重载完成!&7共耗时 &f%(time)ms&7。" display-name: "§f下一页"
help: lore:
- "&3&l用户前缀系统 &f帮助" - ""
- "&8#/upa&f list" - "§f右键可前往最后一页哦~"
- "&8- &7查看当前前缀列表。" previous-page: # 上一页物品,如果没有上一页则不显示
- "&8#/upa&f reload" ==: org.bukkit.inventory.ItemStack
- "&8- &7重载前缀配置。" type: ARROW
list-title: meta:
- "&3&l用户前缀系统 &f前缀列表" ==: ItemMeta
list-value: meta-type: UNSPECIFIC
- "&8#%(weight) &f%(identifier)" display-name: "§f上一页"
- "&8- &7显示名 &r%(name) &7权限 &r%(permission)" lore:
- "&8- &7内容示例&r %(content) %(sender_name)" - ""
- "§f右键可前往第一页哦~"
Sounds: #相关的声音,注释掉则不播放声音 Sounds: #相关的声音,注释掉则不播放声音
# 格式为 【声音名:音量:音调】 或 【声音名:音量】 或 【声音名】 # 格式为 【声音名:音量:音调】 或 【声音名:音量】 或 【声音名】
@@ -160,64 +163,117 @@ defaultPrefix:
lore: lore:
- "" - ""
- "§a✔ 您正在使用该前缀" - "§a✔ 您正在使用该前缀"
prefixes:
VIP:
name: "&b&lPro&b" # [必须] 名字(切换的时候左下角会弹提示 用的就是这个名字)
content: "§b§lPro §b" # [必须] 显示在名字前面的内容
weight: 1 # [必须] 权重,用于GUI里面的排序(越大显示在越后面)和自动前缀显示
permission: "yc.pro" # [非必须] 检测的权限,如果没有就是人人都能用,也代表不用配置“itemNoPermission”了(因为压根不可能显示没权限时候的物品)
itemHasPermission:
# [必须] 当有权限的时候会显示这个Item
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a➥ 点击切换到该前缀"
itemUsing:
# [非必需] 当有权限的时候会显示这个Item,如果没有这个配置就自动显示“itemHasPermission”的。
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
enchants:
PROTECTION_ENVIRONMENTAL: 1 #加一个附魔这样看上去就像是选中了的
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a✔ 您正在使用该前缀"
itemNoPermission:
# [非必需] 如果没有权限就会显示这个item。如果不配置该物品,则玩家没有使用权限时不会显示在GUI里面。
==: org.bukkit.inventory.ItemStack
type: INK_SACK
damage: 8
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro+ §b会员前缀 §c(未拥有)"
lore:
- "§7Pro+会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- "§f您可以输入 §b/vip §f指令查看详细特权!"
- ""
- "§e✯ 加入Pro+会员以使用该前缀!"
``` ```
### [消息配置文件](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/messages.yml) (messages.yml)
```yaml
selected:
- "&7您选择了 &f%(name) &7作为当前显示的前缀。"
expired:
- "&7您先前使用的前缀 &f%(oldName) &7已到期。"
- "&7现在已为您重新调整为 &f%(newName) &7。"
reload:
- "&a&l重载完成!&7共耗时 &f%(time)ms&7。"
help:
- "&3&l用户前缀系统 &f帮助"
- "&8#/upa&f list"
- "&8- &7查看当前前缀列表。"
- "&8#/upa&f reload"
- "&8- &7重载前缀配置。"
list-title:
- "&3&l用户前缀系统 &f前缀列表"
list-value:
- "&8#%(weight) &f%(identifier)"
- "&8- &7显示名 &r%(name) &7权限 &r%(permission)"
- "&8- &7内容示例&r %(content) %(sender_name)"
```
### [前缀配置文件](https://github.com/CarmJos/UserPrefix/blob/master/src/main/resources/prefixes/example-prefix.yml) (prefixes/*.yml)
所有前缀均为单独的配置文件,存放于 `插件配置目录/prefixes` 下,便于管理。
文件名理论上可以随便取,推荐使用英文,部分符号可能会影响正常读取,请避免使用。
```yaml
# 唯一标识 [必须]
# 将用于记录玩家所选的前缀,以及用于数据的缓存。
# 必须 必须 必须 保持唯一!
identifier: "pro"
# 名字 [必须]
# 切换的时候左下角会弹提示 用的就是这个名字
name: "&b&lPro&b"
# 内容 [必须]
# 显示在名字前面的内容
content: "§b§lPro §b"
# 权重 [必须]
# 用于GUI、TabList的排序和自动前缀显示
# 在GUI中,权重越高的会显示在越后面
# 在TabList中,权重越高的会显示在越上面
weight: 1
# 检测的权限 [非必须]
# 如果没有就是人人都能用,也代表不用配置“itemNoPermission”了(因为压根不可能显示没权限时候的物品)
permission: "yc.pro"
# 有权限时显示的物品 [必须]
# 当用户有权限且未选中时,会显示该物品
itemHasPermission: #
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a➥ 点击切换到该前缀"
# 正在使用时显示的物品 [非必需]
# 当用户正在使用时会显示这个物品,不配置即自动加载“itemHasPermission”
itemUsing:
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
enchants:
PROTECTION_ENVIRONMENTAL: 1 #加一个附魔这样看上去就像是选中了的
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a✔ 您正在使用该前缀"
# 没有权限时显示的物品 [非必需]
# 如果没有权限就会显示这个item。如果不配置该物品,则玩家没有使用权限时不会显示在GUI里面。
itemNoPermission:
==: org.bukkit.inventory.ItemStack
type: INK_SACK
damage: 8
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro+ §b会员前缀 §c(未拥有)"
lore:
- "§7Pro+会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- "§f您可以输入 §b/vip §f指令查看详细特权!"
- ""
- "§e✯ 加入Pro+会员以使用该前缀!"
```
## 支持与捐赠 ## 支持与捐赠
本项目由 [YourCraft(你的世界)](https://www.ycraft.cn) 团队提供长期支持与维护。 本项目由 [YourCraft(你的世界)](https://www.ycraft.cn) 团队提供长期支持与维护。
+1 -1
View File
@@ -6,7 +6,7 @@
<groupId>cc.carm.plugin</groupId> <groupId>cc.carm.plugin</groupId>
<artifactId>UserPrefix</artifactId> <artifactId>UserPrefix</artifactId>
<version>1.2.5</version> <version>2.0.0</version>
<properties> <properties>
<maven.compiler.source>8</maven.compiler.source> <maven.compiler.source>8</maven.compiler.source>
@@ -42,8 +42,8 @@ public class UserPrefixAdminCommand implements CommandExecutor {
} else if (aim.equalsIgnoreCase("reload")) { } else if (aim.equalsIgnoreCase("reload")) {
long s1 = System.currentTimeMillis(); long s1 = System.currentTimeMillis();
PrefixSelectGUI.closeAll(); // 关掉所有正在显示的前缀列表 PrefixSelectGUI.closeAll(); // 关掉所有正在显示的前缀列表
ConfigManager.reloadConfig(); // 重载配置文件 ConfigManager.reload(); // 重载配置文件
PrefixManager.loadConfiguredPrefixes(); //加载重载后了的配置文件 PrefixManager.loadPrefixes(); //加载重载后了的前缀配置
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) { for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
UserManager.checkPrefix(onlinePlayer, false); UserManager.checkPrefix(onlinePlayer, false);
/* /*
@@ -1,8 +1,11 @@
package cc.carm.plugin.userprefix.configuration; package cc.carm.plugin.userprefix.configuration;
import cc.carm.plugin.userprefix.configuration.message.ConfigMessageList;
import cc.carm.plugin.userprefix.configuration.values.ConfigSound; import cc.carm.plugin.userprefix.configuration.values.ConfigSound;
import cc.carm.plugin.userprefix.configuration.values.ConfigValue; import cc.carm.plugin.userprefix.configuration.values.ConfigValue;
import cc.carm.plugin.userprefix.configuration.values.ConfigValueList; import cc.carm.plugin.userprefix.util.ItemStackFactory;
import org.bukkit.Material;
import org.bukkit.inventory.ItemStack;
public class PrefixConfig { public class PrefixConfig {
@@ -19,18 +22,35 @@ public class PrefixConfig {
public static ConfigValue<String> TITLE = new ConfigValue<>("GUI.title", String.class, "&f&l我的前缀 &8| 列表"); public static ConfigValue<String> TITLE = new ConfigValue<>("GUI.title", String.class, "&f&l我的前缀 &8| 列表");
public static class Items {
public static ConfigValue<ItemStack> NEXT_PAGE = new ConfigValue<>("GUI.items.next-page", ItemStack.class,
new ItemStackFactory(Material.ARROW)
.setDisplayName("下一页")
.addLore("&7&o右键可前往最后一页哦")
.toItemStack()
);
public static ConfigValue<ItemStack> PREVIOUS_PAGE = new ConfigValue<>("GUI.items.previous-page", ItemStack.class,
new ItemStackFactory(Material.ARROW)
.setDisplayName("上一页")
.addLore("&7&o右键可前往第一页哦")
.toItemStack()
);
}
} }
public static class Messages { public static class Messages {
public static ConfigValueList<String> SELECTED = new ConfigValueList<>("messages.selected", String.class); public static ConfigMessageList SELECTED = new ConfigMessageList("selected");
public static ConfigValueList<String> EXPIRED = new ConfigValueList<>("messages.expired", String.class); public static ConfigMessageList EXPIRED = new ConfigMessageList("expired");
public static ConfigValueList<String> RELOAD = new ConfigValueList<>("messages.reload", String.class); public static ConfigMessageList RELOAD = new ConfigMessageList("reload");
public static ConfigValueList<String> HELP = new ConfigValueList<>("messages.help", String.class); public static ConfigMessageList HELP = new ConfigMessageList("help");
public static ConfigValueList<String> LIST_TITLE = new ConfigValueList<>("messages.list-title", String.class); public static ConfigMessageList LIST_TITLE = new ConfigMessageList("list-title");
public static ConfigValueList<String> LIST_VALUE = new ConfigValueList<>("messages.list-value", String.class); public static ConfigMessageList LIST_VALUE = new ConfigMessageList("list-value");
} }
public static class Sounds { public static class Sounds {
@@ -0,0 +1,64 @@
package cc.carm.plugin.userprefix.configuration.file;
import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.plugin.java.JavaPlugin;
import java.io.File;
import java.io.IOException;
public class FileConfig {
private final JavaPlugin plugin;
private final String fileName;
private File file;
private FileConfiguration config;
public FileConfig(final JavaPlugin plugin) {
this(plugin, "config.yml");
}
public FileConfig(final JavaPlugin plugin, final String name) {
this.plugin = plugin;
this.fileName = name;
initFile();
}
private void initFile() {
this.file = new File(plugin.getDataFolder(), fileName);
if (!this.file.exists()) {
if (!this.file.getParentFile().exists()) {
this.file.getParentFile().mkdirs();
}
plugin.saveResource(fileName, true);
}
this.config = YamlConfiguration.loadConfiguration(this.file);
}
public File getFile() {
return file;
}
public FileConfiguration getConfig() {
return config;
}
public void save() {
try {
getConfig().save(getFile());
} catch (IOException e) {
e.printStackTrace();
}
}
public void reload() {
if (getFile().exists()) {
this.config = YamlConfiguration.loadConfiguration(getFile());
} else {
initFile();
}
}
}
@@ -0,0 +1,32 @@
package cc.carm.plugin.userprefix.configuration.message;
import cc.carm.plugin.userprefix.configuration.values.ConfigValue;
import cc.carm.plugin.userprefix.manager.ConfigManager;
import cc.carm.plugin.userprefix.util.MessageUtil;
import org.bukkit.command.CommandSender;
import java.util.Arrays;
public class ConfigMessage extends ConfigValue<String> {
public ConfigMessage(String configSection) {
this(configSection, null);
}
public ConfigMessage(String configSection, String defaultValue) {
super(ConfigManager.getMessageConfig(), configSection, String.class, defaultValue);
}
public void send(CommandSender sender) {
MessageUtil.send(sender, get());
}
public void sendWithPlaceholders(CommandSender sender) {
MessageUtil.sendWithPlaceholders(sender, get());
}
public void sendWithPlaceholders(CommandSender sender, String[] params, Object[] values) {
MessageUtil.sendWithPlaceholders(sender, Arrays.asList(get()), params, values);
}
}
@@ -0,0 +1,29 @@
package cc.carm.plugin.userprefix.configuration.message;
import cc.carm.plugin.userprefix.configuration.values.ConfigValueList;
import cc.carm.plugin.userprefix.manager.ConfigManager;
import cc.carm.plugin.userprefix.util.MessageUtil;
import org.bukkit.command.CommandSender;
public class ConfigMessageList extends ConfigValueList<String> {
public ConfigMessageList(String configSection) {
super(ConfigManager.getMessageConfig(), configSection, String.class);
}
public ConfigMessageList(String configSection, String[] defaultValue) {
super(ConfigManager.getMessageConfig(), configSection, String.class, defaultValue);
}
public void send(CommandSender sender) {
MessageUtil.send(sender, get());
}
public void sendWithPlaceholders(CommandSender sender) {
MessageUtil.sendWithPlaceholders(sender, get());
}
public void sendWithPlaceholders(CommandSender sender, String[] params, Object[] values) {
MessageUtil.sendWithPlaceholders(sender, get(), params, values);
}
}
@@ -1,13 +1,16 @@
package cc.carm.plugin.userprefix.configuration.values; package cc.carm.plugin.userprefix.configuration.values;
import cc.carm.plugin.userprefix.Main; import cc.carm.plugin.userprefix.Main;
import cc.carm.plugin.userprefix.configuration.file.FileConfig;
import cc.carm.plugin.userprefix.manager.ConfigManager; import cc.carm.plugin.userprefix.manager.ConfigManager;
import org.bukkit.Sound; import org.bukkit.Sound;
import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
public class ConfigSound { public class ConfigSound {
FileConfiguration source;
FileConfig source;
String configSection; String configSection;
Sound defaultValue; Sound defaultValue;
@@ -17,18 +20,26 @@ public class ConfigSound {
} }
public ConfigSound(String configSection, Sound defaultValue) { public ConfigSound(String configSection, Sound defaultValue) {
this.source = ConfigManager.getConfig(); this(ConfigManager.getPluginConfig(), configSection, defaultValue);
}
public ConfigSound(FileConfig source, String configSection, Sound defaultValue) {
this.source = source;
this.configSection = configSection; this.configSection = configSection;
this.defaultValue = defaultValue; this.defaultValue = defaultValue;
} }
public FileConfiguration getConfiguration() {
return this.source.getConfig();
}
public void set(Sound value, float volume) { public void set(Sound value, float volume) {
this.source.set(this.configSection, value.name() + ":" + volume); getConfiguration().set(this.configSection, value.name() + ":" + volume);
this.save(); this.save();
} }
public void set(Sound value, float volume, float pitch) { public void set(Sound value, float volume, float pitch) {
this.source.set(this.configSection, value.name() + ":" + volume + ":" + pitch); getConfiguration().set(this.configSection, value.name() + ":" + volume + ":" + pitch);
this.save(); this.save();
} }
@@ -36,7 +47,7 @@ public class ConfigSound {
Sound finalSound = defaultValue; Sound finalSound = defaultValue;
float pitch = 1; float pitch = 1;
float volume = 1; float volume = 1;
String soundString = this.source.getString(this.configSection); String soundString = getConfiguration().getString(this.configSection);
if (soundString != null) { if (soundString != null) {
String[] args = soundString.contains(":") ? soundString.split(":") : new String[]{soundString}; String[] args = soundString.contains(":") ? soundString.split(":") : new String[]{soundString};
try { try {
@@ -54,7 +65,7 @@ public class ConfigSound {
} }
public void save() { public void save() {
ConfigManager.saveConfig(); this.source.save();
} }
} }
@@ -1,10 +1,13 @@
package cc.carm.plugin.userprefix.configuration.values; package cc.carm.plugin.userprefix.configuration.values;
import cc.carm.plugin.userprefix.configuration.file.FileConfig;
import cc.carm.plugin.userprefix.manager.ConfigManager; import cc.carm.plugin.userprefix.manager.ConfigManager;
import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.configuration.file.FileConfiguration;
public class ConfigValue<V> { public class ConfigValue<V> {
FileConfiguration source;
FileConfig source;
String configSection; String configSection;
Class<V> clazz; Class<V> clazz;
V defaultValue; V defaultValue;
@@ -14,24 +17,32 @@ public class ConfigValue<V> {
} }
public ConfigValue(String configSection, Class<V> clazz, V defaultValue) { public ConfigValue(String configSection, Class<V> clazz, V defaultValue) {
this.source = ConfigManager.getConfig(); this(ConfigManager.getPluginConfig(), configSection, clazz, defaultValue);
}
public ConfigValue(FileConfig source, String configSection, Class<V> clazz, V defaultValue) {
this.source = source;
this.configSection = configSection; this.configSection = configSection;
this.clazz = clazz; this.clazz = clazz;
this.defaultValue = defaultValue; this.defaultValue = defaultValue;
} }
public FileConfiguration getConfiguration() {
return this.source.getConfig();
}
public V get() { public V get() {
Object val = this.source.get(this.configSection, this.defaultValue); Object val = getConfiguration().get(this.configSection, this.defaultValue);
return this.clazz.isInstance(val) ? this.clazz.cast(val) : this.defaultValue; return this.clazz.isInstance(val) ? this.clazz.cast(val) : this.defaultValue;
} }
public void set(V value) { public void set(V value) {
this.source.set(this.configSection, value); getConfiguration().set(this.configSection, value);
this.save(); this.save();
} }
public void save() { public void save() {
ConfigManager.saveConfig(); this.source.save();
} }
} }
@@ -1,26 +1,52 @@
package cc.carm.plugin.userprefix.configuration.values; package cc.carm.plugin.userprefix.configuration.values;
import cc.carm.plugin.userprefix.configuration.file.FileConfig;
import cc.carm.plugin.userprefix.manager.ConfigManager; import cc.carm.plugin.userprefix.manager.ConfigManager;
import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.configuration.file.FileConfiguration;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Arrays;
import java.util.List; import java.util.List;
public class ConfigValueList<V> { public class ConfigValueList<V> {
FileConfiguration source; FileConfig source;
String configSection; String configSection;
Class<V> clazz; Class<V> clazz;
V[] defaultValue;
public ConfigValueList(String configSection, Class<V> clazz) { public ConfigValueList(String configSection, Class<V> clazz) {
this.source = ConfigManager.getConfig(); this(ConfigManager.getPluginConfig(), configSection, clazz);
this.configSection = configSection;
this.clazz = clazz;
} }
public ConfigValueList(String configSection, Class<V> clazz, V[] defaultValue) {
this(ConfigManager.getPluginConfig(), configSection, clazz, defaultValue);
}
public ConfigValueList(FileConfig configuration, String configSection, Class<V> clazz) {
this(configuration, configSection, clazz, null);
}
public ConfigValueList(FileConfig configuration, String configSection, Class<V> clazz, V[] defaultValue) {
this.source = configuration;
this.configSection = configSection;
this.clazz = clazz;
this.defaultValue = defaultValue;
}
public FileConfiguration getConfiguration() {
return this.source.getConfig();
}
public ArrayList<V> get() { public ArrayList<V> get() {
List<?> list = this.source.getList(this.configSection); List<?> list = getConfiguration().getList(this.configSection);
if (list == null) { if (list == null) {
return new ArrayList(0); if (defaultValue != null) {
return new ArrayList<>(Arrays.asList(defaultValue));
} else {
return new ArrayList(0);
}
} else { } else {
ArrayList<V> result = new ArrayList(); ArrayList<V> result = new ArrayList();
@@ -29,17 +55,17 @@ public class ConfigValueList<V> {
result.add(this.clazz.cast(object)); result.add(this.clazz.cast(object));
} }
} }
return result; return result;
} }
} }
public void set(ArrayList<V> value) { public void set(ArrayList<V> value) {
this.source.set(this.configSection, value); getConfiguration().set(this.configSection, value);
this.save(); this.save();
} }
public void save() { public void save() {
ConfigManager.saveConfig(); this.source.save();
} }
} }
@@ -1,30 +1,47 @@
package cc.carm.plugin.userprefix.manager; package cc.carm.plugin.userprefix.manager;
import cc.carm.plugin.userprefix.Main; import cc.carm.plugin.userprefix.Main;
import org.bukkit.configuration.file.FileConfiguration; import cc.carm.plugin.userprefix.configuration.file.FileConfig;
import java.io.File;
public class ConfigManager { public class ConfigManager {
private static FileConfiguration config; private static FileConfig config;
private static FileConfig messageConfig;
public static void initConfig() { public static void initConfig() {
Main.getInstance().saveDefaultConfig(); File configFile = new File(Main.getInstance().getDataFolder(), "config.yml");
Main.getInstance().reloadConfig(); if (!configFile.exists()) {
//没找到配置文件,可能是第一次加载此插件
//把一些英文版的东西复制出来,方便英文用户使用。
Main.getInstance().saveResource("prefixes/example-prefix.yml", false);
Main.getInstance().saveResource("en_US/config.yml", false);
Main.getInstance().saveResource("en_US/messages.yml", false);
Main.getInstance().saveResource("en_US/example-prefix.yml", false);
}
config = Main.getInstance().getConfig(); ConfigManager.config = new FileConfig(Main.getInstance(), "config.yml");
ConfigManager.messageConfig = new FileConfig(Main.getInstance(), "messages.yml");
} }
public static FileConfiguration getConfig() { public static FileConfig getPluginConfig() {
return config; return config;
} }
public static void reloadConfig() { public static FileConfig getMessageConfig() {
Main.getInstance().reloadConfig(); return messageConfig;
config = Main.getInstance().getConfig(); }
public static void reload() {
getPluginConfig().reload();
getMessageConfig().reload();
} }
public static void saveConfig() { public static void saveConfig() {
Main.getInstance().saveConfig(); getPluginConfig().save();
getMessageConfig().save();
} }
@@ -11,6 +11,8 @@ import org.bukkit.inventory.ItemStack;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import java.io.File;
import java.util.Arrays;
import java.util.Comparator; import java.util.Comparator;
import java.util.HashMap; import java.util.HashMap;
import java.util.List; import java.util.List;
@@ -21,45 +23,48 @@ public class PrefixManager {
public static ConfiguredPrefix defaultPrefix; public static ConfiguredPrefix defaultPrefix;
public static HashMap<String, ConfiguredPrefix> prefixes = new HashMap<>(); public static HashMap<String, ConfiguredPrefix> prefixes = new HashMap<>();
private static final String FOLDER_NAME = "prefixes";
public static void init() { public static void init() {
loadConfiguredPrefixes(); loadPrefixes();
Main.log("共加载了 " + prefixes.size() + " 个前缀。"); Main.log("共加载了 " + prefixes.size() + " 个前缀。");
} }
public static void loadConfiguredPrefixes() { public static void loadPrefixes() {
loadDefaultPrefix(); loadDefaultPrefix();
loadConfiguredPrefixes();
}
ConfigurationSection prefixesSection = ConfigManager.getConfig().getConfigurationSection("prefixes"); public static void loadConfiguredPrefixes() {
if (prefixesSection == null || prefixesSection.getKeys(false).isEmpty()) {
File prefixDataFolder = new File(Main.getInstance().getDataFolder() + File.separator + FOLDER_NAME);
if (!prefixDataFolder.isDirectory() || !prefixDataFolder.exists()) {
prefixDataFolder.mkdir();
}
String[] filesList = prefixDataFolder.list();
if (filesList == null || filesList.length < 1) {
Main.log("配置文件中暂无任何前缀配置,请检查。"); Main.log("配置文件中暂无任何前缀配置,请检查。");
Main.log("There's no configured prefix.");
return; return;
} }
List<File> files = Arrays.stream(filesList)
.map(s -> new File(prefixDataFolder, s))
.filter(File::isFile)
.collect(Collectors.toList());
HashMap<String, ConfiguredPrefix> dataPrefixes = new HashMap<>(); HashMap<String, ConfiguredPrefix> dataPrefixes = new HashMap<>();
for (String prefixIdentifier : prefixesSection.getKeys(false)) { if (files.size() > 0) {
ConfigurationSection configuredPrefixSection = prefixesSection.getConfigurationSection(prefixIdentifier); for (File file : files) {
if (configuredPrefixSection == null) continue; try {
try { ConfiguredPrefix prefix = new ConfiguredPrefix(file);
String name = configuredPrefixSection.getString("name", "ERROR"); Main.log("完成前缀加载 " + prefix.getIdentifier() + " : " + prefix.getName());
String content = configuredPrefixSection.getString("content", "&r"); dataPrefixes.put(prefix.getIdentifier(), prefix);
String permission = configuredPrefixSection.getString("permission"); } catch (Exception ex) {
int weight = configuredPrefixSection.getInt("weight", 1); Main.log("Error occurred when loading prefix #" + file.getAbsolutePath() + " !");
ex.printStackTrace();
ItemStack itemHasPermission = configuredPrefixSection.getItemStack("itemHasPermission", }
new ItemStackFactory(Material.STONE).setDisplayName(name).addLore(" ").addLore("§a➥ 点击切换到该前缀").toItemStack()
);
ItemStack itemNoPermission = configuredPrefixSection.getItemStack("itemNoPermission", itemHasPermission);
ItemStack itemUsing = configuredPrefixSection.getItemStack("itemUsing", itemHasPermission);
Main.log("完成前缀加载 " + prefixIdentifier + " : " + name);
dataPrefixes.put(prefixIdentifier, new ConfiguredPrefix(prefixIdentifier, name, content, weight, permission, itemHasPermission, itemNoPermission, itemUsing));
} catch (Exception exception) {
Main.log("Error occurred when loading prefix #" + prefixIdentifier + " !");
exception.printStackTrace();
} }
} }
@@ -69,7 +74,7 @@ public class PrefixManager {
public static void loadDefaultPrefix() { public static void loadDefaultPrefix() {
PrefixManager.defaultPrefix = null; PrefixManager.defaultPrefix = null;
ConfigurationSection defaultPrefixSection = ConfigManager.getConfig().getConfigurationSection("defaultPrefix"); ConfigurationSection defaultPrefixSection = ConfigManager.getPluginConfig().getConfig().getConfigurationSection("defaultPrefix");
if (defaultPrefixSection != null) { if (defaultPrefixSection != null) {
try { try {
String name = defaultPrefixSection.getString("name", "默认前缀"); String name = defaultPrefixSection.getString("name", "默认前缀");
@@ -1,12 +1,23 @@
package cc.carm.plugin.userprefix.model; package cc.carm.plugin.userprefix.model;
import cc.carm.plugin.userprefix.util.ColorParser; import cc.carm.plugin.userprefix.util.ColorParser;
import cc.carm.plugin.userprefix.util.ItemStackFactory;
import org.bukkit.Material;
import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import java.io.File;
public class ConfiguredPrefix { public class ConfiguredPrefix {
@Nullable
private File dataFile;
@Nullable
private FileConfiguration configuration;
String identifier; String identifier;
String name; String name;
@@ -20,6 +31,25 @@ public class ConfiguredPrefix {
ItemStack itemNoPermission; ItemStack itemNoPermission;
ItemStack itemWhenUsing; ItemStack itemWhenUsing;
public ConfiguredPrefix(@NotNull File dataFile) {
this.dataFile = dataFile;
this.configuration = YamlConfiguration.loadConfiguration(dataFile);
if (getConfiguration() != null) {
this.identifier = getConfiguration().getString("identifier", "ERROR");
this.name = getConfiguration().getString("name", "ERROR");
this.content = getConfiguration().getString("content", "&r");
this.permission = getConfiguration().getString("permission");
this.weight = getConfiguration().getInt("weight", 1);
this.itemHasPermission = (ItemStack) getConfiguration().get("itemHasPermission",
new ItemStackFactory(Material.STONE).setDisplayName(name).addLore(" ").addLore("§a➥ 点击切换到该前缀").toItemStack()
);
this.itemNoPermission = (ItemStack) getConfiguration().get("itemNoPermission", itemHasPermission);
this.itemWhenUsing = (ItemStack) getConfiguration().get("itemUsing", itemHasPermission);
}
}
public ConfiguredPrefix(@NotNull String identifier, public ConfiguredPrefix(@NotNull String identifier,
@NotNull String name, @NotNull String name,
@NotNull String content, @NotNull String content,
@@ -37,6 +67,11 @@ public class ConfiguredPrefix {
this.itemWhenUsing = itemWhenUsing; this.itemWhenUsing = itemWhenUsing;
} }
@Nullable
public FileConfiguration getConfiguration() {
return configuration;
}
@NotNull @NotNull
public String getIdentifier() { public String getIdentifier() {
return identifier; return identifier;
@@ -1,8 +1,6 @@
package cc.carm.plugin.userprefix.util.gui; package cc.carm.plugin.userprefix.util.gui;
import cc.carm.plugin.userprefix.configuration.PrefixConfig; import cc.carm.plugin.userprefix.configuration.PrefixConfig;
import cc.carm.plugin.userprefix.util.ItemStackFactory;
import org.bukkit.Material;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.event.inventory.ClickType; import org.bukkit.event.inventory.ClickType;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
@@ -53,10 +51,7 @@ public class AutoPagedGUI extends CommonPagedGUI {
public void openGUI(Player user) { public void openGUI(Player user) {
if (previousPageSlot >= 0) if (previousPageSlot >= 0)
if (hasPreviousPage()) { if (hasPreviousPage()) {
setItem(previousPageSlot, new GUIItem(previousPageUI == null ? new ItemStackFactory(Material.ARROW) setItem(previousPageSlot, new GUIItem(previousPageUI == null ? PrefixConfig.GUI.Items.PREVIOUS_PAGE.get() : previousPageUI) {
.setDisplayName("&f上一页")
.addLore("&7&o右键可前往第一页哦")
.toItemStack() : previousPageUI) {
@Override @Override
public void onClick(ClickType type) { public void onClick(ClickType type) {
if (type == ClickType.RIGHT) { if (type == ClickType.RIGHT) {
@@ -70,12 +65,9 @@ public class AutoPagedGUI extends CommonPagedGUI {
}); });
} }
if (previousPageSlot >= 0) if (nextPageSlot >= 0)
if (hasNextPage()) { if (hasNextPage()) {
setItem(nextPageSlot, new GUIItem(nextPageUI == null ? new ItemStackFactory(Material.ARROW) setItem(nextPageSlot, new GUIItem(nextPageUI == null ? PrefixConfig.GUI.Items.NEXT_PAGE.get() : nextPageUI) {
.setDisplayName("下一页")
.addLore("&7&o右键可前往最后一页哦")
.toItemStack() : nextPageUI) {
@Override @Override
public void onClick(ClickType type) { public void onClick(ClickType type) {
if (type == ClickType.RIGHT) { if (type == ClickType.RIGHT) {
-120
View File
@@ -1,120 +0,0 @@
version: ${project.version} # DO NOT EDIT IT
debug: false #DEBUG OUT PUT
GUI:
title: "&f&lMy Prefixes List" # Title of the GUI
functions:
# Whether to add a prefix to the top of the head,
# this method uses the scoreboard above the head,
# please turn it off if there is a conflict.
OnNamePrefix: true
# Automatic prefix select.
# When the player does not choose a prefix by himself,
# the prefix with the highest weight will be used automatically
autoUsePrefix: true
messages:
selected:
- "&7You have selected the &f%(name) &7as current prefix."
expired:
- "&7Your prefix &f%(oldName) &7has expired,"
- "&7Now the prefix is changed to &f%(newName) &7."
reload:
- "&a&lReload completed&7costs &f%(time)ms&7."
help:
- "&3&lUserPrefixAdmin &fHelp"
- "&8#/upa&f list"
- "&8- &7Show configured prefixes."
- "&8#/upa&f reload"
- "&8- &7Reload configuration."
list-title:
- "&3&lUserPrefixAdmin &fList"
list-value:
- "&8#%(weight) &f%(identifier)"
- "&8- &7Name &r%(name) &7Perm &r%(permission)"
- "&8- &7Example&r %(content) %(sender_name)"
Sounds:
# Format is [SOUND_NAME:Volume:Pitch] or [SOUND_NAME:Volume] or [SOUND_NAME]
openGUI: "BLOCK_NOTE_BLOCK_PLING:1:1"
guiClick: "UI_BUTTON_CLICK"
prefixChange: "ENTITY_VILLAGER_YES"
prefixExpired: "ENTITY_VILLAGER_NO"
# The default prefix's weight is 0.
defaultPrefix:
name: "Default prefix"
content: "&b"
itemNotUsing:
==: org.bukkit.inventory.ItemStack
type: NAME_TAG
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fThe default prefix §f(Click to select)"
lore:
- ""
- "§a➥ Click to use"
itemUsing:
==: org.bukkit.inventory.ItemStack
type: NAME_TAG
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fThe default prefix"
lore:
- ""
- "§a✔ Selected"
prefixes:
VIP:
name: "&b&lPro&b" # [Necessary] Name (Using in messages)
content: "§b§lPro §b" # [Necessary] What to display before the name
# [Necessary] Weight, used for sorting in the GUI
# (the larger is displayed at the back) and the automatic prefix display
weight: 1
# [Necessary] If there is no permission for detection, everyone can use it,
# which means there is no need to configure "itemNoPermission"
# (because it is impossible to display items without permission at all)
permission: "yc.pro"
itemHasPermission:
# [Necessary] This Item will be displayed when player has permission
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lVIP Prefix"
lore:
- ""
- "§a➥ Click to use"
itemUsing:
# [Not Necessary] This Item will be displayed when the prefix is selected.
# If there is no such configuration, it will automatically display "itemHasPermission".
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lVIP Prefix"
enchants:
PROTECTION_ENVIRONMENTAL: 1 #Add an enchantment so it looks like its selected
lore:
- ""
- "§a✔ Selected"
itemNoPermission:
# [Not Necessary] If player doesn't have the permission,this item will be displayed.
# If this item is not configured, it will not be displayed in the GUI when the player does not have permission to use it.
==: org.bukkit.inventory.ItemStack
type: INK_SACK
damage: 8
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lVIP §c(Buy it!)"
lore:
- ""
- "§e✯ Buy the VIP to use it!"
+22 -75
View File
@@ -8,27 +8,28 @@ functions:
GUI: GUI:
title: "&f&l我的前缀 &8| 列表" title: "&f&l我的前缀 &8| 列表"
items:
messages: # 【必须】 GUI中可能存在的其他物品
selected: next-page: # 下一页物品,如果没有下一页则不显示
- "&7您选择了 &f%(name) &7作为当前显示的前缀。" ==: org.bukkit.inventory.ItemStack
expired: type: ARROW
- "&7您先前使用的前缀 &f%(oldName) &7已到期。" meta:
- "&7现在已为您重新调整为 &f%(newName) &7。" ==: ItemMeta
reload: meta-type: UNSPECIFIC
- "&a&l重载完成!&7共耗时 &f%(time)ms&7。" display-name: "§f下一页"
help: lore:
- "&3&l用户前缀系统 &f帮助" - ""
- "&8#/upa&f list" - "§f右键可前往最后一页哦~"
- "&8- &7查看当前前缀列表。" previous-page: # 上一页物品,如果没有上一页则不显示
- "&8#/upa&f reload" ==: org.bukkit.inventory.ItemStack
- "&8- &7重载前缀配置。" type: ARROW
list-title: meta:
- "&3&l用户前缀系统 &f前缀列表" ==: ItemMeta
list-value: meta-type: UNSPECIFIC
- "&8#%(weight) &f%(identifier)" display-name: "§f上一页"
- "&8- &7显示名 &r%(name) &7权限 &r%(permission)" lore:
- "&8- &7内容示例&r %(content) %(sender_name)" - ""
- "§f右键可前往第一页哦~"
Sounds: #相关的声音,注释掉则不播放声音 格式为 【声音名:音量:音调】 或 【声音名:音量】 或 【声音名】 Sounds: #相关的声音,注释掉则不播放声音 格式为 【声音名:音量:音调】 或 【声音名:音量】 或 【声音名】
openGUI: "BLOCK_NOTE_BLOCK_PLING:1:1" openGUI: "BLOCK_NOTE_BLOCK_PLING:1:1"
@@ -61,57 +62,3 @@ defaultPrefix:
lore: lore:
- "" - ""
- "§a✔ 您正在使用该前缀" - "§a✔ 您正在使用该前缀"
prefixes:
VIP:
name: "&b&lPro&b" # [必须] 名字(切换的时候左下角会弹提示 用的就是这个名字)
content: "§b§lPro §b" # [必须] 显示在名字前面的内容
weight: 1 # [必须] 权重,用于GUI里面的排序(越大显示在越后面)和自动前缀显示
permission: "yc.pro" # [非必须] 检测的权限,如果没有就是人人都能用,也代表不用配置“itemNoPermission”了(因为压根不可能显示没权限时候的物品)
itemHasPermission: # [必须] 当有权限的时候会显示这个Item
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a➥ 点击切换到该前缀"
itemUsing: # [非必需] 当有权限的时候会显示这个Item,如果没有这个配置就自动显示“itemHasPermission”的。
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
enchants:
PROTECTION_ENVIRONMENTAL: 1 #加一个附魔这样看上去就像是选中了的
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a✔ 您正在使用该前缀"
itemNoPermission: # [非必需] 如果没有权限就会显示这个item。如果不配置该物品,则玩家没有使用权限时不会显示在GUI里面。
==: org.bukkit.inventory.ItemStack
type: INK_SACK
damage: 8
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro+ §b会员前缀 §c(未拥有)"
lore:
- "§7Pro+会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- "§f您可以输入 §b/vip §f指令查看详细特权!"
- ""
- "§e✯ 加入Pro+会员以使用该前缀!"
+71
View File
@@ -0,0 +1,71 @@
version: ${project.version} # DO NOT EDIT IT
debug: false #DEBUG OUT PUT
GUI:
title: "&f&lMy Prefixes List" # Title of the GUI
items:
next-page: # only show has next page
==: org.bukkit.inventory.ItemStack
type: ARROW
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fNext Page"
lore:
- ""
- "§fRight-Click to the last page"
previous-page: # only show has previous page
==: org.bukkit.inventory.ItemStack
type: ARROW
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fPrevious Page"
lore:
- ""
- "§fRight-Click to the first page"
functions:
# Whether to add a prefix to the top of the head,
# this method uses the scoreboard above the head,
# please turn it off if there is a conflict.
OnNamePrefix: true
# Automatic prefix select.
# When the player does not choose a prefix by himself,
# the prefix with the highest weight will be used automatically
autoUsePrefix: true
Sounds:
# Format is [SOUND_NAME:Volume:Pitch] or [SOUND_NAME:Volume] or [SOUND_NAME]
openGUI: "BLOCK_NOTE_BLOCK_PLING:1:1"
guiClick: "UI_BUTTON_CLICK"
prefixChange: "ENTITY_VILLAGER_YES"
prefixExpired: "ENTITY_VILLAGER_NO"
# The default prefix's weight is 0.
defaultPrefix:
name: "Default prefix"
content: "&b"
itemNotUsing:
==: org.bukkit.inventory.ItemStack
type: NAME_TAG
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fThe default prefix §f(Click to select)"
lore:
- ""
- "§a➥ Click to use"
itemUsing:
==: org.bukkit.inventory.ItemStack
type: NAME_TAG
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§fThe default prefix"
lore:
- ""
- "§a✔ Selected"
@@ -0,0 +1,71 @@
# identifier [Necessary]
# This will be used for data-storage.
identifier: "pro"
# Name [Necessary]
# Use in messages.
name: "&b&lPro&b"
# Content [Necessary]
# Use in Placeholders
content: "§b§lPro §b"
# Weight [Necessary]
# used for sorting in the GUI and TabList
# In GUI : the larger is displayed at the back
# At TabList : the larger is displayed at the top
weight: 1
# Permission [Unnecessary]
# If there is no permission for detection, everyone can use it,
# which means there is no need to configure "itemNoPermission"
# (because it is impossible to display items without permission at all)
permission: "yc.vip"
# itemHasPermission [Necessary]
# This Item will be displayed when player has permission
itemHasPermission:
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lVIP Prefix"
lore:
- ""
- "§a➥ Click to use"
# itemUsing [Unnecessary]
# This Item will be displayed when the prefix is selected.
# If there is no such configuration, it will automatically display "itemHasPermission".
itemUsing:
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lVIP Prefix"
enchants:
PROTECTION_ENVIRONMENTAL: 1 #Add an enchantment so it looks like its selected
lore:
- ""
- "§a✔ Selected"
# itemNoPermission [Unnecessary]
# If player doesn't have the permission,this item will be displayed.
# If this item is not configured, it will not be displayed in the GUI when the player does not have permission to use it.
itemNoPermission:
==: org.bukkit.inventory.ItemStack
type: INK_SACK
damage: 8
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lVIP §c(Buy it!)"
lore:
- ""
- "§e✯ Buy the VIP to use it!"
+19
View File
@@ -0,0 +1,19 @@
selected:
- "&7You have selected the &f%(name) &7as current prefix."
expired:
- "&7Your prefix &f%(oldName) &7has expired,"
- "&7Now the prefix is changed to &f%(newName) &7."
reload:
- "&a&lReload completed&7costs &f%(time)ms&7."
help:
- "&3&lUserPrefixAdmin &fHelp"
- "&8#/upa&f list"
- "&8- &7Show configured prefixes."
- "&8#/upa&f reload"
- "&8- &7Reload configuration."
list-title:
- "&3&lUserPrefixAdmin &fList"
list-value:
- "&8#%(weight) &f%(identifier)"
- "&8- &7Name &r%(name) &7Perm &r%(permission)"
- "&8- &7Example&r %(content) %(sender_name)"
+19
View File
@@ -0,0 +1,19 @@
selected:
- "&7您选择了 &f%(name) &7作为当前显示的前缀。"
expired:
- "&7您先前使用的前缀 &f%(oldName) &7已到期。"
- "&7现在已为您重新调整为 &f%(newName) &7。"
reload:
- "&a&l重载完成!&7共耗时 &f%(time)ms&7。"
help:
- "&3&l用户前缀系统 &f帮助"
- "&8#/upa&f list"
- "&8- &7查看当前前缀列表。"
- "&8#/upa&f reload"
- "&8- &7重载前缀配置。"
list-title:
- "&3&l用户前缀系统 &f前缀列表"
list-value:
- "&8#%(weight) &f%(identifier)"
- "&8- &7显示名 &r%(name) &7权限 &r%(permission)"
- "&8- &7内容示例&r %(content) %(sender_name)"
+1
View File
@@ -5,6 +5,7 @@ authors:
- Carm - Carm
- YourCraft - YourCraft
- SakuraGame - SakuraGame
website: "https://github.com/CarmJos/UserPrefix"
depend: depend:
- LuckPerms - LuckPerms
softdepend: softdepend:
@@ -0,0 +1,78 @@
# 唯一标识 [必须]
# 将用于记录玩家所选的前缀,以及用于数据的缓存。
# 必须 必须 必须 保持唯一!
identifier: "pro"
# 名字 [必须]
# 切换的时候左下角会弹提示 用的就是这个名字
name: "&b&lPro&b"
# 内容 [必须]
# 显示在名字前面的内容
content: "§b§lPro §b"
# 权重 [必须]
# 用于GUI、TabList的排序和自动前缀显示
# 在GUI中,权重越高的会显示在越后面
# 在TabList中,权重越高的会显示在越上面
weight: 1
# 检测的权限 [非必须]
# 如果没有就是人人都能用,也代表不用配置“itemNoPermission”了(因为压根不可能显示没权限时候的物品)
permission: "yc.pro"
# 有权限时显示的物品 [必须]
# 当用户有权限且未选中时,会显示该物品
itemHasPermission: #
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a➥ 点击切换到该前缀"
# 正在使用时显示的物品 [非必需]
# 当用户正在使用时会显示这个物品,不配置即自动加载“itemHasPermission”
itemUsing:
==: org.bukkit.inventory.ItemStack
type: DIAMOND
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro §b会员前缀"
enchants:
PROTECTION_ENVIRONMENTAL: 1 #加一个附魔这样看上去就像是选中了的
lore:
- "§7Pro会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- ""
- "§a✔ 您正在使用该前缀"
# 没有权限时显示的物品 [非必需]
# 如果没有权限就会显示这个item。如果不配置该物品,则玩家没有使用权限时不会显示在GUI里面。
itemNoPermission:
==: org.bukkit.inventory.ItemStack
type: INK_SACK
damage: 8
meta:
==: ItemMeta
meta-type: UNSPECIFIC
display-name: "§b§lPro+ §b会员前缀 §c(未拥有)"
lore:
- "§7Pro+会员专属称号"
- ""
- "§f尊贵的Pro会员专属称号。"
- "§f您将获得多种特权与更好的游戏体验。"
- "§f您可以输入 §b/vip §f指令查看详细特权!"
- ""
- "§e✯ 加入Pro+会员以使用该前缀!"