Compare commits

...
93 Commits
Author SHA1 Message Date
RoinujNosde 1c457ce552 feat: redirect commands to GUI 2022-11-29 19:51:33 -03:00
Minat0_ 8fa465da38 fix: missing getHandlerList on HomeRegroupEvent (#338) 2022-11-29 14:48:31 -03:00
RoinujNosde 56c7908c33 fix(bungee): error deserializing clan banners 2022-11-23 20:14:14 -03:00
RoinujNosde fc81e76521 fix: added check for clan_member on land commands 2022-11-18 19:21:01 -03:00
RoinujNosde f7fe5c4ad4 refactor: ignore unknown subchannels 2022-11-08 20:19:57 -03:00
RoinujNosde 8f4f763c37 refactor: added debug messages to BungeeManager 2022-11-04 23:15:09 -03:00
RoinujNosde 7a37382264 fix: default ranks were getting re-added on config load 2022-11-03 20:37:29 -03:00
RoinujNosde 7f9d133051 fix: channel auto creation setting not respected on join/link 2022-11-02 14:55:00 -03:00
RoinujNosde 26ba9f7329 fix: attempt at fixing NPE on getAllClanPlayers 2022-11-01 21:43:31 -03:00
Minat0_ d8cb61b0fc fix: money was not given back when channel creation failed (#336) 2022-10-31 18:39:26 -03:00
Minat0_ 3f1b06dcf9 fix: wrong path of discord economy section (#334) 2022-10-31 17:14:10 -03:00
WolfBot b043eb0742 chore(master): release 2.18.1-SNAPSHOT (#331) 2022-10-14 18:15:11 -03:00
github-actions[bot]andWolfBot 7691a4b719 chore(master): release 2.18.0 (#318)
Co-authored-by: WolfBot <112733600+bot-wolf@users.noreply.github.com>
2022-10-14 18:13:47 -03:00
Edson Passos 87ece22036 feat(lang): new crowdin updates (#319) 2022-10-14 18:10:47 -03:00
RoinujNosde f7e7ec6624 fix: removes duplicate /clan from help 2022-10-03 19:59:02 -03:00
RoinujNosde 25197cdd72 feat: add help-size config 2022-09-30 18:43:00 -03:00
Edson Passos 30a501c063 fix: ConfigurationSerializableAdapter NPE 2022-09-27 10:22:47 -03:00
RoinujNosde f14c425488 fix: NPE while purging data 2022-09-24 19:43:14 -03:00
Edson Passos cc2e32984d ci: added modrinth action 2022-09-20 20:07:56 -03:00
Edson Passos 2c9b0f98fe feat: Improves Bungee support (#327) 2022-09-17 11:22:11 -03:00
Edson Passos f484bc16c6 fix: set useSSL to false 2022-08-30 08:30:42 -03:00
RoinujNosde 37f0ecff50 fix: supports '.' and '*' as username prefix by default 2022-08-28 12:33:01 -03:00
Minat0_ c8969f2196 chore: update dependency version at README.md (#329) 2022-08-28 12:03:20 -03:00
Edson Passos b9c3cfd640 ci: adds name to job 2022-08-24 22:02:56 -03:00
RoinujNosde a440834347 feat: adds starter-ranks
A list of ranks, defined in the config, which are added to new clans
2022-08-16 19:09:10 -03:00
RoinujNosde 1adec0b89d fix: changes size of some frames for better visualization on Bedrock 2022-08-15 20:27:53 -03:00
RoinujNosde d56a0a979a feat: adds permission to bypass the teleport delay
Node: simpleclans.vip.teleport-delay
2022-08-15 20:18:53 -03:00
RoinujNosde af07988103 fix: getPastClans() preserves the insertion order 2022-08-15 19:37:17 -03:00
Edson Passos 96a13d8d6c fix: updates join date when joining a clan (#326) 2022-08-15 11:33:14 -03:00
Edson Passos 2a1ad5b5c8 fix: removes rank and join date on disband 2022-08-15 10:28:50 -03:00
RoinujNosde 1311423a17 refactor: changed members list to <ClanPlayer> 2022-08-01 19:38:50 -03:00
RoinujNosde 59e9c4caed refactor: changed clanPlayers map to <UUID, ClanPlayer> 2022-08-01 19:17:00 -03:00
RoinujNosde 4ab53d1613 perf: improved UUID lookup performance 2022-07-11 22:55:13 -03:00
RoinujNosde 2ea744443f feat: added method for registering protection providers 2022-06-27 18:58:05 -03:00
Edson Passos 8bd8bb6466 ci: disable fork on release-please 2022-06-24 19:29:58 -03:00
Minat0_ e7f756f306 fix: NPE while sending a message to spies (#322) 2022-06-24 19:27:34 -03:00
Edson Passos b7961acd5c ci: use fork on release-please 2022-06-12 15:12:43 -03:00
RoinujNosde c47289c5bf fix: NPE while collecting fees
ClanPlayer#toPlayer() returns null when the player is not connected
2022-06-12 15:10:32 -03:00
Edson Passos 7769060f4d ci: updated release-please token
This fixes actions listening to "release" not running
2022-06-10 19:35:52 -03:00
RoinujNosde a859928622 fix: NoClassDefFoundError in WorldGuard6Provider 2022-06-09 23:38:55 -03:00
RoinujNosde becb88b763 feat: adds PlayerHomeClearEvent
and fires PlayerHomeSetEvent when the mod command is used
2022-06-09 14:15:14 -03:00
RoinujNosde 711f81f3da ci: update java version
here we go again
2022-06-08 21:41:15 -03:00
RoinujNosde 7fae6f8b8a ci: added missing required input 2022-06-08 21:36:57 -03:00
RoinujNosde 62a8d304f4 ci: adds snapshots repository and udpated setup-jdk 2022-06-08 21:32:22 -03:00
Edson Passos fe8668abb0 Merge pull request #317 from RoinujNosde/release-please--branches--master
chore(master): release 2.17.1-SNAPSHOT
2022-06-08 21:04:55 -03:00
github-actions[bot] 36f5739f06 chore(master): release 2.17.1-SNAPSHOT 2022-06-09 00:01:26 +00:00
RoinujNosde f7465941b2 ci: updated crowdin.yml and publish actions 2022-06-08 21:00:08 -03:00
Edson Passos 2aa5b9aad3 bump version... 2022-06-08 20:20:55 -03:00
Edson Passos 51f82ba988 New Crowdin updates (#316) 2022-06-08 19:57:45 -03:00
Edson Passos 327bcf3980 v2.17.0 2022-06-08 19:45:19 -03:00
Edson Passos 5c3bb558cf feat(lang): new Crowdin updates (#295) 2022-06-08 19:27:22 -03:00
RoinujNosde c726e2bb3c feature: adds coordinates to Land 2022-06-07 14:27:17 -03:00
Edson Passos af6c72eda9 fix: war end via request 2022-06-05 12:53:56 -03:00
RoinujNosde d48c17f1f9 feature: adds permission FEE_BYPASS to ranks
removes simpleclans.member.bypass-fee
2022-05-31 19:14:00 -03:00
RoinujNosde 93eef5c727 fix: catches exceptions when creating Discord channels 2022-05-22 22:01:01 -03:00
RoinujNosde 714aa10701 fix: adds groups (Vault) to the global storage, instead of per world 2022-05-20 19:53:50 -03:00
Minat0_ b2d271b23b fix: don't confuse auto-group-groupname and auto-groups 2022-05-18 17:54:57 +03:00
RoinujNosde 7dad746269 fix: possibly improves performance of ClanPlayer lookup 2022-05-17 20:28:30 -03:00
RoinujNosde 37399cd50b fix: refactored ConfirmationPrompts 2022-05-10 20:03:09 -03:00
RoinujNosde 132eac98e2 fix: doesn't try saving Players with duplicate names 2022-05-09 20:21:15 -03:00
RoinujNosde ba68e8f70a fix: doesn't try saving Players with null names 2022-05-08 18:48:25 -03:00
RoinujNosde 0d3542b4aa Merge remote-tracking branch 'origin/dev' into dev 2022-05-08 17:40:28 -03:00
RoinujNosde 94eed8710c fix!: removed PlotSquared3Provider
Maven repo is down
2022-05-08 17:40:06 -03:00
RoinujNosde 0d3d4981c0 fix: removed PlotSquared3Provider
Maven repo is down
2022-05-08 17:35:56 -03:00
Minat0_ 73fa75fccc fix!: Log "API" when player is offline (#310) 2022-05-08 16:44:17 -03:00
RoinujNosde a855b51617 fix: pending invites could bypass the max members limit 2022-05-03 20:32:39 -03:00
RoinujNosde 83e7ad4ae1 fix: duplicate usernames logic 2022-05-02 21:24:18 -03:00
RoinujNosde 05cddb7e7f feature: adds ClanPlayerTeleportEvent 2022-04-08 14:23:05 -03:00
RoinujNosde 8d1ed8cf41 fix: refactored DBCore, added caller's stack trace to db exceptions 2022-04-05 20:00:33 -03:00
RoinujNosde f8862299f2 fix: optimizes player lookup by using Bukkit#getOfflinePlayers #306 2022-04-02 20:35:09 -03:00
RoinujNosde 1de339addc fix: parsing placeholders that return new placeholders 2022-03-30 19:23:39 -03:00
RoinujNosde e929b58cd7 fix: player not removed from Discord channel on kick #305 2022-03-17 18:55:42 -03:00
RoinujNosde 237755b5d5 fix: remove colors from logged chat messages 2022-03-13 20:02:47 -03:00
RoinujNosde c648343cdc fix: stop setting player locale on insert
The player has not set a language yet
2022-03-13 00:02:19 -03:00
RoinujNosde f34b9273cc fix: setting server's default language as the player's 2022-03-12 23:44:00 -03:00
Minat0_andRoinujNosde d07bc160e6 fix: Strips only Spy and Discord chats (#304)
Co-authored-by: RoinujNosde <edsonpassosjr@outlook.com>
2022-03-12 23:24:31 -03:00
RoinujNosde 6f1f919977 fix: NoSuchFieldException on PlayerHeadCacheTask 2022-03-11 18:13:11 -03:00
Edson Passos 12a5aa92bb fix: disallows 'k' format in tags by default 2022-03-08 12:11:28 -03:00
RoinujNosde 5d7ad0808d fix: checks for valid alphabet even for players with bypass permission 2022-03-06 10:58:02 -03:00
RoinujNosde ac0e2f2116 fix: checks for spaces in tag when ACCEPT_OTHER_ALPHABETS_LETTERS is enabled 2022-03-06 10:57:10 -03:00
Edson Passos 2d553234a3 Update maven.yml 2022-03-06 01:03:38 -03:00
RoinujNosde e4588fe1ef fix: error parsing username regex 2022-03-05 22:29:09 -03:00
RoinujNosde 4221cc2fa1 fix: teleporting to highest block if home is set on a slab #301 2022-03-05 22:18:49 -03:00
RoinujNosde 5db69775a3 feature: adds username regex to config 2022-03-04 20:40:40 -03:00
Minat0_ 88f61a150f Lack of permissions when auto-create is false (#300)
* fix: Lack of permissions when auto-create is false
2022-03-03 20:06:23 -03:00
Edson Passos f0df4435be Bump version 2022-03-02 15:09:53 -03:00
Minat0_andEdson Passos 05c0f734b5 Disband command requires confirmation (#299)
* build: Add maven dependency plugin

* feature: Disband command requires confirmation

* fix: Don't create clans (event) if auto-creation is false

* Updates env variable for testing purpose

* Makes confirm and decline methods abstract

* Testing dependency plugin config

Co-authored-by: Edson Passos <edsonpassosjr@outlook.com>
2022-03-02 17:03:49 +03:00
Edson Passos 4f0b721d49 Updates SCMessage with ChatEvent changes #298 2022-03-02 07:57:11 -03:00
RoinujNosde 3ebb041a3f Merge remote-tracking branch 'origin/dev' into dev 2022-02-26 22:13:47 -03:00
RoinujNosde 3b8dc4992d fix: first time players marked as "not played before" 2022-02-26 22:13:28 -03:00
Edson Passos 16be0c12a0 Fixes line breaks in changelog 2022-02-24 22:36:27 -03:00
Edson Passos 18c7c41ac4 Updated badges and repo info 2022-02-24 22:26:21 -03:00
Edson Passos cb201eb4b8 Update publish_reposilite.yml 2022-02-24 22:01:47 -03:00
137 changed files with 4350 additions and 1962 deletions

No files matched your search

+8 -8
View File
@@ -1,24 +1,23 @@
# This workflow will build a Java project with Maven
# For more information see: https://help.github.com/actions/language-and-framework-guides/building-and-testing-java-with-maven
name: Java CI Dev Build
name: CI
on:
push:
branches: [ dev ]
branches: [ master ]
pull_request:
branches: [ dev ]
branches: [ master ]
jobs:
build:
strategy:
fail-fast: false
fail-fast: true
max-parallel: 4
matrix:
java-version: [ 8, 11, 16 ]
java-version: [ 8, 11, 16, 17 ]
runs-on: ubuntu-latest
name: Java ${{ matrix.java-version }}
steps:
- name: Checkout
uses: actions/checkout@v2
@@ -27,9 +26,10 @@ jobs:
with:
java-version: "${{ matrix.java-version }}"
distribution: 'adopt'
cache: 'maven'
- name: Build with Maven
run: mvn -B -U package --file pom.xml
- name: Upload a Build Artifact
- name: Upload Build Artifact
if: "${{ matrix.java-version == 8 }}"
uses: actions/upload-artifact@v2
with:
+6 -4
View File
@@ -4,15 +4,16 @@ on:
types: [created]
jobs:
build:
publish:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Set up JDK 1.8
uses: actions/setup-java@v1
uses: actions/setup-java@v2
with:
java-version: 1.8
java-version: 8
cache: 'maven'
distribution: 'adopt'
- name: Build with Maven
run: mvn -B package --file pom.xml
- name: Upload artifact
@@ -23,6 +24,7 @@ jobs:
game_endpoint: minecraft
file_path: target/SimpleClans.jar
changelog: ${{ github.event.release.body }}
changelog_type: markdown
display_name: ${{ github.event.release.tag_name }}
game_versions: 8849,8503,7915,7667,7330,7105,6588,630,591,585,531
release_type: release
+31
View File
@@ -0,0 +1,31 @@
name: Publish to Modrinth
on:
release:
types: [created]
jobs:
publish:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Set up JDK 1.8
uses: actions/setup-java@v2
with:
java-version: 8
cache: 'maven'
distribution: 'adopt'
- name: Build with Maven
run: mvn -B package --file pom.xml
- name: Upload artifact
uses: RubixDev/modrinth-upload@v1.0.0
with:
token: ${{ secrets.MODRINTH_TOKEN }}
project_id: quLDfyDl
file_path: target/SimpleClans.jar
changelog: ${{ github.event.release.body }}
name: ${{ github.event.release.tag_name }}
version: ${{ github.event.release.tag_name }}
game_versions: 1.19,1.18,1.17,1.16,1.15,1.14,1.13,1.12,1.11,1.10,1.9,1.8
release_type: release
loaders: spigot
featured: true
+9 -8
View File
@@ -1,26 +1,27 @@
name: Publish to Reposilite
on:
release:
types: [created]
push:
branches:
- master
workflow_dispatch:
jobs:
build:
publish:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Set up JDK 1.8
uses: actions/setup-java@v1
uses: actions/setup-java@v2
with:
java-version: 1.8
java-version: 8
server-id: reposilite # Value of the distributionManagement/repository/id field of the pom.xml
server-username: MAVEN_USERNAME
server-password: MAVEN_PASSWORD
cache: 'maven'
distribution: 'adopt'
- name: Build with Maven
run: mvn -B package --file pom.xml
- name: Publish to Reposilite
run: mvn -B deploy
env:
+15
View File
@@ -0,0 +1,15 @@
on:
push:
branches:
- master
name: release-please
jobs:
release-please:
runs-on: ubuntu-latest
steps:
- uses: google-github-actions/release-please-action@v3
with:
release-type: maven
package-name: SimpleClans
token: ${{ secrets.PAT_TOKEN }}
fork: false
+35
View File
@@ -0,0 +1,35 @@
# Changelog
## [2.18.0](https://github.com/RoinujNosde/SimpleClans/compare/v2.17.0...v2.18.0) (2022-10-14)
### Features
* add help-size config ([25197cd](https://github.com/RoinujNosde/SimpleClans/commit/25197cdd729cea63d7e223dc1e0aaef830613327))
* added method for registering protection providers ([2ea7444](https://github.com/RoinujNosde/SimpleClans/commit/2ea744443f502970b15859818e9d5e45ca69d453))
* adds permission to bypass the teleport delay ([d56a0a9](https://github.com/RoinujNosde/SimpleClans/commit/d56a0a979a47a140115742518e934a2469e6f880))
* adds PlayerHomeClearEvent ([becb88b](https://github.com/RoinujNosde/SimpleClans/commit/becb88b763380bed5a2e1dd209c32c8363a7f88b))
* adds starter-ranks ([a440834](https://github.com/RoinujNosde/SimpleClans/commit/a4408343479d7efa6ae5a65894f8b822ecd47ebb))
* Improves Bungee support ([#327](https://github.com/RoinujNosde/SimpleClans/issues/327)) ([2c9b0f9](https://github.com/RoinujNosde/SimpleClans/commit/2c9b0f98fe3942ea74190c1a81d61be2c8647db8))
* **lang:** new crowdin updates ([#319](https://github.com/RoinujNosde/SimpleClans/issues/319)) ([87ece22](https://github.com/RoinujNosde/SimpleClans/commit/87ece22036fb674c8c362b6a1b86fe884543e6ad))
### Bug Fixes
* changes size of some frames for better visualization on Bedrock ([1adec0b](https://github.com/RoinujNosde/SimpleClans/commit/1adec0b89d676767cdb94dcdf91ba37a231eb4a8))
* ConfigurationSerializableAdapter NPE ([30a501c](https://github.com/RoinujNosde/SimpleClans/commit/30a501c063aa9dbcf596df83adc2b15baf0e4bb9))
* getPastClans() preserves the insertion order ([af07988](https://github.com/RoinujNosde/SimpleClans/commit/af079881030bd299b9bae1ebf0cc62353af7e6fc))
* NoClassDefFoundError in WorldGuard6Provider ([a859928](https://github.com/RoinujNosde/SimpleClans/commit/a8599286225ba603ea124b8b52510245b94ffd24))
* NPE while collecting fees ([c47289c](https://github.com/RoinujNosde/SimpleClans/commit/c47289c5bf8113a9d6a8e1ee74a5afb0358647b6))
* NPE while purging data ([f14c425](https://github.com/RoinujNosde/SimpleClans/commit/f14c42548846feef01b484acbb5f02bcbcabd8db))
* NPE while sending a message to spies ([#322](https://github.com/RoinujNosde/SimpleClans/issues/322)) ([e7f756f](https://github.com/RoinujNosde/SimpleClans/commit/e7f756f3063c646e21415e08eea73f123d2818a0))
* removes duplicate /clan from help ([f7e7ec6](https://github.com/RoinujNosde/SimpleClans/commit/f7e7ec66243359e26d3c456a9740a53753951c48))
* removes rank and join date on disband ([2a1ad5b](https://github.com/RoinujNosde/SimpleClans/commit/2a1ad5b5c8d2937a8ee6dd6f7f43d85c86f08307))
* set useSSL to false ([f484bc1](https://github.com/RoinujNosde/SimpleClans/commit/f484bc16c6176ccd13e05aae2169400e7bcf5d62))
* supports '.' and '*' as username prefix by default ([37f0ecf](https://github.com/RoinujNosde/SimpleClans/commit/37f0ecff506d06f3047e3598848117a14c2b7ead))
* updates join date when joining a clan ([#326](https://github.com/RoinujNosde/SimpleClans/issues/326)) ([96a13d8](https://github.com/RoinujNosde/SimpleClans/commit/96a13d8d6cc18c91d4dee20dd632cd5d65db5213))
### Performance Improvements
* improved UUID lookup performance ([4ab53d1](https://github.com/RoinujNosde/SimpleClans/commit/4ab53d16135ecf5a4067b1a63d058da392dc5313))
+8 -7
View File
@@ -5,7 +5,7 @@ SimpleClans
Full featured clan system for PVP Minecraft Servers!
[![Build Status](https://travis-ci.com/RoinujNosde/SimpleClans.svg?branch=master)](https://travis-ci.com/RoinujNosde/SimpleClans)
[![Build Status](https://img.shields.io/jenkins/build?jobUrl=https%3A%2F%2Fci.roinujnosde.me%2Fjob%2FSimpleClans%2F)](https://ci.roinujnosde.me/job/SimpleClans/)
[![Spiget Downloads](https://img.shields.io/spiget/downloads/71242)](https://www.spigotmc.org/resources/simpleclans.71242/)
[![Issues](https://img.shields.io/github/issues/RoinujNosde/SimpleClans.svg)](https://github.com/RoinujNosde/SimpleClans/issues)
[![Crowdin](https://badges.crowdin.net/simpleclans/localized.svg)](https://crowdin.com/project/simpleclans)
@@ -50,8 +50,8 @@ Including SimpleClans with Maven:
```xml
<repositories>
<repository>
<id>codemc-repo</id>
<url>https://repo.codemc.org/repository/maven-public</url>
<id>roinujnosde-repo</id>
<url>https://repo.roinujnosde.me/releases/</url>
</repository>
</repositories>
```
@@ -60,7 +60,7 @@ Including SimpleClans with Maven:
<dependency>
<groupId>net.sacredlabyrinth.phaed.simpleclans</groupId>
<artifactId>SimpleClans</artifactId>
<version>2.15.0</version> <!-- You can find the latest version at the bottom -->
<version>2.17.0</version> <!-- You can find the latest version at the bottom -->
<scope>provided</scope>
</dependency>
</dependencies>
@@ -70,15 +70,16 @@ Using Gradle:
```groovy
repositories {
maven {
url "https://repo.codemc.org/repository/maven-public"
url "https://repo.roinujnosde.me/releases/"
}
}
dependencies {
compileOnly "net.sacredlabyrinth.phaed.simpleclans:SimpleClans:2.15.0"
compileOnly "net.sacredlabyrinth.phaed.simpleclans:SimpleClans:2.17.0"
}
```
Feel free to learn our [Javadoc](https://ci.roinujnosde.me/job/SimpleClans/Javadoc/).
##### Latest version:
[![](https://jitpack.io/v/roinujnosde/simpleclans.svg?label=Maven)]()
[![Maven metadata URL](https://img.shields.io/maven-metadata/v?metadataUrl=https%3A%2F%2Frepo.roinujnosde.me%2Freleases%2Fnet%2Fsacredlabyrinth%2Fphaed%2Fsimpleclans%2FSimpleClans%2Fmaven-metadata.xml)](https://repo.roinujnosde.me/#/releases/net/sacredlabyrinth/phaed/simpleclans/SimpleClans)
##### API Examples
* [Examples of how to use the API](https://simpleclans.gitbook.io/simpleclans/other/simpleclans-api)
+1 -4
View File
@@ -14,7 +14,6 @@
<orderEntry type="library" scope="PROVIDED" name="Maven: org.spigotmc:spigot-api:1.16.4-R0.1-SNAPSHOT" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: commons-lang:commons-lang:2.6" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.google.guava:guava:21.0" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.google.code.gson:gson:2.8.0" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: net.md-5:bungeecord-chat:1.16-R0.3" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: org.yaml:snakeyaml:1.26" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.github.MilkBowl:VaultAPI:1.7" level="project" />
@@ -86,9 +85,6 @@
<orderEntry type="library" scope="PROVIDED" name="Maven: org.flywaydb:flyway-core:3.0" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q:commandbook:2.3" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.github.TechFortress:GriefPrevention:16.17.1" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.plotsquared:plotsquared-api:3.1" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.plotsquared:plotsquared-bukkitapi:3.1" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: net.milkbowl.vault:VaultAPI:1.7" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.discordsrv:discordsrv:1.24.1-SNAPSHOT" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: net.dv8tion:JDA:4.3.0_349" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: com.google.code.findbugs:jsr305:3.0.2" level="project" />
@@ -144,5 +140,6 @@
<orderEntry type="library" scope="PROVIDED" name="Maven: com.zaxxer:HikariCP:4.0.3" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: io.github.bananapuncher714:nbteditor:7.16.1" level="project" />
<orderEntry type="library" scope="PROVIDED" name="Maven: de.eldoria:eldo-util:1.9.1" level="project" />
<orderEntry type="library" name="Maven: com.google.code.gson:gson:2.9.1" level="project" />
</component>
</module>
+4
View File
@@ -1,3 +1,7 @@
pull_request_title: "feat(lang): new crowdin updates"
pull_request_labels: ["l10n"]
commit_message: "feat(lang): new translations for %language%"
append_commit_message: false
files:
- source: src/main/resources/messages.properties
translation: /src/main/resources/%file_name%_%locale_with_underscore%.%file_extension%
+34 -74
View File
@@ -4,7 +4,7 @@
<groupId>net.sacredlabyrinth.phaed.simpleclans</groupId>
<artifactId>SimpleClans</artifactId>
<name>SimpleClans</name>
<version>2.16.0</version>
<version>2.18.1-SNAPSHOT</version>
<url>https://www.spigotmc.org/resources/simpleclans.71242/</url>
<build>
<resources>
@@ -29,7 +29,6 @@
<target>1.8</target>
<showDeprecation>true</showDeprecation>
<showWarnings>true</showWarnings>
<fork>true</fork>
<compilerArgs>
<arg>-parameters</arg>
</compilerArgs>
@@ -76,6 +75,10 @@
<pattern>com.cryptomorin.xseries</pattern>
<shadedPattern>net.sacredlabyrinth.phaed.simpleclans.xseries</shadedPattern>
</relocation>
<relocation>
<pattern>com.google.gson</pattern>
<shadedPattern>net.sacredlabyrinth.phaed.simpleclans.gson</shadedPattern>
</relocation>
</relocations>
<artifactSet>
<excludes>
@@ -84,6 +87,31 @@
</artifactSet>
</configuration>
</plugin>
<plugin>
<artifactId>maven-dependency-plugin</artifactId>
<version>3.2.0</version>
<executions>
<execution>
<id>copy-installed</id>
<phase>package</phase>
<goals>
<goal>copy</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>${project.groupId}</groupId>
<artifactId>${project.artifactId}</artifactId>
<version>${project.version}</version>
<type>${project.packaging}</type>
</artifactItem>
</artifactItems>
<outputDirectory>${env.TEST_SERVER}\plugins</outputDirectory>
<silent>true</silent>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>pl.project13.maven</groupId>
<artifactId>git-commit-id-plugin</artifactId>
@@ -142,10 +170,6 @@
<id>sk89q-repo</id>
<url>https://maven.enginehub.org/repo/</url>
</repository>
<repository>
<id>plotsquared</id>
<url>https://plotsquared.com/mvn/</url>
</repository>
<repository>
<id>Scarsz-Nexus</id>
<url>https://nexus.scarsz.me/content/groups/public/</url>
@@ -174,10 +198,6 @@
<artifactId>guava</artifactId>
<groupId>com.google.guava</groupId>
</exclusion>
<exclusion>
<artifactId>gson</artifactId>
<groupId>com.google.code.gson</groupId>
</exclusion>
<exclusion>
<artifactId>bungeecord-chat</artifactId>
<groupId>net.md-5</groupId>
@@ -200,18 +220,6 @@
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.googlecode.json-simple</groupId>
<artifactId>json-simple</artifactId>
<version>1.1.1</version>
<scope>provided</scope>
<exclusions>
<exclusion>
<artifactId>junit</artifactId>
<groupId>junit</groupId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>me.clip</groupId>
<artifactId>placeholderapi</artifactId>
@@ -274,54 +282,6 @@
<version>16.17.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.plotsquared</groupId>
<artifactId>plotsquared-api</artifactId>
<version>3.1</version>
<scope>provided</scope>
<exclusions>
<exclusion>
<artifactId>*</artifactId>
<groupId>com.sk89q.worldedit</groupId>
</exclusion>
<exclusion>
<artifactId>snakeyaml</artifactId>
<groupId>org.yaml</groupId>
</exclusion>
<exclusion>
<artifactId>gson</artifactId>
<groupId>com.google.code.gson</groupId>
</exclusion>
<exclusion>
<artifactId>guava</artifactId>
<groupId>com.google.guava</groupId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.plotsquared</groupId>
<artifactId>plotsquared-bukkitapi</artifactId>
<version>3.1</version>
<scope>provided</scope>
<exclusions>
<exclusion>
<artifactId>*</artifactId>
<groupId>com.sk89q.worldedit</groupId>
</exclusion>
<exclusion>
<artifactId>Core</artifactId>
<groupId>PlotSquared</groupId>
</exclusion>
<exclusion>
<artifactId>VaultAPI</artifactId>
<groupId>net.milkbowl.vault</groupId>
</exclusion>
<exclusion>
<artifactId>guava</artifactId>
<groupId>com.google.guava</groupId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.discordsrv</groupId>
<artifactId>discordsrv</artifactId>
@@ -437,12 +397,12 @@
</dependencies>
<distributionManagement>
<repository>
<id>codemc-releases</id>
<url>https://repo.codemc.io/repository/maven-releases/</url>
<id>reposilite</id>
<url>https://repo.roinujnosde.me/releases/</url>
</repository>
<snapshotRepository>
<id>codemc-snapshots</id>
<url>https://repo.codemc.io/repository/maven-snapshots/</url>
<id>reposilite</id>
<url>https://repo.roinujnosde.me/snapshots/</url>
</snapshotRepository>
</distributionManagement>
<properties>
+44 -65
View File
@@ -1,9 +1,8 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>net.sacredlabyrinth.phaed.simpleclans</groupId>
<artifactId>SimpleClans</artifactId>
<version>2.16.2</version>
<version>2.18.1-SNAPSHOT</version>
<name>SimpleClans</name>
<url>https://www.spigotmc.org/resources/simpleclans.71242/</url>
@@ -36,7 +35,6 @@
<target>1.8</target>
<showDeprecation>true</showDeprecation>
<showWarnings>true</showWarnings>
<fork>true</fork>
<compilerArgs>
<arg>-parameters</arg>
</compilerArgs>
@@ -84,6 +82,10 @@
<pattern>com.cryptomorin.xseries</pattern>
<shadedPattern>net.sacredlabyrinth.phaed.simpleclans.xseries</shadedPattern>
</relocation>
<relocation>
<pattern>com.google.gson</pattern>
<shadedPattern>net.sacredlabyrinth.phaed.simpleclans.gson</shadedPattern>
</relocation>
</relocations>
<artifactSet>
<excludes>
@@ -101,6 +103,34 @@
</executions>
</plugin>
<!-- Dependency plugin -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>3.2.0</version>
<executions>
<execution>
<id>copy-installed</id>
<phase>package</phase>
<goals>
<goal>copy</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>${project.groupId}</groupId>
<artifactId>${project.artifactId}</artifactId>
<version>${project.version}</version>
<type>${project.packaging}</type>
</artifactItem>
</artifactItems>
<outputDirectory>${env.TEST_SERVER}\plugins</outputDirectory>
<silent>true</silent>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>pl.project13.maven</groupId>
<artifactId>git-commit-id-plugin</artifactId>
@@ -150,12 +180,6 @@
<version>1.7</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.googlecode.json-simple</groupId>
<artifactId>json-simple</artifactId>
<version>1.1.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.bstats</groupId>
<artifactId>bstats-bukkit</artifactId>
@@ -207,52 +231,6 @@
<version>16.17.1</version>
<scope>provided</scope>
</dependency>
<!-- <dependency>-->
<!-- <groupId>com.plotsquared</groupId>-->
<!-- <artifactId>PlotSquared-Core</artifactId>-->
<!-- <version>5.13.3</version>-->
<!-- <scope>provided</scope>-->
<!-- </dependency>-->
<!-- <dependency>-->
<!-- <groupId>com.plotsquared</groupId>-->
<!-- <artifactId>PlotSquared-Bukkit</artifactId>-->
<!-- <version>5.13.3</version>-->
<!-- <scope>provided</scope>-->
<!-- <exclusions>-->
<!-- <exclusion>-->
<!-- <groupId>*</groupId>-->
<!-- <artifactId>PlotSquared-Core</artifactId>-->
<!-- </exclusion>-->
<!-- </exclusions>-->
<!-- </dependency>-->
<dependency>
<groupId>com.plotsquared</groupId>
<artifactId>plotsquared-api</artifactId>
<version>3.1</version>
<scope>provided</scope>
<exclusions>
<exclusion>
<groupId>com.sk89q.worldedit</groupId>
<artifactId>*</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.plotsquared</groupId>
<artifactId>plotsquared-bukkitapi</artifactId>
<version>3.1</version>
<scope>provided</scope>
<exclusions>
<exclusion>
<groupId>com.sk89q.worldedit</groupId>
<artifactId>*</artifactId>
</exclusion>
<exclusion>
<groupId>PlotSquared</groupId>
<artifactId>Core</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.discordsrv</groupId>
<artifactId>discordsrv</artifactId>
@@ -265,6 +243,11 @@
<version>4.351</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.9.1</version>
</dependency>
</dependencies>
<!-- Repositories -->
@@ -293,14 +276,6 @@
<id>sk89q-repo</id>
<url>https://maven.enginehub.org/repo/</url>
</repository>
<!-- <repository>-->
<!-- <id>IntellectualSites</id>-->
<!-- <url>https://mvn.intellectualsites.com/content/groups/public/</url>-->
<!-- </repository>-->
<repository>
<id>plotsquared</id>
<url>https://plotsquared.com/mvn/</url>
</repository>
<repository>
<id>Scarsz-Nexus</id>
<url>https://nexus.scarsz.me/content/groups/public/</url>
@@ -326,5 +301,9 @@
<id>reposilite</id>
<url>https://repo.roinujnosde.me/releases/</url>
</repository>
<snapshotRepository>
<id>reposilite</id>
<url>https://repo.roinujnosde.me/snapshots/</url>
</snapshotRepository>
</distributionManagement>
</project>
</project>
@@ -3,7 +3,6 @@ package net.sacredlabyrinth.phaed.simpleclans;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import org.bukkit.ChatColor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -554,12 +553,7 @@ public class ChatBlock {
return;
}
Player player = receiver.toPlayer();
if (player == null) {
return;
}
player.sendMessage(ChatUtils.parseColors(msg));
SimpleClans.getInstance().getProxyManager().sendMessage(receiver.getName(), ChatUtils.parseColors(msg));
}
// ClanCommands#setbanner, LandCommands#Allow/BlockCommand/verify, StaffCommands#kick, etc
@@ -6,7 +6,7 @@ import net.sacredlabyrinth.phaed.simpleclans.events.*;
import net.sacredlabyrinth.phaed.simpleclans.hooks.papi.Placeholder;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankLog;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankLogger;
import net.sacredlabyrinth.phaed.simpleclans.managers.PermissionsManager;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import org.bukkit.Bukkit;
@@ -53,7 +53,7 @@ public class Clan implements Serializable, Comparable<Clan> {
private List<String> allies = new ArrayList<>();
private List<String> rivals = new ArrayList<>();
private List<String> bb = new ArrayList<>();
private final List<String> members = new ArrayList<>();
private final List<ClanPlayer> members = new ArrayList<>();
private Flags flags = new Flags(null);
private boolean feeEnabled;
private List<Rank> ranks = new ArrayList<>();
@@ -128,7 +128,7 @@ public class Clan implements Serializable, Comparable<Clan> {
/**
* Deposits money to the clan
*/
public EconomyResponse deposit(@Nullable CommandSender sender, @NotNull Cause cause, double amount) {
public EconomyResponse deposit(@NotNull BankOperator sender, @NotNull Cause cause, double amount) {
EconomyResponse response = null;
if (amount < 0) {
@@ -162,7 +162,7 @@ public class Clan implements Serializable, Comparable<Clan> {
/**
* Withdraws money from the clan
*/
public EconomyResponse withdraw(@Nullable CommandSender sender, @NotNull Cause cause, double amount) {
public EconomyResponse withdraw(@NotNull BankOperator sender, @NotNull Cause cause, double amount) {
EconomyResponse response = null;
if (amount < 0) {
@@ -250,14 +250,15 @@ public class Clan implements Serializable, Comparable<Clan> {
*
* @param balance the balance to set
*/
public void setBalance(double balance) {
setBalance(null, Cause.API, SET, balance);
private void setBalance(double balance) {
setBalance(BankOperator.INTERNAL, Cause.INTERNAL, SET, balance);
}
public EconomyResponse setBalance(@Nullable CommandSender updater, @NotNull Cause cause, @NotNull BankLogger.Operation operation, double balance) {
public EconomyResponse setBalance(@NotNull BankOperator operator, @NotNull Cause cause,
@NotNull BankLogger.Operation operation, double balance) {
EconomyResponse response = SUCCESS;
ClanBalanceUpdateEvent event = new ClanBalanceUpdateEvent(updater, this, getBalance(), balance, cause);
ClanBalanceUpdateEvent event = new ClanBalanceUpdateEvent(operator, this, getBalance(), balance, cause);
Bukkit.getPluginManager().callEvent(event);
if (event.isCancelled()) {
response = CANCELLED;
@@ -266,7 +267,7 @@ public class Clan implements Serializable, Comparable<Clan> {
this.balance = event.getNewBalance();
if (cause != Cause.LOADING) {
if (operation == SET) {
SimpleClans.getInstance().getBankLogger().log(new BankLog(updater, this, response, SET, cause, balance));
SimpleClans.getInstance().getBankLogger().log(new BankLog(operator, this, response, SET, cause, balance));
}
SimpleClans.getInstance().getStorageManager().updateClan(this);
}
@@ -383,17 +384,22 @@ public class Clan implements Serializable, Comparable<Clan> {
* @return confirmation
*/
public boolean isMember(Player player) {
return members.contains(player.getUniqueId().toString());
return isMember(player.getUniqueId());
}
/**
* Check if the player is a member of this clan
*
* @param playerUniqueId the Player's UUID
* @param uuid the Player's UUID
* @return confirmation
*/
public boolean isMember(UUID playerUniqueId) {
return members.contains(playerUniqueId.toString());
public boolean isMember(UUID uuid) {
for (ClanPlayer cp : members) {
if (cp.getUniqueId().equals(uuid)) {
return true;
}
}
return false;
}
@SuppressWarnings("deprecation")
@@ -520,23 +526,16 @@ public class Clan implements Serializable, Comparable<Clan> {
* (used internally)
*/
public void importMember(ClanPlayer cp) {
String uuid;
if (cp.getUniqueId() != null) {
uuid = cp.getUniqueId().toString();
} else {
return;
}
if (!members.contains(uuid)) {
members.add(uuid);
if (!members.contains(cp)) {
members.add(cp);
}
}
/**
* (used internally)
*/
public void removeMember(UUID playerUniqueId) {
members.remove(playerUniqueId.toString());
public void removeMember(UUID uuid) {
members.removeIf(cp -> cp.getUniqueId().equals(uuid));
}
/**
@@ -732,12 +731,8 @@ public class Clan implements Serializable, Comparable<Clan> {
* @return the formatted leaders string
*/
public String getLeadersString(String prefix, String sep) {
return members.stream().
map(member -> SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member))).
filter(Objects::nonNull).
filter(ClanPlayer::isLeader).
map(clanPlayer -> prefix.concat(clanPlayer.getName())).
collect(Collectors.joining(sep));
return members.stream().filter(ClanPlayer::isLeader).map(ClanPlayer::getName).
collect(Collectors.joining(sep, prefix, ""));
}
/**
@@ -776,8 +771,10 @@ public class Clan implements Serializable, Comparable<Clan> {
* @return the fee payers
*/
public Set<ClanPlayer> getFeePayers() {
PermissionsManager permissions = SimpleClans.getInstance().getPermissionsManager();
return getNonLeaders().stream().filter(cp -> !permissions.has(cp.toPlayer(), "simpleclans.member.bypass-fee")).collect(Collectors.toSet());
return getMembers().stream().filter(cp -> !cp.isLeader()).filter(cp -> {
Rank rank = getRank(cp.getRankId());
return rank == null || !rank.getPermissions().contains(RankPermission.FEE_BYPASS.toString());
}).collect(Collectors.toSet());
}
/**
@@ -786,19 +783,7 @@ public class Clan implements Serializable, Comparable<Clan> {
* @return the members
*/
public List<ClanPlayer> getMembers() {
List<ClanPlayer> out = new ArrayList<>();
for (String member : members) {
ClanPlayer cp = SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member));
if (cp == null) {
continue;
}
out.add(cp);
}
Collections.sort(out);
return out;
return new ArrayList<>(members);
}
/**
@@ -808,22 +793,9 @@ public class Clan implements Serializable, Comparable<Clan> {
*/
@Placeholder(value = "onlinemembers_count", resolver = "list_size", config = "filter_vanished")
public List<ClanPlayer> getOnlineMembers() {
List<ClanPlayer> out = new ArrayList<>();
for (String member : members) {
ClanPlayer cp = SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member));
if (cp == null) {
continue;
}
if (cp.toPlayer() != null) {
out.add(cp);
}
}
return out;
return members.stream().filter(cp -> cp.toPlayer() != null).collect(Collectors.toList());
}
/**
* Get all leaders in the clan
*
@@ -831,20 +803,7 @@ public class Clan implements Serializable, Comparable<Clan> {
*/
@Placeholder(value = "leader_size", resolver = "list_size")
public List<ClanPlayer> getLeaders() {
List<ClanPlayer> out = new ArrayList<>();
for (String member : members) {
ClanPlayer cp = SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member));
if (cp == null) {
continue;
}
if (cp.isLeader()) {
out.add(cp);
}
}
return out;
return members.stream().filter(ClanPlayer::isLeader).collect(Collectors.toList());
}
/**
@@ -853,22 +812,7 @@ public class Clan implements Serializable, Comparable<Clan> {
* @return non leaders
*/
public List<ClanPlayer> getNonLeaders() {
List<ClanPlayer> out = new ArrayList<>();
for (String member : members) {
ClanPlayer cp = SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member));
if (cp == null) {
continue;
}
if (!cp.isLeader()) {
out.add(cp);
}
}
Collections.sort(out);
return out;
return members.stream().filter(cp -> !cp.isLeader()).collect(Collectors.toList());
}
/**
@@ -907,16 +851,10 @@ public class Clan implements Serializable, Comparable<Clan> {
if (members.isEmpty()) {
return 0;
}
double totalWeightedKills = 0;
int totalDeaths = 0;
for (String member : members) {
ClanPlayer cp = SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member));
if (cp == null) {
continue;
}
for (ClanPlayer cp : members) {
totalWeightedKills += cp.getWeightedKills();
totalDeaths += cp.getDeaths();
}
@@ -939,12 +877,7 @@ public class Clan implements Serializable, Comparable<Clan> {
return totalDeaths;
}
for (String member : members) {
ClanPlayer cp = SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member));
if (cp == null) {
continue;
}
for (ClanPlayer cp : members) {
totalDeaths += cp.getDeaths();
}
@@ -962,12 +895,7 @@ public class Clan implements Serializable, Comparable<Clan> {
return total;
}
for (String member : members) {
ClanPlayer cp = SimpleClans.getInstance().getClanManager().getClanPlayer(UUID.fromString(member));
if (cp == null) {
continue;
}
for (ClanPlayer cp : members) {
total += cp.getWeightedKills();
}
@@ -1052,6 +980,7 @@ public class Clan implements Serializable, Comparable<Clan> {
cp.removePastClan(getColorTag());
cp.setClan(this);
cp.setLeader(false);
cp.setJoinDate(new Date().getTime());
cp.setTrusted(SimpleClans.getInstance().getSettingsManager().is(CLAN_TRUST_MEMBERS_BY_DEFAULT));
if (defaultRank != null) {
cp.setRank(defaultRank);
@@ -1172,7 +1101,7 @@ public class Clan implements Serializable, Comparable<Clan> {
}
/**
* Remove an ally form the clan, and the clan from the ally
* Remove an ally from the clan, and the clan from the ally
*/
public void removeAlly(Clan ally) {
removeAlly(ally.getTag());
@@ -1223,7 +1152,7 @@ public class Clan implements Serializable, Comparable<Clan> {
*/
@Placeholder("is_anyonline")
public boolean isAnyOnline() {
return members.stream().map(UUID::fromString).map(Bukkit::getPlayer).anyMatch(Objects::nonNull);
return members.stream().anyMatch(cp -> cp.toPlayer() != null);
}
/**
@@ -1323,18 +1252,14 @@ public class Clan implements Serializable, Comparable<Clan> {
String message = SimpleClans.getInstance().getSettingsManager().getColored(CLANCHAT_ANNOUNCEMENT_COLOR) + msg;
for (ClanPlayer cp : getMembers()) {
Player pl = cp.toPlayer();
if (pl != null) {
ChatBlock.sendMessage(pl, message);
}
ChatBlock.sendMessage(cp, message);
}
SimpleClans.getInstance().getServer().getConsoleSender().sendMessage(AQUA + "[" + lang("clan.announce") + AQUA + "] " + AQUA + "[" + Helper.getColorName(playerName) + WHITE + "] " + message);
Bukkit.getConsoleSender().sendMessage(AQUA + "[" + lang("clan.announce") + AQUA + "] " + AQUA + "[" + Helper.getColorName(playerName) + WHITE + "] " + message);
}
/**
* Announce message to a all the leaders of a clan
* Announce message to all the leaders of a clan
*/
public void leaderAnnounce(String msg) {
String message = SimpleClans.getInstance().getSettingsManager().getColored(CLANCHAT_ANNOUNCEMENT_COLOR) + msg;
@@ -1342,13 +1267,9 @@ public class Clan implements Serializable, Comparable<Clan> {
List<ClanPlayer> leaders = getLeaders();
for (ClanPlayer cp : leaders) {
Player pl = cp.toPlayer();
if (pl != null) {
ChatBlock.sendMessage(pl, message);
}
ChatBlock.sendMessage(cp, message);
}
SimpleClans.getInstance().getServer().getConsoleSender().sendMessage(AQUA + "[" + lang("leader.announce") + AQUA + "] " + WHITE + message);
Bukkit.getConsoleSender().sendMessage(AQUA + "[" + lang("leader.announce") + AQUA + "] " + WHITE + message);
}
/**
@@ -1466,7 +1387,8 @@ public class Clan implements Serializable, Comparable<Clan> {
for (ClanPlayer cp : clanPlayers) {
if (cp.getTag().equals(getTag())) {
cp.setClan(null);
cp.setJoinDate(0);
cp.setRank(null);
if (isVerified()) {
cp.addPastClan(getColorTag() + (cp.isLeader() ? DARK_RED + "*" : ""));
}
@@ -1614,6 +1536,8 @@ public class Clan implements Serializable, Comparable<Clan> {
flags.put("homeYaw", home != null ? home.getYaw() : 0);
String world = home != null && home.getWorld() != null ? home.getWorld().getName() : "";
flags.put("homeWorld", world);
String name = SimpleClans.getInstance().getProxyManager().getServerName();
flags.put("homeServer", name);
SimpleClans.getInstance().getStorageManager().updateClan(this);
}
@@ -1632,11 +1556,8 @@ public class Clan implements Serializable, Comparable<Clan> {
double z = flags.getNumber("homeZ").doubleValue();
float yaw = flags.getNumber("homeYaw").floatValue();
float pitch = flags.getNumber("homePitch").floatValue();
Location location = new Location(world, x, y, z, yaw, pitch);
if (!Helper.isAir(location.getBlock().getType(), location.clone().add(0, 1, 0).getBlock().getType())) {
location.setY(world.getHighestBlockYAt(location) + 1);
}
return location;
return new Location(world, x, y, z, yaw, pitch);
}
public String getTagLabel(boolean isLeader) {
@@ -38,7 +38,7 @@ public class ClanPlayer implements Serializable, Comparable<ClanPlayer> {
private int deaths;
private long lastSeen;
private long joinDate;
private Set<String> pastClans = new HashSet<>();
private final Set<String> pastClans = new LinkedHashSet<>();
private final Map<String, Long> resignTimes = new HashMap<>();
private @Nullable VoteResult vote;
private Flags flags = new Flags(null);
@@ -509,8 +509,7 @@ public class ClanPlayer implements Serializable, Comparable<ClanPlayer> {
}
public String getLastSeenString(@Nullable CommandSender sender) {
Player player = toPlayer();
if (player != null && player.isOnline() && !VanishUtils.isVanished(sender, player)) {
if (!VanishUtils.isVanished(sender, this)) {
return lang("online", sender);
}
return new java.text.SimpleDateFormat("MMM dd, ''yy h:mm a").format(new Date(lastSeen));
@@ -537,10 +536,11 @@ public class ClanPlayer implements Serializable, Comparable<ClanPlayer> {
/**
* (used internally)
*
* @param PackedPastClans the PackedPastClans to set
* @param packedPastClans the packedPastClans to set
*/
public void setPackedPastClans(String PackedPastClans) {
pastClans = Helper.fromArrayToSet(PackedPastClans.split("[|]"));
public void setPackedPastClans(String packedPastClans) {
String[] clans = packedPastClans.split("\\|");
Collections.addAll(pastClans, clans);
}
/**
@@ -616,7 +616,7 @@ public class ClanPlayer implements Serializable, Comparable<ClanPlayer> {
/**
* Sets the resign times (does not update to db)
*/
public void setResignTimes(Map<String, Long> resignTimes) {
public void setResignTimes(@Nullable Map<String, Long> resignTimes) {
if (resignTimes != null) {
final int cooldown = SimpleClans.getInstance().getSettingsManager().getInt(REJOIN_COOLDOWN);
resignTimes.forEach((k, v) -> {
@@ -845,10 +845,7 @@ public class ClanPlayer implements Serializable, Comparable<ClanPlayer> {
flags.put("rank", rank == null ? "" : rank);
}
public @NotNull Locale getLocale() {
if (locale == null) {
return SimpleClans.getInstance().getSettingsManager().getLanguage();
}
public @Nullable Locale getLocale() {
return locale;
}
@@ -1,36 +1,34 @@
package net.sacredlabyrinth.phaed.simpleclans;
import com.google.gson.Gson;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import org.json.simple.JSONValue;
import java.util.ArrayList;
import java.util.List;
public class Flags {
private final JSONObject flags;
private static final Gson gson = new Gson();
private final JsonObject flags;
public Flags(@Nullable String json) {
JSONObject flags = null;
if (json != null && !json.isEmpty()) {
flags = (JSONObject) JSONValue.parse(json);
flags = gson.fromJson(json, JsonObject.class);
} else {
flags = new JsonObject();
}
if (flags == null) {
flags = new JSONObject();
}
this.flags = flags;
}
@NotNull
public List<String> getStringList(@NotNull String key) {
Object object = flags.get(key);
JsonElement object = flags.get(key);
ArrayList<String> list = new ArrayList<>();
if (object instanceof JSONArray) {
for (Object o : ((JSONArray) object)) {
list.add(String.valueOf(o));
if (object != null && object.isJsonArray()) {
for (JsonElement element : object.getAsJsonArray()) {
list.add(element.getAsString());
}
}
return list;
@@ -38,11 +36,11 @@ public class Flags {
@Nullable
public String getString(@NotNull String key) {
Object object = flags.get(key);
if (object == null) {
JsonElement element = flags.get(key);
if (element == null || element.isJsonNull()) {
return null;
}
return String.valueOf(object);
return element.getAsString();
}
@NotNull
@@ -56,11 +54,11 @@ public class Flags {
@NotNull
public Number getNumber(@NotNull String key) {
Object object = flags.get(key);
if (object instanceof Number) {
return (Number) object;
JsonElement element = flags.get(key);
if (element == null || element.isJsonNull()) {
return 0;
}
return 0;
return element.getAsNumber();
}
public boolean getBoolean(@NotNull String key) {
@@ -68,26 +66,22 @@ public class Flags {
}
public boolean getBoolean(@NotNull String key, boolean def) {
Object object = flags.get(key);
if (object instanceof Boolean) {
return (Boolean) object;
JsonElement element = flags.get(key);
if (element == null || element.isJsonNull()) {
return def;
}
return def;
return element.getAsBoolean();
}
@SuppressWarnings("unchecked")
public void put(@NotNull String key, @NotNull List<?> value) {
JSONArray array = new JSONArray();
array.addAll(value);
flags.put(key, array);
flags.add(key, gson.toJsonTree(value));
}
@SuppressWarnings("unchecked")
public void put(@NotNull String key, @NotNull Object object) {
flags.put(key, object);
flags.add(key, gson.toJsonTree(object));
}
public String toJSONString() {
return flags.toJSONString();
return flags.toString();
}
}
@@ -1,18 +1,19 @@
package net.sacredlabyrinth.phaed.simpleclans;
import com.google.gson.Gson;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.reflect.TypeToken;
import net.sacredlabyrinth.phaed.simpleclans.managers.PermissionsManager;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.Contract;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import org.json.simple.parser.JSONParser;
import org.json.simple.parser.ParseException;
import java.io.IOException;
import java.lang.reflect.Type;
import java.net.URI;
import java.net.URISyntaxException;
import java.nio.file.FileSystem;
@@ -35,8 +36,11 @@ import static net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils.stripColors;
* @author phaed
*/
public class Helper {
public final class Helper {
private static final Gson GSON = new Gson();
private static final Type RANKS_TYPE = TypeToken.getParameterized(List.class, Rank.class).getType();
private static final Type RESIGN_TYPE = TypeToken.getParameterized(Map.class, String.class, Long.class).getType();
private Helper() {
}
@@ -49,15 +53,10 @@ public class Helper {
return Locale.forLanguageTag(languageTag);
}
public static @Nullable JSONObject parseJson(String json) {
if (json != null && !json.isEmpty()) {
try {
return (JSONObject) new JSONParser().parse(json);
} catch (ParseException e) {
e.printStackTrace();
}
}
return null;
@Contract("null -> null")
@Nullable
public static String toLanguageTag(@Nullable Locale locale) {
return locale != null ? locale.toLanguageTag() : null;
}
public static Set<Path> getPathsIn(String path, Predicate<? super Path> filter) {
@@ -117,47 +116,32 @@ public class Helper {
}
/**
* Parses a list of ranks from the specified JSONObject
* Parses a list of ranks from the specified Json String
*
* @param jo the JSON Object
* @param json the Json String
* @return a list of ranks or null if the JSON String is null/empty
*/
public static @Nullable List<Rank> ranksFromJson(@Nullable JSONObject jo) {
if (jo != null && !jo.isEmpty()) {
Object ranks = jo.get("ranks");
if (ranks != null) {
JSONArray array = (JSONArray) ranks;
List<Rank> rankList = new ArrayList<>();
for (Object o : array) {
JSONObject r = (JSONObject) o;
String name = (String) r.get("name");
String displayName = (String) r.get("displayName");
Set<String> permissions = new HashSet<>();
for (Object p : (JSONArray) r.get("permissions")) {
permissions.add((String) p);
}
Rank rank = new Rank(name, displayName, permissions);
rankList.add(rank);
}
return rankList;
}
public static @Nullable List<Rank> ranksFromJson(@Nullable String json) {
if (json != null && !json.isEmpty()) {
JsonObject object = GSON.fromJson(json, JsonObject.class);
JsonElement ranks = object.get("ranks");
return GSON.fromJson(ranks, RANKS_TYPE);
}
return null;
}
/**
* Parses the default rank from the specified JSONObject
* Parses the default rank from the specified Json String
*
* @param jo the JSON object
* @param json the Json String
* @return the default rank or null if not found and/or it does not exist
*/
public static @Nullable String defaultRankFromJson(@Nullable JSONObject jo) {
if (jo != null && !jo.isEmpty()) {
if (!jo.containsKey("defaultRank")) {
return null;
} else {
return (String) jo.get("defaultRank");
public static @Nullable String defaultRankFromJson(@Nullable String json) {
if (json != null && !json.isEmpty()) {
JsonObject object = GSON.fromJson(json, JsonObject.class);
JsonElement defaultRank = object.get("defaultRank");
if (defaultRank != null && !defaultRank.isJsonNull()) {
return defaultRank.getAsString();
}
}
return null;
@@ -170,36 +154,24 @@ public class Helper {
* @param defaultRank the default rank
* @return a JSON String
*/
@SuppressWarnings("unchecked")
public static String ranksToJson(List<Rank> ranks, @Nullable String defaultRank) {
if (ranks == null)
ranks = new ArrayList<>();
JSONArray array = new JSONArray();
for (Rank rank : ranks) {
JSONObject o = new JSONObject();
o.put("name", rank.getName());
o.put("displayName", rank.getDisplayName());
JSONArray permArray = new JSONArray();
permArray.addAll(rank.getPermissions());
o.put("permissions", permArray);
array.add(o);
}
JSONObject object = new JSONObject();
object.put("ranks", array);
object.put("defaultRank", defaultRank);
return object.toJSONString();
JsonObject object = new JsonObject();
object.add("ranks", GSON.toJsonTree(ranks));
object.addProperty("defaultRank", defaultRank);
return object.toString();
}
/**
* Converts a resign times map to a JSON String
*
* @param resignTimes
* @param resignTimes the resign times
* @return a JSON String
*/
public static String resignTimesToJson(Map<String, Long> resignTimes) {
return JSONObject.toJSONString(resignTimes);
return GSON.toJson(resignTimes);
}
/**
@@ -208,14 +180,9 @@ public class Helper {
* @param json JSON String
* @return a map
*/
@SuppressWarnings("unchecked")
public static Map<String, Long> resignTimesFromJson(String json) {
if (json != null) {
try {
return (Map<String, Long>) new JSONParser().parse(json);
} catch (ParseException e) {
e.printStackTrace();
}
public static @Nullable Map<String, Long> resignTimesFromJson(String json) {
if (json != null && !json.isEmpty()) {
return GSON.fromJson(json, RESIGN_TYPE);
}
return null;
}
@@ -277,6 +244,7 @@ public class Helper {
* @param values
* @return
*/
@Deprecated
public static Set<String> fromArrayToSet(String... values) {
HashSet<String> results = new HashSet<>();
Collections.addAll(results, values);
@@ -418,19 +386,4 @@ public class Helper {
}
return String.join(", ", statuses);
}
/**
* Checks if all passed materials are some kind of AIR
*
* @param materials materials to test
* @return true if all materials are AIR
*/
public static boolean isAir(@NotNull Material... materials) {
for (Material m : materials) {
if (!m.name().contains("AIR")) {
return false;
}
}
return true;
}
}
@@ -1,5 +1,7 @@
package net.sacredlabyrinth.phaed.simpleclans;
import org.jetbrains.annotations.Nullable;
import java.util.HashSet;
import java.util.Set;
@@ -15,11 +17,11 @@ public class Rank implements Comparable<Rank> {
public Rank(String name) {
setName(name);
permissions = new HashSet<String>();
permissions = new HashSet<>();
setDisplayName(displayName);
}
public Rank(String name, String displayName, Set<String> permissions) {
public Rank(String name, @Nullable String displayName, Set<String> permissions) {
setName(name);
setDisplayName(displayName);
setPermissions(permissions);
@@ -32,7 +34,7 @@ public class Rank implements Comparable<Rank> {
this.name = name;
}
public void setDisplayName(String displayName) {
public void setDisplayName(@Nullable String displayName) {
if (displayName == null || displayName.isEmpty()) {
displayName = name;
}
@@ -41,7 +43,7 @@ public class Rank implements Comparable<Rank> {
public void setPermissions(Set<String> permissions) {
if (permissions == null) {
permissions = new HashSet<String>();
permissions = new HashSet<>();
}
this.permissions = permissions;
}
@@ -21,6 +21,7 @@ public enum RankPermission {
COORDS("simpleclans.member.coords", PermissionLevel.TRUSTED),
FEE_ENABLE("simpleclans.leader.fee", PermissionLevel.LEADER),
FEE_SET("simpleclans.leader.fee", PermissionLevel.LEADER),
FEE_BYPASS("", PermissionLevel.LEADER),
REGROUP_HOME("simpleclans.leader.regroup.home", PermissionLevel.LEADER),
REGROUP_ME("simpleclans.leader.regroup.me", PermissionLevel.LEADER),
HOME_SET("simpleclans.leader.home-set", PermissionLevel.LEADER),
@@ -9,6 +9,8 @@ import net.sacredlabyrinth.phaed.simpleclans.listeners.*;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankLogger;
import net.sacredlabyrinth.phaed.simpleclans.loggers.CSVBankLogger;
import net.sacredlabyrinth.phaed.simpleclans.managers.*;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
import net.sacredlabyrinth.phaed.simpleclans.proxy.ProxyManager;
import net.sacredlabyrinth.phaed.simpleclans.tasks.*;
import net.sacredlabyrinth.phaed.simpleclans.ui.InventoryController;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatFormatMigration;
@@ -55,6 +57,7 @@ public class SimpleClans extends JavaPlugin {
private TeleportManager teleportManager;
private ProtectionManager protectionManager;
private ChatManager chatManager;
private ProxyManager proxyManager;
private boolean hasUUID;
private static final Pattern ACF_PLACEHOLDER_PATTERN = Pattern.compile("\\{(?<key>[a-zA-Z]+?)}");
@@ -101,6 +104,7 @@ public class SimpleClans extends JavaPlugin {
permissionsManager = new PermissionsManager();
requestManager = new RequestManager();
clanManager = new ClanManager();
proxyManager = new BungeeManager(this);
storageManager = new StorageManager();
teleportManager = new TeleportManager();
protectionManager = new ProtectionManager();
@@ -248,6 +252,10 @@ public class SimpleClans extends JavaPlugin {
return chatManager;
}
public ProxyManager getProxyManager() {
return proxyManager;
}
public BankLogger getBankLogger() {
return bankLogger;
}
@@ -269,7 +277,7 @@ public class SimpleClans extends JavaPlugin {
@Nullable
public static String optionalLang(@NotNull String key, @Nullable ClanPlayer clanPlayer, Object... arguments) {
Locale locale = instance.getSettingsManager().getLanguage();
if (clanPlayer != null && instance.getSettingsManager().is(LANGUAGE_SELECTOR)) {
if (clanPlayer != null && clanPlayer.getLocale() != null && instance.getSettingsManager().is(LANGUAGE_SELECTOR)) {
locale = clanPlayer.getLocale();
}
@@ -5,8 +5,11 @@ import net.sacredlabyrinth.phaed.simpleclans.managers.ChatManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
public interface ChatHandler {
SimpleClans plugin = SimpleClans.getInstance();
SettingsManager settingsManager = plugin.getSettingsManager();
ChatManager chatManager = plugin.getChatManager();
void sendMessage(SCMessage message);
@@ -6,7 +6,7 @@ import org.jetbrains.annotations.NotNull;
import java.util.ArrayList;
import java.util.List;
public class SCMessage {
public class SCMessage implements Cloneable {
private final Source source;
private final ClanPlayer.Channel channel;
@@ -23,7 +23,8 @@ public class SCMessage {
* @param content The content of message
* @param receivers The clan players, who will receive the content
*/
public SCMessage(@NotNull Source source, @NotNull ClanPlayer.Channel channel, @NotNull ClanPlayer sender, String content, @NotNull List<ClanPlayer> receivers) {
public SCMessage(@NotNull Source source, @NotNull ClanPlayer.Channel channel,
@NotNull ClanPlayer sender, String content, @NotNull List<ClanPlayer> receivers) {
this.source = source;
this.channel = channel;
this.sender = sender;
@@ -68,6 +69,15 @@ public class SCMessage {
this.receivers = receivers;
}
@Override
public SCMessage clone() {
try {
return (SCMessage) super.clone();
} catch (CloneNotSupportedException e) {
throw new Error(); //never thrown
}
}
/**
* The place where the message came from.
* Used by ChatHandlers to know which SCMessages they can handle.
@@ -75,6 +85,6 @@ public class SCMessage {
* @see ChatHandler initiate the handler
*/
public enum Source {
SPIGOT, DISCORD, BUNGEE
SPIGOT, DISCORD, PROXY
}
}
@@ -6,17 +6,16 @@ import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.chat.ChatHandler;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.hooks.discord.DiscordHook;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import org.jetbrains.annotations.NotNull;
import java.util.Objects;
import java.util.Optional;
import static net.sacredlabyrinth.phaed.simpleclans.ClanPlayer.Channel.CLAN;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.SPIGOT;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.DISCORDCHAT_ENABLE;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.SPIGOT;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.DISCORDCHAT_FORMAT_TO;
import static org.bukkit.Bukkit.getPluginManager;
/**
* Handles delivering messages from {@link Source#SPIGOT} to {@link Source#DISCORD}.
@@ -30,13 +29,13 @@ public class DiscordChatHandler implements ChatHandler {
}
String format = settingsManager.getString(DISCORDCHAT_FORMAT_TO);
String formattedMessage = chatManager.parseChatFormat(format, message);
String formattedMessage = ChatUtils.stripColors(chatManager.parseChatFormat(format, message));
Clan clan = message.getSender().getClan();
if (clan == null) {
return;
}
DiscordHook discordHook = Objects.requireNonNull(chatManager.getDiscordHook(), "DiscordHook cannot be null");
Optional<TextChannel> channel = discordHook.getCachedChannel(clan.getTag());
channel.ifPresent(textChannel -> DiscordUtil.sendMessage(textChannel, formattedMessage));
@@ -44,7 +43,6 @@ public class DiscordChatHandler implements ChatHandler {
@Override
public boolean canHandle(SCMessage.Source source) {
return source == SPIGOT && settingsManager.is(DISCORDCHAT_ENABLE) &&
getPluginManager().getPlugin("DiscordSRV") != null;
return source == SPIGOT && chatManager.isDiscordHookEnabled();
}
}
@@ -0,0 +1,20 @@
package net.sacredlabyrinth.phaed.simpleclans.chat.handlers;
import net.sacredlabyrinth.phaed.simpleclans.chat.ChatHandler;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.PERFORMANCE_USE_BUNGEECORD;
public class ProxyChatHandler implements ChatHandler {
@Override
public void sendMessage(SCMessage message) {
plugin.getProxyManager().sendMessage(message);
}
@Override
public boolean canHandle(Source source) {
return source == Source.SPIGOT && settingsManager.is(PERFORMANCE_USE_BUNGEECORD);
}
}
@@ -5,12 +5,12 @@ import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.chat.ChatHandler;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.events.ChatEvent;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import org.bukkit.scheduler.BukkitRunnable;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.DISCORD;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.SPIGOT;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.*;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.DISCORDCHAT_ENABLE;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.PERFORMANCE_USE_BUNGEECORD;
import static org.bukkit.Bukkit.getPluginManager;
public class SpigotChatHandler implements ChatHandler {
@@ -30,14 +30,15 @@ public class SpigotChatHandler implements ChatHandler {
if (event.isCancelled()) {
return;
}
message.setContent(event.getMessage());
ConfigField configField = ConfigField.valueOf(String.format("%sCHAT_FORMAT",
message.getSource() == SPIGOT ? message.getChannel() : message.getSource()));
message.getSource() == DISCORD ? "DISCORD" : message.getChannel()));
String format = settingsManager.getString(configField);
String formattedMessage = chatManager.parseChatFormat(format, message, event.getPlaceholders());
plugin.getLogger().info(formattedMessage);
plugin.getLogger().info(ChatUtils.stripColors(formattedMessage));
for (ClanPlayer cp : message.getReceivers()) {
ChatBlock.sendMessage(cp, formattedMessage);
@@ -48,7 +49,7 @@ public class SpigotChatHandler implements ChatHandler {
@Override
public boolean canHandle(SCMessage.Source source) {
return source == SPIGOT || (source == DISCORD && settingsManager.is(DISCORDCHAT_ENABLE) &&
getPluginManager().getPlugin("DiscordSRV") != null);
return source == SPIGOT || (source == PROXY && settingsManager.is(PERFORMANCE_USE_BUNGEECORD))
|| (source == DISCORD && chatManager.isDiscordHookEnabled());
}
}
@@ -4,48 +4,51 @@ import net.sacredlabyrinth.phaed.simpleclans.ChatBlock;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.chat.ChatHandler;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import org.bukkit.Bukkit;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.DISCORD;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.SPIGOT;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.*;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.DISCORDCHAT_ENABLE;
import static org.bukkit.Bukkit.getPluginManager;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.PERFORMANCE_USE_BUNGEECORD;
/**
* Handles delivering messages from {@link Source#SPIGOT} and {@link Source#DISCORD} to internal spy chat.
* Handles delivering messages from {@link Source#SPIGOT} or {@link Source#DISCORD} to internal spy chat.
*/
public class SpyChatHandler implements ChatHandler {
@Override
public void sendMessage(SCMessage message) {
ConfigField configField = ConfigField.valueOf(String.format("%sCHAT_SPYFORMAT",
message.getSource() == SPIGOT ? message.getChannel() : message.getSource()));
String format = settingsManager.getString(configField);
ConfigField formatField = ConfigField.valueOf(String.format("%sCHAT_SPYFORMAT",
message.getSource() == DISCORD ? "DISCORD" : message.getChannel()));
String format = settingsManager.getString(formatField);
message.setContent(ChatUtils.stripColors(message.getContent()));
String formattedMessage = chatManager.parseChatFormat(format, message);
List<ClanPlayer> onlinePlayers = getOnlineClanPlayers().stream()
.filter(player -> plugin.getPermissionsManager().has(player.toPlayer(), "simpleclans.admin.all-seeing-eye"))
.filter(player -> !player.isMuted())
.collect(Collectors.toList());
List<ClanPlayer> onlineSpies = getOnlineSpies();
onlinePlayers.removeAll(message.getReceivers());
onlinePlayers.forEach(receiver -> ChatBlock.sendMessage(receiver, formattedMessage));
// Don't send a duplicate message if a spy is inside the clan
onlineSpies.removeAll(message.getReceivers());
onlineSpies.forEach(receiver -> ChatBlock.sendMessage(receiver, formattedMessage));
}
@Override
public boolean canHandle(SCMessage.Source source) {
return source == SPIGOT || (source == DISCORD && settingsManager.is(DISCORDCHAT_ENABLE) &&
getPluginManager().getPlugin("DiscordSRV") != null);
return source == SPIGOT || (source == PROXY && settingsManager.is(PERFORMANCE_USE_BUNGEECORD))
|| (source == DISCORD && chatManager.isDiscordHookEnabled());
}
private List<ClanPlayer> getOnlineClanPlayers() {
return plugin.getClanManager().getAllClanPlayers().stream().
filter(cp -> cp.toPlayer() != null).
private List<ClanPlayer> getOnlineSpies() {
return Bukkit.getOnlinePlayers().stream().
filter(Objects::nonNull).
filter(player -> plugin.getPermissionsManager().has(player, "simpleclans.admin.all-seeing-eye")).
map(player -> plugin.getClanManager().getCreateClanPlayer(player.getUniqueId())).
filter(Objects::nonNull).
filter(clanPlayer -> !clanPlayer.isMuted()).
collect(Collectors.toList());
}
}
@@ -53,6 +53,7 @@ public class SCCommandManager extends PaperCommandManager {
registerCommands();
registerConditions();
registerCompletions();
defaultHelpPerPage = plugin.getSettingsManager().getInt(HELP_SIZE);
}
private void registerDependencies() {
@@ -8,6 +8,7 @@ import net.sacredlabyrinth.phaed.simpleclans.EconomyResponse;
import net.sacredlabyrinth.phaed.simpleclans.events.BankDepositEvent;
import net.sacredlabyrinth.phaed.simpleclans.events.BankWithdrawEvent;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankLogger;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import net.sacredlabyrinth.phaed.simpleclans.managers.PermissionsManager;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player;
@@ -68,13 +69,14 @@ public class BankCommand extends BaseCommand {
/*
* ——————————————————————————————————
*/
switch (clan.withdraw(player, COMMAND, amount)) {
BankOperator operator = new BankOperator(player, permissions.playerGetMoney(player));
switch (clan.withdraw(operator, COMMAND, amount)) {
case SUCCESS:
if (permissions.playerGrantMoney(player, amount)) {
player.sendMessage(AQUA + lang("player.clan.withdraw", player, amount));
clan.addBb(player.getName(), AQUA + lang("bb.clan.withdraw", amount, player.getName()));
} else {
clan.setBalance(player, REVERT, BankLogger.Operation.WITHDRAW, clan.getBalance() + amount);
clan.setBalance(operator, REVERT, BankLogger.Operation.WITHDRAW, clan.getBalance() + amount);
}
break;
case NOT_ENOUGH_BALANCE:
@@ -124,14 +126,15 @@ public class BankCommand extends BaseCommand {
player.sendMessage(AQUA + lang("not.sufficient.money", player, amount));
return;
}
EconomyResponse response = clan.deposit(player, COMMAND, amount);
BankOperator operator = new BankOperator(player, permissions.playerGetMoney(player));
EconomyResponse response = clan.deposit(operator, COMMAND, amount);
if (response == EconomyResponse.SUCCESS) {
if (permissions.playerChargeMoney(player, amount)) {
player.sendMessage(AQUA + lang("player.clan.deposit", player, amount));
clan.addBb(player.getName(), AQUA + lang("bb.clan.deposit", amount, player.getName()));
} else {
//Reverts the deposit if something went wrong with Vault
clan.setBalance(player, REVERT, BankLogger.Operation.DEPOSIT, clan.getBalance() - amount);
clan.setBalance(operator, REVERT, BankLogger.Operation.DEPOSIT, clan.getBalance() - amount);
}
}
}
@@ -22,8 +22,6 @@ public class ChatCommand extends BaseCommand {
@Dependency
private ChatManager chatManager;
@Dependency
private SettingsManager settingsManager;
@Dependency
private StorageManager storageManager;
@Default
@@ -6,11 +6,16 @@ import net.sacredlabyrinth.phaed.simpleclans.ChatBlock;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.commands.data.*;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
import net.sacredlabyrinth.phaed.simpleclans.ui.InventoryDrawer;
import net.sacredlabyrinth.phaed.simpleclans.ui.frames.CoordsFrame;
import net.sacredlabyrinth.phaed.simpleclans.ui.frames.RosterFrame;
import net.sacredlabyrinth.phaed.simpleclans.utils.VanishUtils;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.*;
import static org.bukkit.ChatColor.RED;
@CommandAlias("%clan")
@@ -18,6 +23,8 @@ import static org.bukkit.ChatColor.RED;
public class DataCommands extends BaseCommand {
@Dependency
private SimpleClans plugin;
@Dependency
private SettingsManager settings;
@Subcommand("%vitals")
@CommandPermission("simpleclans.member.vitals")
@@ -49,6 +56,10 @@ public class DataCommands extends BaseCommand {
@CommandPermission("simpleclans.member.roster")
@Description("{@@command.description.roster}")
public void roster(Player player, Clan clan) {
if (settings.is(ENABLE_GUI)) {
InventoryDrawer.open(new RosterFrame(player, null, clan));
return;
}
ClanRoster r = new ClanRoster(plugin, player, clan);
r.send();
}
@@ -59,6 +70,10 @@ public class DataCommands extends BaseCommand {
@HelpSearchTags("local location")
@Description("{@@command.description.coords}")
public void coords(Player player, Clan clan) {
if (settings.is(ENABLE_GUI)) {
InventoryDrawer.open(new CoordsFrame(player, null, clan));
return;
}
if (VanishUtils.getNonVanished(player, clan).size() == 1) {
ChatBlock.sendMessage(player, RED + lang("you.are.the.only.member.online", player));
return;
@@ -4,12 +4,14 @@ import co.aikar.commands.BaseCommand;
import co.aikar.commands.annotation.*;
import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.events.HomeRegroupEvent;
import net.sacredlabyrinth.phaed.simpleclans.events.PlayerHomeClearEvent;
import net.sacredlabyrinth.phaed.simpleclans.events.PlayerHomeSetEvent;
import net.sacredlabyrinth.phaed.simpleclans.managers.ClanManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.PermissionsManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.ProtectionManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
import net.sacredlabyrinth.phaed.simpleclans.utils.VanishUtils;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.entity.Player;
@@ -59,17 +61,12 @@ public class HomeCommands extends BaseCommand {
@CommandPermission("simpleclans.leader.regroup.home")
@Conditions("rank:name=REGROUP_HOME")
@Description("{@@command.description.regroup.home}")
public void regroupHome(Player player, ClanPlayer cp, Clan clan) {
public void regroupHome(Player player, ClanPlayer cp, @Conditions("can_teleport") Clan clan) {
if (!settings.is(ALLOW_REGROUP)) {
ChatBlock.sendMessage(player, RED + lang("insufficient.permissions", player));
return;
}
Location location = clan.getHomeLocation();
if (location == null) {
ChatBlock.sendMessage(player, RED + lang("hombase.not.set", player));
return;
}
processRegroup(player, cp, clan, location);
}
@@ -77,14 +74,9 @@ public class HomeCommands extends BaseCommand {
@CommandPermission("simpleclans.member.home")
@Conditions("rank:name=HOME_TP")
@Description("{@@command.description.home.tp}")
public void teleport(Player player, Clan clan, ClanPlayer cp) {
public void teleport(Player player, @Conditions("can_teleport") Clan clan, ClanPlayer cp) {
Location homeLocation = clan.getHomeLocation();
if (homeLocation == null) {
ChatBlock.sendMessage(player, RED + lang("hombase.not.set", player));
return;
}
if (cm.purchaseHomeTeleport(player)) {
plugin.getTeleportManager().addPlayer(player, homeLocation, clan.getName());
}
@@ -94,13 +86,19 @@ public class HomeCommands extends BaseCommand {
@CommandPermission("simpleclans.leader.home-set")
@Conditions("rank:name=HOME_SET")
@Description("{@@command.description.home.clear}")
public void clear(Player player, Clan clan) {
public void clear(Player player, ClanPlayer cp, Clan clan) {
if (settings.is(CLAN_HOMEBASE_CAN_BE_SET_ONLY_ONCE) && clan.getHomeLocation() != null &&
!permissions.has(player, "simpleclans.mod.home")) {
ChatBlock.sendMessage(player, RED + lang("home.base.only.once", player));
return;
}
PlayerHomeClearEvent event = new PlayerHomeClearEvent(clan, cp);
Bukkit.getPluginManager().callEvent(event);
if (event.isCancelled()) {
return;
}
clan.setHomeLocation(null);
ChatBlock.sendMessage(player, AQUA + lang("hombase.cleared", player));
}
@@ -18,7 +18,7 @@ import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.Con
@CommandAlias("%clan")
@Subcommand("%land")
@Conditions("%basic_conditions|land_sharing|own_land")
@Conditions("%basic_conditions|clan_member|land_sharing|own_land")
@CommandPermission("simpleclans.member.land")
public class LandCommand extends BaseCommand {
@@ -5,7 +5,10 @@ import co.aikar.commands.annotation.*;
import net.sacredlabyrinth.phaed.simpleclans.ChatBlock;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.commands.ClanPlayerInput;
import net.sacredlabyrinth.phaed.simpleclans.conversation.DisbandPrompt;
import net.sacredlabyrinth.phaed.simpleclans.conversation.SCConversation;
import net.sacredlabyrinth.phaed.simpleclans.hooks.discord.DiscordHook;
import net.sacredlabyrinth.phaed.simpleclans.hooks.discord.exceptions.DiscordHookException;
import net.sacredlabyrinth.phaed.simpleclans.managers.*;
@@ -22,6 +25,8 @@ import static org.bukkit.ChatColor.*;
@Conditions("%basic_conditions|leader")
public class LeaderCommands extends BaseCommand {
@Dependency
private SimpleClans plugin;
@Dependency
private StorageManager storage;
@Dependency
@@ -106,7 +111,7 @@ public class LeaderCommands extends BaseCommand {
return;
}
clan.disband(player, true, false);
new SCConversation(plugin, player, new DisbandPrompt()).begin();
}
@Subcommand("%verify")
@@ -193,8 +198,8 @@ public class LeaderCommands extends BaseCommand {
return;
}
double amount = settings.getDouble(ECONOMY_DISCORD_CREATION_PRICE);
if (settings.is(ECONOMY_PURCHASE_DISCORD_CREATE)) {
double amount = settings.getDouble(ECONOMY_DISCORD_CREATION_PRICE);
if (!permissions.playerHasMoney(player, amount)) {
player.sendMessage(AQUA + lang("not.sufficient.money", player, amount));
return;
@@ -207,8 +212,12 @@ public class LeaderCommands extends BaseCommand {
try {
discordHook.createChannel(clan.getTag());
ChatBlock.sendMessage(player, AQUA + "discord.created.successfully");
ChatBlock.sendMessageKey(player, "discord.created.successfully");
} catch (DiscordHookException ex) {
// Return player's money if clan creation went wrong
if (settings.is(ECONOMY_PURCHASE_DISCORD_CREATE)) {
permissions.playerGrantMoney(player, amount);
}
String messageKey = ex.getMessageKey();
if (messageKey != null) {
ChatBlock.sendMessage(player, RED + lang(messageKey));
@@ -24,7 +24,7 @@ public class ClansCompletion extends AbstractSyncCompletion {
clans.removeIf(clan -> clan.getHomeLocation() == null);
}
if (c.hasConfig("unverified")) {
clans.removeIf(clan -> clan.isVerified());
clans.removeIf(Clan::isVerified);
}
if (c.hasConfig("hide_own")) {
Clan clan = getClan(c.getIssuer());
@@ -0,0 +1,42 @@
package net.sacredlabyrinth.phaed.simpleclans.commands.conditions;
import co.aikar.commands.*;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.Flags;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
public class TeleportCondition extends AbstractParameterCondition<Clan> {
public TeleportCondition(@NotNull SimpleClans plugin) {
super(plugin);
}
@Override
public Class<Clan> getType() {
return Clan.class;
}
@Override
public void validateCondition(ConditionContext<BukkitCommandIssuer> context,
BukkitCommandExecutionContext execContext,
Clan value) throws InvalidCommandArgument {
Player player = execContext.getPlayer();
if (value.getHomeLocation() == null) {
throw new ConditionFailedException(lang("hombase.not.set", player));
}
Flags flags = new Flags(value.getFlags());
String homeServer = flags.getString("homeServer", "");
if (!homeServer.isEmpty() && !plugin.getProxyManager().getServerName().equals(homeServer)) {
throw new ConditionFailedException(lang("home.set.in.different.server"));
}
}
@Override
public @NotNull String getId() {
return "can_teleport";
}
}
@@ -0,0 +1,31 @@
package net.sacredlabyrinth.phaed.simpleclans.commands.conditions;
import co.aikar.commands.BukkitCommandExecutionContext;
import co.aikar.commands.BukkitCommandIssuer;
import co.aikar.commands.ConditionContext;
import co.aikar.commands.InvalidCommandArgument;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.commands.ClanInput;
import org.jetbrains.annotations.NotNull;
public class TeleportInputCondition extends AbstractParameterCondition<ClanInput> {
public TeleportInputCondition(@NotNull SimpleClans plugin) {
super(plugin);
}
@Override
public Class<ClanInput> getType() {
return ClanInput.class;
}
@Override
public void validateCondition(ConditionContext<BukkitCommandIssuer> context, BukkitCommandExecutionContext execContext, ClanInput value) throws InvalidCommandArgument {
new TeleportCondition(plugin).validateCondition(context, execContext, value.getClan());
}
@Override
public @NotNull String getId() {
return "can_teleport";
}
}
@@ -2,32 +2,43 @@ package net.sacredlabyrinth.phaed.simpleclans.commands.contexts;
import co.aikar.commands.BukkitCommandExecutionContext;
import co.aikar.commands.InvalidCommandArgument;
import co.aikar.commands.MinecraftMessageKeys;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.commands.ClanPlayerInput;
import org.bukkit.Bukkit;
import org.bukkit.OfflinePlayer;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import java.util.regex.Pattern;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.USERNAME_REGEX;
@SuppressWarnings("unused")
public class ClanPlayerInputContextResolver extends AbstractInputOnlyContextResolver<ClanPlayerInput> {
private final Pattern validUsername;
public ClanPlayerInputContextResolver(@NotNull SimpleClans plugin) {
super(plugin);
validUsername = Pattern.compile(plugin.getSettingsManager().getString(USERNAME_REGEX));
}
@Override
public ClanPlayerInput getContext(BukkitCommandExecutionContext context) throws InvalidCommandArgument {
String arg = context.popFirstArg();
if (!validUsername.matcher(arg).matches()) {
throw new InvalidCommandArgument(MinecraftMessageKeys.IS_NOT_A_VALID_NAME, "{name}", arg);
}
ClanPlayer cp = clanManager.getAnyClanPlayer(arg);
if (cp == null) {
@SuppressWarnings("deprecation")
OfflinePlayer offlinePlayer = Bukkit.getOfflinePlayer(arg);
if (!offlinePlayer.hasPlayedBefore()) {
Player player = Bukkit.getPlayer(arg);
if (player == null) {
throw new InvalidCommandArgument(lang("user.hasnt.played.before", context.getSender()));
}
cp = clanManager.getCreateClanPlayer(offlinePlayer.getUniqueId());
cp = clanManager.getCreateClanPlayer(player.getUniqueId());
}
return new ClanPlayerInput(cp);
@@ -37,4 +48,5 @@ public class ClanPlayerInputContextResolver extends AbstractInputOnlyContextReso
public Class<ClanPlayerInput> getType() {
return ClanPlayerInput.class;
}
}
@@ -4,7 +4,6 @@ import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import net.sacredlabyrinth.phaed.simpleclans.utils.VanishUtils;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import java.util.List;
@@ -35,10 +34,8 @@ public class ClanRoster extends Sendable {
List<ClanPlayer> members = clan.getNonLeaders();
plugin.getClanManager().sortClanPlayersByLastSeen(members);
for (ClanPlayer cp : members) {
Player p = cp.toPlayer();
String name = (cp.isTrusted() ? sm.getColored(PAGE_TRUSTED_COLOR) : sm.getColored(PAGE_UNTRUSTED_COLOR)) + cp.getName();
String lastSeen = p != null && p.isOnline() && !VanishUtils.isVanished(sender, p) ? GREEN + lang("online", sender) : WHITE + cp.getLastSeenDaysString(sender);
String lastSeen = VanishUtils.isVanished(sender, cp) ? WHITE + cp.getLastSeenDaysString(sender) : GREEN + lang("online", sender);
chatBlock.addRow(" " + name, YELLOW + ChatUtils.parseColors(cp.getRankDisplayName()) + RESET, lastSeen);
}
@@ -48,11 +45,9 @@ public class ClanRoster extends Sendable {
List<ClanPlayer> leaders = clan.getLeaders();
plugin.getClanManager().sortClanPlayersByLastSeen(leaders);
for (ClanPlayer cp : leaders) {
Player p = cp.toPlayer();
String name = sm.getColored(PAGE_LEADER_COLOR) + cp.getName();
String lastSeen = p != null && p.isOnline() && !VanishUtils.isVanished(sender, p) ? GREEN + lang("online", sender)
: WHITE + cp.getLastSeenDaysString(sender);
String lastSeen = VanishUtils.isVanished(sender, cp) ? WHITE + cp.getLastSeenDaysString(sender) :
GREEN + lang("online", sender);
chatBlock.addRow(" " + name, YELLOW + ChatUtils.parseColors(cp.getRankDisplayName()) + RESET, lastSeen);
}
@@ -6,6 +6,7 @@ import net.sacredlabyrinth.phaed.simpleclans.Helper;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.utils.KDRFormat;
import net.sacredlabyrinth.phaed.simpleclans.utils.RankingNumberResolver;
import net.sacredlabyrinth.phaed.simpleclans.utils.VanishUtils;
import org.bukkit.command.CommandSender;
import org.jetbrains.annotations.NotNull;
@@ -37,7 +38,7 @@ public class Leaderboard extends Sendable {
private void addLines() {
for (ClanPlayer cp : clanPlayers) {
boolean online = cp.toPlayer() != null;
boolean online = !VanishUtils.isVanished(cp);
String name = (cp.isLeader() ? sm.getColored(PAGE_LEADER_COLOR) : (cp.isTrusted() ? sm.getColored(PAGE_TRUSTED_COLOR) :
sm.getColored(PAGE_UNTRUSTED_COLOR))) + cp.getName();
@@ -20,7 +20,8 @@ import net.sacredlabyrinth.phaed.simpleclans.managers.RequestManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.StorageManager;
import net.sacredlabyrinth.phaed.simpleclans.ui.InventoryDrawer;
import net.sacredlabyrinth.phaed.simpleclans.ui.frames.MainFrame;
import net.sacredlabyrinth.phaed.simpleclans.ui.frames.*;
import org.bukkit.Bukkit;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
@@ -28,6 +29,7 @@ import java.text.MessageFormat;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;
import java.util.UUID;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static net.sacredlabyrinth.phaed.simpleclans.conversation.CreateClanNamePrompt.NAME_KEY;
@@ -52,7 +54,6 @@ public class GeneralCommands extends BaseCommand {
@Default
@Description("{@@command.description.clan}")
@CommandAlias("%clan")
@HelpSearchTags("menu gui interface ui")
public void main(CommandSender sender) {
if (sender instanceof Player && settings.is(ENABLE_GUI)) {
@@ -86,6 +87,10 @@ public class GeneralCommands extends BaseCommand {
@CommandPermission("simpleclans.anyone.leaderboard")
@Description("{@@command.description.leaderboard}")
public void leaderboard(CommandSender sender) {
if (settings.is(ENABLE_GUI) && sender instanceof Player) {
InventoryDrawer.open(new LeaderboardFrame((Player) sender, null));
return;
}
Leaderboard l = new Leaderboard(plugin, sender);
l.send();
}
@@ -95,7 +100,12 @@ public class GeneralCommands extends BaseCommand {
@CommandPermission("simpleclans.anyone.lookup")
@Description("{@@command.description.lookup.other}")
public void lookup(CommandSender sender, @Name("player") ClanPlayerInput player) {
Lookup l = new Lookup(plugin, sender, player.getClanPlayer().getUniqueId());
UUID uuid = player.getClanPlayer().getUniqueId();
if (settings.is(ENABLE_GUI) && sender instanceof Player) {
InventoryDrawer.open(new PlayerDetailsFrame((Player) sender, null, Bukkit.getOfflinePlayer(uuid)));
return;
}
Lookup l = new Lookup(plugin, sender, uuid);
l.send();
}
@@ -103,6 +113,10 @@ public class GeneralCommands extends BaseCommand {
@CommandPermission("simpleclans.member.lookup")
@Description("{@@command.description.lookup}")
public void lookup(Player sender) {
if (settings.is(ENABLE_GUI)) {
InventoryDrawer.open(new PlayerDetailsFrame(sender, null, sender));
return;
}
Lookup l = new Lookup(plugin, sender, sender.getUniqueId());
l.send();
}
@@ -135,6 +149,10 @@ public class GeneralCommands extends BaseCommand {
@CommandPermission("simpleclans.anyone.roster")
@Description("{@@command.description.roster.other}")
public void roster(CommandSender sender, @Conditions("verified") @Name("clan") ClanInput clan) {
if (settings.is(ENABLE_GUI) && sender instanceof Player) {
InventoryDrawer.open(new RosterFrame(((Player) sender), null, clan.getClan()));
return;
}
ClanRoster r = new ClanRoster(plugin, sender, clan.getClan());
r.send();
}
@@ -268,6 +286,10 @@ public class GeneralCommands extends BaseCommand {
@CommandCompletion("@clan_list_type @order")
public void list(CommandSender sender, @Optional @Values("@clan_list_type") String type,
@Optional @Single @Values("@order") String order) {
if (settings.is(ENABLE_GUI) && sender instanceof Player) {
InventoryDrawer.open(new ClanListFrame(null, (Player) sender));
return;
}
ClanList list = new ClanList(plugin, sender, type, order);
list.send();
}
@@ -8,7 +8,10 @@ import net.sacredlabyrinth.phaed.simpleclans.EconomyResponse;
import net.sacredlabyrinth.phaed.simpleclans.commands.ClanInput;
import net.sacredlabyrinth.phaed.simpleclans.events.ClanBalanceUpdateEvent;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankLogger;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import net.sacredlabyrinth.phaed.simpleclans.managers.PermissionsManager;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import static net.md_5.bungee.api.ChatColor.RED;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
@@ -19,6 +22,9 @@ import static org.bukkit.ChatColor.AQUA;
@Subcommand("%admin %bank")
public class BankCommand extends BaseCommand {
@Dependency
private PermissionsManager permissions;
@Subcommand("%status")
@CommandPermission("simpleclans.admin.bank.status")
@CommandCompletion("@clans")
@@ -35,8 +41,9 @@ public class BankCommand extends BaseCommand {
public void take(CommandSender sender, @Name("clan") ClanInput clanInput, @Name("amount") double amount) {
Clan clan = clanInput.getClan();
amount = Math.abs(amount);
BankOperator operator = new BankOperator(sender, sender instanceof Player ? permissions.playerGetMoney((Player) sender) : 0);
EconomyResponse economyResponse = clan.withdraw(sender, ClanBalanceUpdateEvent.Cause.COMMAND, amount);
EconomyResponse economyResponse = clan.withdraw(operator, ClanBalanceUpdateEvent.Cause.COMMAND, amount);
switch (economyResponse) {
case SUCCESS:
ChatBlock.sendMessage(sender, AQUA + lang("clan.admin.take", sender, amount, clan.getName()));
@@ -55,8 +62,9 @@ public class BankCommand extends BaseCommand {
public void give(CommandSender sender, @Name("clan") ClanInput clanInput, @Name("amount") double amount) {
Clan clan = clanInput.getClan();
amount = Math.abs(amount);
BankOperator operator = new BankOperator(sender, sender instanceof Player ? permissions.playerGetMoney((Player) sender) : 0);
EconomyResponse economyResponse = clan.deposit(sender, ClanBalanceUpdateEvent.Cause.COMMAND, amount);
EconomyResponse economyResponse = clan.deposit(operator, ClanBalanceUpdateEvent.Cause.COMMAND, amount);
if (economyResponse == EconomyResponse.SUCCESS) {
ChatBlock.sendMessage(sender, AQUA + lang("clan.admin.give", sender, amount, clan.getName()));
clan.addBb(sender.getName(), AQUA + lang("bb.clan.give", sender, amount, sender.getName()));
@@ -70,8 +78,9 @@ public class BankCommand extends BaseCommand {
public void set(CommandSender sender, @Name("clan") ClanInput clanInput, @Name("amount") double amount) {
Clan clan = clanInput.getClan();
amount = Math.abs(amount);
BankOperator operator = new BankOperator(sender, sender instanceof Player ? permissions.playerGetMoney((Player) sender) : 0);
EconomyResponse response = clan.setBalance(sender, ClanBalanceUpdateEvent.Cause.COMMAND, BankLogger.Operation.SET, amount);
EconomyResponse response = clan.setBalance(operator, ClanBalanceUpdateEvent.Cause.COMMAND, BankLogger.Operation.SET, amount);
if (response == EconomyResponse.SUCCESS) {
ChatBlock.sendMessage(sender, AQUA + lang("clan.admin.set", sender, clan.getName(), amount));
clan.addBb(sender.getName(), AQUA + lang("bb.clan.set", sender, amount, sender.getName()));
@@ -5,6 +5,7 @@ import co.aikar.commands.annotation.*;
import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.commands.ClanInput;
import net.sacredlabyrinth.phaed.simpleclans.commands.ClanPlayerInput;
import net.sacredlabyrinth.phaed.simpleclans.events.PlayerHomeSetEvent;
import net.sacredlabyrinth.phaed.simpleclans.events.TagChangeEvent;
import net.sacredlabyrinth.phaed.simpleclans.language.LanguageResource;
import net.sacredlabyrinth.phaed.simpleclans.managers.ClanManager;
@@ -17,7 +18,6 @@ import net.sacredlabyrinth.phaed.simpleclans.utils.TagValidator;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.Location;
import org.bukkit.OfflinePlayer;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
@@ -49,8 +49,8 @@ public class StaffCommands extends BaseCommand {
@CommandCompletion("@players @clans")
@HelpSearchTags("move put")
@Description("{@@command.description.place}")
public void place(CommandSender sender, @Name("player") OfflinePlayer offlinePlayer, @Name("clan") ClanInput clanInput) {
UUID uuid = offlinePlayer.getUniqueId();
public void place(CommandSender sender, @Name("player") ClanPlayerInput cpInput, @Name("clan") ClanInput clanInput) {
UUID uuid = cpInput.getClanPlayer().getUniqueId();
ClanPlayer oldCp = cm.getClanPlayer(uuid);
Clan newClan = clanInput.getClan();
@@ -128,11 +128,18 @@ public class StaffCommands extends BaseCommand {
@CommandPermission("simpleclans.mod.home")
@CommandCompletion("@clans")
@Description("{@@command.description.mod.home.set}")
public void homeSet(Player player, @Name("clan") ClanInput clan) {
public void homeSet(Player player, ClanPlayer cp, @Name("clan") ClanInput clanInput) {
Location loc = player.getLocation();
Clan clan = clanInput.getClan();
clan.getClan().setHomeLocation(loc);
ChatBlock.sendMessage(player, AQUA + lang("hombase.mod.set", player, clan.getClan().getName()) + " " +
PlayerHomeSetEvent event = new PlayerHomeSetEvent(clan, cp, loc);
Bukkit.getPluginManager().callEvent(event);
if (event.isCancelled()) {
return;
}
clan.setHomeLocation(loc);
ChatBlock.sendMessage(player, AQUA + lang("hombase.mod.set", player, clan.getName()) + " " +
ChatColor.YELLOW + Helper.toLocationString(loc));
}
@@ -140,14 +147,7 @@ public class StaffCommands extends BaseCommand {
@CommandCompletion("@clans:has_home")
@CommandPermission("simpleclans.mod.hometp")
@Description("{@@command.description.mod.home.tp}")
public void homeTp(Player player, @Name("clan") ClanInput clan) {
Location loc = clan.getClan().getHomeLocation();
if (loc == null) {
ChatBlock.sendMessage(player, ChatColor.RED + lang("hombase.not.set", player));
return;
}
public void homeTp(Player player, @Name("clan") @Conditions("can_teleport") ClanInput clan) {
plugin.getTeleportManager().teleportToHome(player, clan.getClan());
}
@@ -155,8 +155,8 @@ public class StaffCommands extends BaseCommand {
@CommandPermission("simpleclans.mod.ban")
@CommandCompletion("@players")
@Description("{@@command.description.ban}")
public void ban(CommandSender sender, @Name("player") OfflinePlayer player) {
UUID uuid = player.getUniqueId();
public void ban(CommandSender sender, @Name("player") ClanPlayerInput player) {
UUID uuid = player.getClanPlayer().getUniqueId();
if (settings.isBanned(uuid)) {
ChatBlock.sendMessage(sender, RED + lang("this.player.is.already.banned", sender));
return;
@@ -175,8 +175,8 @@ public class StaffCommands extends BaseCommand {
@CommandPermission("simpleclans.mod.ban")
@CommandCompletion("@players")
@Description("{@@command.description.unban}")
public void unban(CommandSender sender, @Name("player") OfflinePlayer player) {
UUID uuid = player.getUniqueId();
public void unban(CommandSender sender, @Name("player") ClanPlayerInput player) {
UUID uuid = player.getClanPlayer().getUniqueId();
if (!settings.isBanned(uuid)) {
ChatBlock.sendMessage(sender, RED + lang("this.player.is.not.banned", sender));
return;
@@ -0,0 +1,57 @@
package net.sacredlabyrinth.phaed.simpleclans.conversation;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.managers.ClanManager;
import org.bukkit.conversations.ConversationContext;
import org.bukkit.conversations.Prompt;
import org.bukkit.conversations.StringPrompt;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Arrays;
import java.util.List;
import java.util.Objects;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static org.bukkit.ChatColor.RED;
abstract public class ConfirmationPrompt extends StringPrompt {
protected abstract Prompt confirm(ClanPlayer sender, Clan clan);
protected Prompt decline(ClanPlayer sender) {
return new MessagePromptImpl(RED + lang(getDeclineTextKey(), sender));
}
protected abstract String getPromptTextKey();
protected abstract String getDeclineTextKey();
@NotNull
@Override
public String getPromptText(@NotNull ConversationContext context) {
Player player = (Player) context.getForWhom();
List<String> options = Arrays.asList(lang("yes", player), lang("cancel", player));
return RED + lang(getPromptTextKey(), player, options);
}
@Override
public Prompt acceptInput(@NotNull ConversationContext cc, @Nullable String input) {
final SimpleClans plugin = (SimpleClans) cc.getPlugin();
Player player = (Player) cc.getForWhom();
String yes = lang("yes", player);
ClanManager cm = Objects.requireNonNull(plugin).getClanManager();
ClanPlayer cp = cm.getCreateClanPlayer(player.getUniqueId());
Clan clan = cp.getClan();
if (clan == null) {
return END_OF_CONVERSATION;
}
return yes.equalsIgnoreCase(input) ? confirm(cp, clan) : decline(cp);
}
}
@@ -0,0 +1,28 @@
package net.sacredlabyrinth.phaed.simpleclans.conversation;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import org.bukkit.conversations.Prompt;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static org.bukkit.ChatColor.RED;
public class DisbandPrompt extends ConfirmationPrompt {
@Override
protected Prompt confirm(ClanPlayer sender, Clan clan) {
clan.disband(sender.toPlayer(), true, false);
return new MessagePromptImpl(RED + lang("clan.has.been.disbanded", sender, clan.getName()));
}
@Override
protected String getPromptTextKey() {
return "disband.confirmation";
}
@Override
protected String getDeclineTextKey() {
return "disband.request.cancelled";
}
}
@@ -1,13 +1,14 @@
package net.sacredlabyrinth.phaed.simpleclans.conversation;
import org.bukkit.conversations.ConversationContext;
import org.bukkit.conversations.MessagePrompt;
import org.bukkit.conversations.Prompt;
import org.jetbrains.annotations.NotNull;
/**
* @author roinujnosde
*/
public class MessagePromptImpl extends org.bukkit.conversations.MessagePrompt {
public class MessagePromptImpl extends MessagePrompt {
private final String message;
private Prompt nextPrompt;
public MessagePromptImpl(String message) {
@@ -2,17 +2,7 @@ package net.sacredlabyrinth.phaed.simpleclans.conversation;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.managers.ClanManager;
import org.bukkit.conversations.ConversationContext;
import org.bukkit.conversations.Prompt;
import org.bukkit.conversations.StringPrompt;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import java.text.MessageFormat;
import java.util.Arrays;
import java.util.Objects;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static org.bukkit.ChatColor.AQUA;
@@ -21,45 +11,31 @@ import static org.bukkit.ChatColor.RED;
/**
* @author roinujnosde
*/
public class ResignPrompt extends StringPrompt {
public class ResignPrompt extends ConfirmationPrompt {
@Override
public Prompt acceptInput(ConversationContext cc, String input) {
final SimpleClans plugin = (SimpleClans) cc.getPlugin();
protected Prompt confirm(ClanPlayer sender, Clan clan) {
if (clan.isPermanent() || !sender.isLeader() || clan.getLeaders().size() > 1) {
clan.addBb(sender.getName(), AQUA + lang("0.has.resigned", sender.getName()));
sender.addResignTime(clan.getTag());
clan.removePlayerFromClan(sender.getUniqueId());
Player player = (Player) cc.getForWhom();
String yes = lang("yes", player);
ClanManager cm = Objects.requireNonNull(plugin).getClanManager();
ClanPlayer cp = cm.getCreateClanPlayer(player.getUniqueId());
Clan clan = cp.getClan();
if (clan == null) {
return END_OF_CONVERSATION;
}
if (yes.equalsIgnoreCase(input)) {
if (clan.isPermanent() || !clan.isLeader(player) || clan.getLeaders().size() > 1) {
clan.addBb(player.getName(), AQUA + lang("0.has.resigned", player.getName()));
cp.addResignTime(clan.getTag());
clan.removePlayerFromClan(player.getUniqueId());
return new MessagePromptImpl(AQUA + lang("resign.success", player));
} else if (clan.isLeader(player) && clan.getLeaders().size() == 1) {
clan.disband(player, true, false);
return new MessagePromptImpl(RED + lang("clan.has.been.disbanded", player, clan.getName()));
} else {
return new MessagePromptImpl(RED + lang("last.leader.cannot.resign.you.must.appoint.another.leader.or.disband.the.clan", player));
}
return new MessagePromptImpl(AQUA + lang("resign.success", sender));
} else if (sender.isLeader() && clan.getLeaders().size() == 1) {
clan.disband(sender.toPlayer(), true, false);
return new MessagePromptImpl(RED + lang("clan.has.been.disbanded", sender, clan.getName()));
} else {
return new MessagePromptImpl(RED + lang("resign.request.cancelled", player));
return new MessagePromptImpl(RED + lang("last.leader.cannot.resign.you.must.appoint.another.leader.or.disband.the.clan", sender));
}
}
@Override
public @NotNull String getPromptText(@NotNull ConversationContext cc) {
Player player = (Player) cc.getForWhom();
return RED + MessageFormat.format(
lang("resign.confirmation", player), Arrays.asList(
lang("yes", player), lang("cancel", player)));
protected String getPromptTextKey() {
return "resign.confirmation";
}
@Override
protected String getDeclineTextKey() {
return "resign.request.cancelled";
}
}
@@ -1,25 +1,24 @@
package net.sacredlabyrinth.phaed.simpleclans.events;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import org.bukkit.command.CommandSender;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import org.bukkit.event.Cancellable;
import org.bukkit.event.Event;
import org.bukkit.event.HandlerList;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
public class ClanBalanceUpdateEvent extends Event implements Cancellable {
private static final HandlerList HANDLER_LIST = new HandlerList();
private final CommandSender updater;
private final BankOperator updater;
private final Clan clan;
private final Cause cause;
private final double balance;
private double newBalance;
private boolean cancelled;
public ClanBalanceUpdateEvent(@Nullable CommandSender updater,
public ClanBalanceUpdateEvent(@NotNull BankOperator updater,
@NotNull Clan clan,
double balance,
double newBalance,
@@ -32,9 +31,9 @@ public class ClanBalanceUpdateEvent extends Event implements Cancellable {
}
/**
* @return the balance updater, may be null
* @return the balance updater
*/
public @Nullable CommandSender getUpdater() {
public @NotNull BankOperator getUpdater() {
return updater;
}
@@ -115,6 +114,10 @@ public class ClanBalanceUpdateEvent extends Event implements Cancellable {
* When the balance is updated via API methods
*/
API,
/**
* WHen the balance is updated via Internal methods
*/
INTERNAL,
/**
* When the clan data is being loaded and the balance is set, usually on server start up or plugin reload
*/
@@ -0,0 +1,54 @@
package net.sacredlabyrinth.phaed.simpleclans.events;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import org.bukkit.Location;
import org.bukkit.event.Cancellable;
import org.bukkit.event.Event;
import org.bukkit.event.HandlerList;
import org.jetbrains.annotations.NotNull;
public class ClanPlayerTeleportEvent extends Event implements Cancellable {
private static final HandlerList HANDLER_LIST = new HandlerList();
private boolean cancelled;
private final ClanPlayer player;
private final Location origin;
private final Location destination;
public ClanPlayerTeleportEvent(ClanPlayer player, Location origin, Location destination) {
this.player = player;
this.origin = origin;
this.destination = destination;
}
@Override
public @NotNull HandlerList getHandlers() {
return HANDLER_LIST;
}
public static HandlerList getHandlerList() {
return HANDLER_LIST;
}
@Override
public boolean isCancelled() {
return cancelled;
}
@Override
public void setCancelled(boolean cancel) {
cancelled = cancel;
}
public ClanPlayer getClanPlayer() {
return player;
}
public Location getOrigin() {
return origin;
}
public Location getDestination() {
return destination;
}
}
@@ -50,12 +50,16 @@ public class HomeRegroupEvent extends Event implements Cancellable {
public HandlerList getHandlers() {
return handlers;
}
public static HandlerList getHandlerList() {
return handlers;
}
@Override
public boolean isCancelled() {
return cancelled;
}
@Override
public void setCancelled(boolean cancel) {
cancelled = cancel;
@@ -0,0 +1,51 @@
package net.sacredlabyrinth.phaed.simpleclans.events;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import org.bukkit.event.Cancellable;
import org.bukkit.event.Event;
import org.bukkit.event.HandlerList;
import org.jetbrains.annotations.NotNull;
public class PlayerHomeClearEvent extends Event implements Cancellable {
private static final HandlerList HANDLER_LIST = new HandlerList();
private final Clan clan;
private final ClanPlayer cp;
private boolean cancelled;
public PlayerHomeClearEvent(Clan clan, ClanPlayer cp) {
this.clan = clan;
this.cp = cp;
}
public Clan getClan() {
return clan;
}
public ClanPlayer getCp() {
return cp;
}
@Override
public boolean isCancelled() {
return cancelled;
}
@Override
public void setCancelled(boolean cancel) {
this.cancelled = cancel;
}
@NotNull
@Override
public HandlerList getHandlers() {
return HANDLER_LIST;
}
public static HandlerList getHandlerList() {
return HANDLER_LIST;
}
}
@@ -9,6 +9,8 @@ import github.scarsz.discordsrv.dependencies.commons.lang3.StringUtils;
import github.scarsz.discordsrv.dependencies.emoji.EmojiParser;
import github.scarsz.discordsrv.dependencies.jda.api.Permission;
import github.scarsz.discordsrv.dependencies.jda.api.entities.*;
import github.scarsz.discordsrv.dependencies.jda.api.exceptions.ErrorResponseException;
import github.scarsz.discordsrv.dependencies.jda.api.requests.Response;
import github.scarsz.discordsrv.dependencies.jda.api.requests.RestAction;
import github.scarsz.discordsrv.dependencies.kyori.adventure.text.Component;
import github.scarsz.discordsrv.objects.managers.AccountLinkManager;
@@ -34,6 +36,7 @@ import java.util.concurrent.ExecutionException;
import java.util.logging.Level;
import java.util.stream.Collectors;
import static github.scarsz.discordsrv.dependencies.jda.api.Permission.MANAGE_CHANNEL;
import static github.scarsz.discordsrv.dependencies.jda.api.Permission.VIEW_CHANNEL;
import static net.sacredlabyrinth.phaed.simpleclans.ClanPlayer.Channel.CLAN;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
@@ -163,7 +166,9 @@ public class DiscordHook implements Listener {
@EventHandler
public void onClanCreate(CreateClanEvent event) {
try {
createChannel(event.getClan().getTag());
if (settingsManager.is(DISCORDCHAT_AUTO_CREATION)) {
createChannel(event.getClan().getTag());
}
} catch (DiscordHookException ex) {
// Clan is not following the conditions, categories are fulled or discord reaches the limit, nothing to do here.
SimpleClans.debug(ex.getMessage());
@@ -173,7 +178,7 @@ public class DiscordHook implements Listener {
@EventHandler
public void onPlayerClanLeave(PlayerKickedClanEvent event) {
ClanPlayer clanPlayer = event.getClanPlayer();
Clan clan = clanPlayer.getClan();
Clan clan = event.getClan();
Member member = getMember(clanPlayer);
if (member == null || clan == null) {
return;
@@ -186,7 +191,7 @@ public class DiscordHook implements Listener {
@EventHandler
public void onPlayerClanJoin(PlayerJoinedClanEvent event) {
ClanPlayer clanPlayer = event.getClanPlayer();
Clan clan = clanPlayer.getClan();
Clan clan = event.getClan();
Member member = getMember(clanPlayer);
if (member == null || clan == null) {
return;
@@ -324,6 +329,9 @@ public class DiscordHook implements Listener {
guild.getPublicRole().getIdLong(),
Collections.emptyList(),
Collections.singletonList(VIEW_CHANNEL)).
addMemberPermissionOverride(guild.getSelfMember().getIdLong(),
Arrays.asList(VIEW_CHANNEL, MANAGE_CHANNEL),
Collections.emptyList()).
submit().get();
textCategories.add(category.getId());
@@ -368,8 +376,14 @@ public class DiscordHook implements Listener {
throw new CategoriesLimitException("Discord reached the categories limit", "discord.reached.category.limit");
}
TextChannel textChannel = availableCategory.createTextChannel(clanTag).complete();
try {
availableCategory.createTextChannel(clanTag).complete();
} catch (ErrorResponseException ex) {
Response response = ex.getResponse();
plugin.getLogger().warning(String.format("Could not create a channel for clan %s, error %d - %s",
clanTag, response.code, response.message));
return;
}
for (Map.Entry<ClanPlayer, Member> entry : discordClanPlayers.entrySet()) {
// The map is formed from clan#getMembers (so the clan exists)
//noinspection ConstantConditions
@@ -513,6 +527,7 @@ public class DiscordHook implements Listener {
map(TextChannel::getMemberPermissionOverrides).
flatMap(Collection::stream).
filter(permissionOverride -> !Objects.equals(permissionOverride.getPermissionHolder(), guild.getPublicRole())).
filter(permissionOverride -> !Objects.equals(permissionOverride.getMember(), guild.getSelfMember())).
forEach(permissionOverride -> permissionOverride.delete().queue());
clanTags.stream().map(clanManager::getClan).
@@ -547,10 +562,8 @@ public class DiscordHook implements Listener {
@SuppressWarnings("ResultOfMethodCallIgnored")
private void sendPrivateMessage(TextChannel textChannel, Message eventMessage, String message) {
RestAction<PrivateChannel> privateChannelAction = eventMessage.getAuthor().openPrivateChannel();
textChannel.deleteMessageById(eventMessage.getId()).queue(unused -> {
String channelLink = "<#" + textChannel.getId() + ">";
privateChannelAction.flatMap(privateChannel -> privateChannel.sendMessage(message));
});
textChannel.deleteMessageById(eventMessage.getId()).queue(unused ->
privateChannelAction.flatMap(privateChannel -> privateChannel.sendMessage(message)));
}
private void validateChannel(@NotNull String clanTag)
@@ -626,7 +639,7 @@ public class DiscordHook implements Listener {
@SuppressWarnings("BooleanMethodIsAlwaysInverted")
private boolean createChannelSilently(ClanPlayer clanPlayer) {
Clan clan = clanPlayer.getClan();
if (clan == null) {
if (clan == null || !settingsManager.is(DISCORDCHAT_AUTO_CREATION)) {
return false;
}
@@ -0,0 +1,43 @@
package net.sacredlabyrinth.phaed.simpleclans.hooks.protection;
import org.bukkit.Location;
import java.util.Objects;
public class Coordinate {
private final double x;
private final double z;
public Coordinate(double x, double z) {
this.x = x;
this.z = z;
}
public Coordinate(Location location) {
this.x = location.getX();
this.z = location.getZ();
}
public double getX() {
return x;
}
public double getZ() {
return z;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Coordinate that = (Coordinate) o;
return Double.compare(that.getX(), getX()) == 0 && Double.compare(that.getZ(), getZ()) == 0;
}
@Override
public int hashCode() {
return Objects.hash(getX(), getZ());
}
}
@@ -2,18 +2,22 @@ package net.sacredlabyrinth.phaed.simpleclans.hooks.protection;
import org.jetbrains.annotations.NotNull;
import java.util.Objects;
import java.util.Set;
import java.util.UUID;
import java.util.*;
public class Land {
private final String id;
private final Set<UUID> owners;
private final List<Coordinate> coordinates;
public Land(@NotNull String id, @NotNull Set<UUID> owners) {
this(id, owners, Collections.emptyList());
}
public Land(@NotNull String id, @NotNull Set<UUID> owners, @NotNull List<Coordinate> coordinates) {
this.id = id;
this.owners = owners;
this.coordinates = coordinates;
}
@NotNull
@@ -26,6 +30,10 @@ public class Land {
return owners;
}
public @NotNull List<Coordinate> getCoordinates() {
return coordinates;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
@@ -1,5 +1,6 @@
package net.sacredlabyrinth.phaed.simpleclans.hooks.protection;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import org.bukkit.Location;
import org.bukkit.OfflinePlayer;
import org.bukkit.World;
@@ -12,6 +13,10 @@ import java.util.Set;
public interface ProtectionProvider {
default void register() {
SimpleClans.getInstance().getProtectionManager().registerProvider(this);
}
void setup() throws LinkageError, Exception;
@NotNull
@@ -4,6 +4,7 @@ import me.ryanhamshire.GriefPrevention.Claim;
import me.ryanhamshire.GriefPrevention.DataStore;
import me.ryanhamshire.GriefPrevention.GriefPrevention;
import me.ryanhamshire.GriefPrevention.events.ClaimCreatedEvent;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.Coordinate;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.Land;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.ProtectionProvider;
import org.bukkit.Bukkit;
@@ -15,10 +16,7 @@ import org.bukkit.event.Event;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import java.util.UUID;
import java.util.*;
@SuppressWarnings("unused")
public class GriefPreventionProvider implements ProtectionProvider {
@@ -91,8 +89,10 @@ public class GriefPreventionProvider implements ProtectionProvider {
if (claim == null) {
return null;
}
List<Coordinate> coords = Arrays.asList(new Coordinate(claim.getLesserBoundaryCorner()),
new Coordinate(claim.getGreaterBoundaryCorner()));
return new Land(getIdPrefix() + claim.getID().toString(), Collections.singleton(getOwnerID(claim)));
return new Land(getIdPrefix() + claim.getID().toString(), Collections.singleton(getOwnerID(claim)), coords);
}
@SuppressWarnings("deprecation")
@@ -1,100 +0,0 @@
package net.sacredlabyrinth.phaed.simpleclans.hooks.protection.providers;
import com.intellectualcrafters.plot.PS;
import com.intellectualcrafters.plot.object.Plot;
import com.plotsquared.bukkit.events.PlayerClaimPlotEvent;
import com.plotsquared.bukkit.util.BukkitUtil;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.Land;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.ProtectionProvider;
import org.bukkit.Location;
import org.bukkit.OfflinePlayer;
import org.bukkit.World;
import org.bukkit.entity.Player;
import org.bukkit.event.Event;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Collection;
import java.util.Collections;
import java.util.Set;
import java.util.stream.Collectors;
@SuppressWarnings("unused")
public class PlotSquared3Provider implements ProtectionProvider {
private Method getLocation;
private Method getPlots;
@Override
public void setup() throws ClassNotFoundException, NoSuchMethodException {
Class.forName("com.intellectualcrafters.plot.object.Location");
Class.forName("com.intellectualcrafters.plot.object.Plot");
getLocation = BukkitUtil.class.getMethod("getLocation", Location.class);
}
@Override
public @NotNull Set<Land> getLandsAt(@NotNull Location location) {
Plot plot = getPlot(location);
if (plot != null) {
return Collections.singleton(getLand(plot));
}
return Collections.emptySet();
}
private @Nullable Plot getPlot(@NotNull Location location) {
try {
return Plot.getPlot((com.intellectualcrafters.plot.object.Location) getLocation.invoke(null, location));
} catch (IllegalAccessException | InvocationTargetException e) {
return null;
}
}
private Land getLand(@NotNull Plot plot) {
String id = getIdPrefix() + plot.getId().toString();
return new Land(id, plot.getOwners());
}
@Override
public @NotNull Set<Land> getLandsOf(@NotNull OfflinePlayer player, @NotNull World world) {
Set<Plot> plots = PS.get().getPlots(world.getName(), player.getUniqueId());
return plots.stream().map(this::getLand).collect(Collectors.toSet());
}
@Override
public @NotNull String getIdPrefix() {
return "ps";
}
@Override
public void deleteLand(@NotNull String id, @NotNull World world) {
id = id.replace(getIdPrefix(), "");
Collection<Plot> plots = PS.get().getPlots(world.getName());
for (Plot plot : plots) {
if (plot.getId().toString().equals(id)) {
plot.deletePlot(null);
break;
}
}
}
@Override
public @Nullable Class<? extends Event> getCreateLandEvent() {
return PlayerClaimPlotEvent.class;
}
@Override
public @Nullable Player getPlayer(Event event) {
if (event instanceof PlayerClaimPlotEvent) {
return ((PlayerClaimPlotEvent) event).getPlayer();
}
return null;
}
@Override
public @Nullable String getRequiredPluginName() {
return "PlotSquared";
}
}
@@ -4,6 +4,7 @@ import com.sk89q.worldguard.bukkit.WorldGuardPlugin;
import com.sk89q.worldguard.protection.ApplicableRegionSet;
import com.sk89q.worldguard.protection.managers.RegionManager;
import com.sk89q.worldguard.protection.regions.ProtectedRegion;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.Coordinate;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.Land;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.ProtectionProvider;
import org.bukkit.Location;
@@ -16,9 +17,7 @@ import org.jetbrains.annotations.Nullable;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import java.util.*;
@SuppressWarnings("unused")
public class WorldGuard6Provider implements ProtectionProvider {
@@ -26,14 +25,20 @@ public class WorldGuard6Provider implements ProtectionProvider {
private WorldGuardPlugin worldGuard;
private Method getRegionManager;
private Method getApplicableRegions;
private Method getPoints;
private Method getX;
private Method getZ;
@SuppressWarnings("JavaReflectionMemberAccess")
@Override
public void setup() throws NoSuchMethodException {
public void setup() throws NoSuchMethodException, ClassNotFoundException {
worldGuard = WorldGuardPlugin.inst();
getRegionManager = worldGuard.getClass().getMethod("getRegionManager", World.class);
//noinspection JavaReflectionMemberAccess
getApplicableRegions = RegionManager.class.getMethod("getApplicableRegions", Location.class);
getPoints = ProtectedRegion.class.getMethod("getPoints");
Class<?> blockVector = Class.forName("com.sk89q.worldedit.BlockVector2");
getX = blockVector.getMethod("getX");
getZ = blockVector.getMethod("getZ");
}
private @Nullable RegionManager getRegionManager(@Nullable World world) {
@@ -56,7 +61,25 @@ public class WorldGuard6Provider implements ProtectionProvider {
@NotNull
private Land getLand(ProtectedRegion region) {
return new Land(getIdPrefix() + region.getId(), region.getOwners().getUniqueIds());
List<Coordinate> coordinates = getCoordinates(region);
return new Land(getIdPrefix() + region.getId(), region.getOwners().getUniqueIds(), coordinates);
}
@NotNull
private List<Coordinate> getCoordinates(ProtectedRegion region) {
List<Coordinate> coordinates = new ArrayList<>();
try {
List<?> points = (List<?>) getPoints.invoke(region);
for (Object point : points) {
double x = (double) getX.invoke(point);
double z = (double) getZ.invoke(point);
coordinates.add(new Coordinate(x, z));
}
} catch (ReflectiveOperationException ex) {
ex.printStackTrace();
}
return coordinates;
}
@Override
@@ -1,11 +1,13 @@
package net.sacredlabyrinth.phaed.simpleclans.hooks.protection.providers;
import com.sk89q.worldedit.bukkit.BukkitAdapter;
import com.sk89q.worldedit.math.BlockVector2;
import com.sk89q.worldguard.WorldGuard;
import com.sk89q.worldguard.protection.ApplicableRegionSet;
import com.sk89q.worldguard.protection.managers.RegionManager;
import com.sk89q.worldguard.protection.regions.ProtectedRegion;
import com.sk89q.worldguard.protection.regions.RegionContainer;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.Coordinate;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.Land;
import net.sacredlabyrinth.phaed.simpleclans.hooks.protection.ProtectionProvider;
import org.bukkit.Location;
@@ -16,9 +18,7 @@ import org.bukkit.event.Event;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import java.util.*;
@SuppressWarnings({"unused"})
public class WorldGuardProvider implements ProtectionProvider {
@@ -46,7 +46,12 @@ public class WorldGuardProvider implements ProtectionProvider {
@NotNull
private Land getLand(ProtectedRegion region) {
return new Land(getIdPrefix() + region.getId(), region.getOwners().getUniqueIds());
//noinspection DuplicatedCode
List<Coordinate> coordinates = new ArrayList<>();
for (BlockVector2 point : region.getPoints()) {
coordinates.add(new Coordinate(point.getX(), point.getZ()));
}
return new Land(getIdPrefix() + region.getId(), region.getOwners().getUniqueIds(), coordinates);
}
@Override
@@ -1,10 +1,7 @@
package net.sacredlabyrinth.phaed.simpleclans.listeners;
import net.sacredlabyrinth.phaed.simpleclans.ChatBlock;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer.Channel;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.managers.PermissionsManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
import org.bukkit.Bukkit;
@@ -15,7 +12,6 @@ import org.bukkit.event.EventHandler;
import org.bukkit.event.EventPriority;
import org.bukkit.event.player.*;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Objects;
@@ -87,23 +83,15 @@ public class SCPlayerListener extends SCListener {
if (isBlacklistedWorld(player)) {
return;
}
ClanPlayer cp = plugin.getClanManager().getAnyClanPlayer(player.getUniqueId());
ClanPlayer cp;
if (settingsManager.is(PERFORMANCE_USE_BUNGEECORD)) {
cp = plugin.getClanManager().getClanPlayerJoinEvent(player);
} else {
cp = plugin.getClanManager().getAnyClanPlayer(player.getUniqueId());
}
updatePlayerName(cp);
updatePlayerName(player);
plugin.getClanManager().updateLastSeen(player);
plugin.getClanManager().updateDisplayName(player);
if (cp == null) {
return;
}
cp.setName(player.getName());
plugin.getPermissionsManager().addPlayerPermissions(cp);
if (settingsManager.is(BB_SHOW_ON_LOGIN) && cp.isBbEnabled() && cp.getClan() != null) {
@@ -121,10 +109,11 @@ public class SCPlayerListener extends SCListener {
}
Clan clan = plugin.getClanManager().getClanByPlayerUniqueId(player.getUniqueId());
if (clan != null) {
Location home = clan.getHomeLocation();
if (home != null) {
event.setRespawnLocation(home);
Location home;
if (clan != null && (home = clan.getHomeLocation()) != null) {
String homeServer = new Flags(clan.getFlags()).getString("homeServer", "");
if (homeServer.isEmpty() || plugin.getProxyManager().getServerName().equals(homeServer)) {
event.setRespawnLocation(plugin.getTeleportManager().getSafe(home));
}
}
}
@@ -187,27 +176,27 @@ public class SCPlayerListener extends SCListener {
}, plugin, true);
}
private void updatePlayerName(@Nullable ClanPlayer cp) {
if (cp == null) {
return;
}
Bukkit.getScheduler().runTaskAsynchronously(plugin, () -> {
ClanPlayer duplicate = null;
for (ClanPlayer other : plugin.getClanManager().getAllClanPlayers()) {
if (other.getName().equals(cp.getName()) && !other.getUniqueId().equals(cp.getUniqueId())) {
duplicate = other;
break;
}
}
private void updatePlayerName(@NotNull final Player player) {
final ClanPlayer cp = plugin.getClanManager().getAnyClanPlayer(player.getUniqueId());
if (duplicate != null) {
plugin.getLogger().warning(String.format("Found duplicate for %s, UUIDs: %s, %s", cp.getName(),
cp.getUniqueId(), duplicate.getUniqueId()));
duplicate.setName(duplicate.getName() + "_duplicate");
plugin.getStorageManager().updatePlayerName(duplicate);
ClanPlayer duplicate = null;
for (ClanPlayer other : plugin.getClanManager().getAllClanPlayers()) {
if (other.getName().equals(player.getName()) && !other.getUniqueId().equals(player.getUniqueId())) {
duplicate = other;
break;
}
}
if (duplicate != null) {
plugin.getLogger().warning(String.format("Found duplicate for %s, UUIDs: %s, %s", player.getName(),
player.getUniqueId(), duplicate.getUniqueId()));
duplicate.setName(duplicate.getName() + "_duplicate");
plugin.getStorageManager().updatePlayerName(duplicate);
}
if (cp != null) {
cp.setName(player.getName());
plugin.getStorageManager().updatePlayerName(cp);
});
}
}
}
@@ -2,12 +2,8 @@ package net.sacredlabyrinth.phaed.simpleclans.loggers;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.EconomyResponse;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.events.ClanBalanceUpdateEvent;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
@@ -25,16 +21,16 @@ public class BankLog {
private final DecimalFormat decimalFormat = new DecimalFormat("##.##");
private final SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd - HH:mm");
private final CommandSender sender;
private final BankOperator operator;
private final Clan clan;
private final EconomyResponse economyResponse;
private final BankLogger.Operation operation;
private final ClanBalanceUpdateEvent.Cause cause;
private final double amount;
public BankLog(@Nullable CommandSender sender, @NotNull Clan clan, @NotNull EconomyResponse economyResponse,
public BankLog(@NotNull BankOperator operator, @NotNull Clan clan, @NotNull EconomyResponse economyResponse,
@NotNull BankLogger.Operation operation, ClanBalanceUpdateEvent.Cause cause, double amount) {
this.sender = sender;
this.operator = operator;
this.clan = clan;
this.economyResponse = economyResponse;
this.operation = operation;
@@ -43,28 +39,27 @@ public class BankLog {
}
public static List<String> getHeader() {
return Arrays.asList("Date", "Sender", "Clan Name", "Response", "Operation", "Cause", "Sender Balance", "Amount", "Clan Balance");
return Arrays.asList("Date", "Sender", "Clan Name", "Response",
"Operation", "Cause", "Sender Balance", "Amount", "Clan Balance");
}
public List<String> getValues() {
double senderMoney = (sender instanceof Player) ? SimpleClans.getInstance().getPermissionsManager().playerGetMoney((Player) sender) : 0;
List<String> values = new ArrayList<>();
values.add(dateFormat.format(new Date()));
values.add(sender != null ? sender.getName() : "API");
values.add(operator.getName());
values.add(clan.getName());
values.add(economyResponse.name());
values.add(operation.name());
values.add(cause.name());
values.add(decimalFormat.format(senderMoney));
values.add(decimalFormat.format(operator.getBalance()));
values.add(decimalFormat.format(amount));
values.add(decimalFormat.format(clan.getBalance()));
return values;
}
public CommandSender getSender() {
return sender;
public BankOperator getOperator() {
return operator;
}
public Clan getClan() {
@@ -0,0 +1,34 @@
package net.sacredlabyrinth.phaed.simpleclans.loggers;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import org.bukkit.command.CommandSender;
import org.jetbrains.annotations.NotNull;
public class BankOperator {
public static final BankOperator API = new BankOperator("API", 0);
public static final BankOperator INTERNAL = new BankOperator("Internal", 0);
private final String name;
private final double balance;
public BankOperator(@NotNull CommandSender sender, double balance) {
this(sender.getName(), balance);
}
public BankOperator(@NotNull ClanPlayer sender, double balance) {
this(sender.getName(), balance);
}
public BankOperator(@NotNull String name, double balance) {
this.name = name;
this.balance = balance;
}
public @NotNull String getName() {
return name;
}
public double getBalance() {
return balance;
}
}
@@ -14,6 +14,7 @@ import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.hooks.discord.DiscordHook;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import org.bukkit.Bukkit;
import org.bukkit.OfflinePlayer;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -24,7 +25,7 @@ import java.util.stream.Collectors;
import static net.sacredlabyrinth.phaed.simpleclans.ClanPlayer.Channel;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.SPIGOT;
import static net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source.DISCORD;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.*;
import static org.bukkit.Bukkit.getPluginManager;
@@ -43,7 +44,6 @@ public final class ChatManager {
}
}
@SuppressWarnings("unused")
@Subscribe
public void registerDiscord(DiscordReadyEvent event) {
discordHook = new DiscordHook(plugin);
@@ -63,12 +63,11 @@ public final class ChatManager {
return discordHook;
}
public void processChat(@NotNull Source source, @NotNull Channel channel,
@NotNull ClanPlayer clanPlayer, String message) {
Clan clan = Objects.requireNonNull(clanPlayer.getClan(), "Clan cannot be null");
List<ClanPlayer> receivers = new ArrayList<>();
public void processChat(@NotNull SCMessage message) {
Clan clan = Objects.requireNonNull(message.getSender().getClan(), "Clan cannot be null");
switch (channel) {
List<ClanPlayer> receivers = new ArrayList<>();
switch (message.getChannel()) {
case ALLY:
if (!plugin.getSettingsManager().is(ALLYCHAT_ENABLE)) {
return;
@@ -84,20 +83,24 @@ public final class ChatManager {
return;
}
receivers.addAll(clan.getOnlineMembers().stream().
filter(member -> !member.isMuted()).
receivers.addAll(clan.getOnlineMembers().stream().filter(member -> !member.isMuted()).
collect(Collectors.toList()));
}
SCMessage scMessage = new SCMessage(source, channel, clanPlayer, ChatUtils.stripColors(message), receivers);
message.setReceivers(receivers);
for (ChatHandler ch : handlers) {
if (ch.canHandle(source)) {
ch.sendMessage(scMessage);
if (ch.canHandle(message.getSource())) {
ch.sendMessage(message.clone());
}
}
}
public void processChat(@NotNull Source source, @NotNull Channel channel,
@NotNull ClanPlayer clanPlayer, String message) {
Objects.requireNonNull(clanPlayer.getClan(), "Clan cannot be null");
processChat(new SCMessage(source, channel, clanPlayer, message));
}
public String parseChatFormat(String format, SCMessage message) {
return parseChatFormat(format, message, new HashMap<>());
}
@@ -112,7 +115,7 @@ public final class ChatManager {
String rank = sender.getRankId().isEmpty() ? null : ChatUtils.parseColors(sender.getRankDisplayName());
ConfigField configField = ConfigField.valueOf(String.format("%sCHAT_RANK",
message.getSource() == SPIGOT ? message.getChannel() : message.getSource()));
message.getSource() == DISCORD ? "DISCORD" : message.getChannel()));
String rankFormat = (rank != null) ? sm.getColored(configField).replace("%rank%", rank) : "";
if (placeholders != null) {
@@ -130,15 +133,28 @@ public final class ChatManager {
.replace("%rank%", rankFormat)
.replace("%message%", message.getContent());
return getPluginManager().getPlugin("PlaceholderAPI") != null ?
PlaceholderAPI.setPlaceholders(Bukkit.getOfflinePlayer(message.getSender().getUniqueId()), parsedFormat)
: parsedFormat;
return parseWithPapi(message.getSender(), parsedFormat);
}
public boolean isDiscordHookEnabled() {
return getPluginManager().getPlugin("DiscordSRV") != null && plugin.getSettingsManager().is(DISCORDCHAT_ENABLE);
}
private String parseWithPapi(ClanPlayer cp, String message) {
if (getPluginManager().getPlugin("PlaceholderAPI") == null) {
return message;
}
OfflinePlayer sender = Bukkit.getOfflinePlayer(cp.getUniqueId());
message = PlaceholderAPI.setPlaceholders(sender, message);
// If there are still placeholders left, try to parse them
// E.g. if the user has a placeholder as LuckPerms prefix/suffix
if (message.contains("%")) {
message = PlaceholderAPI.setPlaceholders(sender, message);
}
return message;
}
private void registerHandlers() {
Set<Class<? extends ChatHandler>> chatHandlers =
Helper.getSubTypesOf("net.sacredlabyrinth.phaed.simpleclans.chat.handlers", ChatHandler.class);
@@ -148,7 +164,7 @@ public final class ChatManager {
try {
handlers.add(handler.getConstructor().newInstance());
} catch (InstantiationException | IllegalAccessException | InvocationTargetException | NoSuchMethodException ex) {
plugin.getLogger().log(Level.SEVERE, "Error while trying to register {0} handler: " +
plugin.getLogger().log(Level.SEVERE, "Error while trying to register {0}: " +
ex.getMessage(), handler.getSimpleName());
}
}
@@ -4,6 +4,7 @@ import com.cryptomorin.xseries.XMaterial;
import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.events.ClanBalanceUpdateEvent;
import net.sacredlabyrinth.phaed.simpleclans.events.CreateClanEvent;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import net.sacredlabyrinth.phaed.simpleclans.utils.VanishUtils;
import net.sacredlabyrinth.phaed.simpleclans.uuid.UUIDMigration;
@@ -23,6 +24,8 @@ import java.time.Instant;
import java.time.LocalDateTime;
import java.time.temporal.ChronoUnit;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.logging.Level;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.*;
@@ -34,8 +37,8 @@ import static org.bukkit.ChatColor.RED;
public final class ClanManager {
private final SimpleClans plugin;
private final HashMap<String, Clan> clans = new HashMap<>();
private final HashMap<String, ClanPlayer> clanPlayers = new HashMap<>();
private final ConcurrentHashMap<String, Clan> clans = new ConcurrentHashMap<>();
private final ConcurrentHashMap<UUID, ClanPlayer> clanPlayers = new ConcurrentHashMap<>();
private final HashMap<ClanPlayer, List<Kill>> kills = new HashMap<>();
/**
@@ -121,7 +124,7 @@ public final class ClanManager {
*/
public void importClanPlayer(ClanPlayer cp) {
if (cp.getUniqueId() != null) {
this.clanPlayers.put(cp.getUniqueId().toString(), cp);
this.clanPlayers.put(cp.getUniqueId(), cp);
}
}
@@ -131,11 +134,13 @@ public final class ClanManager {
public void createClan(Player player, String colorTag, String name) {
ClanPlayer cp = getCreateClanPlayer(player.getUniqueId());
boolean verified = !plugin.getSettingsManager().is(REQUIRE_VERIFICATION) || plugin.getPermissionsManager().has(player, "simpleclans.mod.verify");
boolean verified = !plugin.getSettingsManager().is(REQUIRE_VERIFICATION)
|| plugin.getPermissionsManager().has(player, "simpleclans.mod.verify");
Clan clan = new Clan(colorTag, name, verified);
clan.addPlayerToClan(cp);
cp.setLeader(true);
clan.getRanks().addAll(plugin.getSettingsManager().getStarterRanks());
plugin.getStorageManager().insertClan(clan);
importClan(clan);
@@ -166,7 +171,7 @@ public final class ClanManager {
if (clan != null) {
clan.removePlayerFromClan(cp.getUniqueId());
}
clanPlayers.remove(cp.getUniqueId().toString());
clanPlayers.remove(cp.getUniqueId());
plugin.getStorageManager().deleteClanPlayer(cp);
}
@@ -174,7 +179,7 @@ public final class ClanManager {
* Delete a player data from memory
*/
public void deleteClanPlayerFromMemory(UUID playerUniqueId) {
clanPlayers.remove(playerUniqueId.toString());
clanPlayers.remove(playerUniqueId);
}
/**
@@ -238,6 +243,7 @@ public final class ClanManager {
* Gets the ClanPlayer data object if a player is currently in a clan, null
* if he's not in a clan Used for BungeeCord Reload ClanPlayer and your Clan
*/
@Deprecated
public @Nullable ClanPlayer getClanPlayerJoinEvent(Player player) {
SimpleClans.getInstance().getStorageManager().importFromDatabaseOnePlayer(player);
return getClanPlayer(player.getUniqueId());
@@ -264,7 +270,7 @@ public final class ClanManager {
* if he's not in a clan
*/
public @Nullable ClanPlayer getClanPlayer(UUID playerUniqueId) {
ClanPlayer cp = clanPlayers.get(playerUniqueId.toString());
ClanPlayer cp = clanPlayers.get(playerUniqueId);
if (cp == null) {
return null;
@@ -295,7 +301,7 @@ public final class ClanManager {
return null;
}
ClanPlayer cp = clanPlayers.get(uuid.toString());
ClanPlayer cp = clanPlayers.get(uuid);
if (cp == null) {
return null;
@@ -317,7 +323,7 @@ public final class ClanManager {
@Nullable
public ClanPlayer getAnyClanPlayer(UUID uuid) {
return clanPlayers.get(uuid.toString());
return clanPlayers.get(uuid);
}
@SuppressWarnings("deprecation")
@@ -346,16 +352,28 @@ public final class ClanManager {
/**
* Gets the ClanPlayer object for the player, creates one if not found
*/
public ClanPlayer getCreateClanPlayer(UUID playerUniqueId) {
Objects.requireNonNull(playerUniqueId, "UUID must not be null");
if (clanPlayers.containsKey(playerUniqueId.toString())) {
return clanPlayers.get(playerUniqueId.toString());
public ClanPlayer getCreateClanPlayer(UUID uuid) {
Objects.requireNonNull(uuid, "UUID must not be null");
if (clanPlayers.containsKey(uuid)) {
return clanPlayers.get(uuid);
}
ClanPlayer cp = new ClanPlayer(playerUniqueId);
ClanPlayer cp = new ClanPlayer(uuid);
plugin.getStorageManager().insertClanPlayer(cp);
importClanPlayer(cp);
boolean save = true;
for (ClanPlayer other : getAllClanPlayers()) {
if (other.getName().equals(cp.getName())) {
save = false;
break;
}
}
if (save) {
plugin.getStorageManager().insertClanPlayer(cp);
importClanPlayer(cp);
} else if (plugin.getSettingsManager().is(DEBUG)) {
plugin.getLogger().log(Level.WARNING, String.format("There already is a ClanPlayer with the name %s",
cp.getName()), new Exception());
}
return cp;
}
@@ -375,13 +393,8 @@ public final class ClanManager {
if (plugin.getSettingsManager().is(DISABLE_MESSAGES)) {
return;
}
Collection<? extends Player> players = Bukkit.getOnlinePlayers();
for (Player player : players) {
ChatBlock.sendMessage(player, ChatColor.DARK_GRAY + "* " + ChatColor.AQUA + msg);
}
SimpleClans.getInstance().getServer().getConsoleSender().sendMessage(ChatColor.AQUA + "[" + lang("server.announce") + "] " + ChatColor.WHITE + msg);
plugin.getProxyManager().sendMessage("ALL", ChatColor.DARK_GRAY + "* " + ChatColor.AQUA + msg);
Bukkit.getConsoleSender().sendMessage(ChatColor.AQUA + "[" + lang("server.announce") + "] " + ChatColor.WHITE + msg);
}
/**
@@ -1070,9 +1083,10 @@ public final class ClanManager {
}
}
} else {
switch (clan.withdraw(player, ClanBalanceUpdateEvent.Cause.COMMAND, price)) {
double money = plugin.getPermissionsManager().playerGetMoney(player);
switch (clan.withdraw(new BankOperator(player, money), ClanBalanceUpdateEvent.Cause.COMMAND, price)) {
case SUCCESS:
if (SimpleClans.getInstance().getPermissionsManager().playerGrantMoney(player, price)) {
if (plugin.getPermissionsManager().playerGrantMoney(player, price)) {
player.sendMessage(ChatColor.AQUA + lang("player.clan.withdraw", player, price));
clan.addBb(player.getName(), ChatColor.AQUA + lang("bb.clan.withdraw", price));
return true;
@@ -10,16 +10,15 @@ import org.bukkit.OfflinePlayer;
import org.bukkit.entity.Player;
import org.bukkit.permissions.PermissionAttachment;
import org.bukkit.plugin.RegisteredServiceProvider;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.text.MessageFormat;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.ENABLE_AUTO_GROUPS;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.PERMISSIONS_AUTO_GROUP_GROUPNAME;
/**
* @author phaed
@@ -63,7 +62,8 @@ public final class PermissionsManager {
public void loadPermissions() {
permissions.clear();
for (Clan clan : plugin.getClanManager().getClans()) {
permissions.put(clan.getTag(), SimpleClans.getInstance().getSettingsManager().getConfig().getStringList("permissions." + clan.getTag()));
permissions.put(clan.getTag(), SimpleClans.getInstance().getSettingsManager().getConfig().
getStringList("permissions." + clan.getTag()));
}
}
@@ -110,7 +110,7 @@ public final class PermissionsManager {
for (String perm : getPermissions(clan)) {
permAttaches.get(player).setPermission(perm, true);
}
if (plugin.getSettingsManager().is(ENABLE_AUTO_GROUPS)) {
if (plugin.getSettingsManager().is(PERMISSIONS_AUTO_GROUP_GROUPNAME)) {
permAttaches.get(player).setPermission("group." + clan.getTag(), true);
}
player.recalculatePermissions();
@@ -152,10 +152,10 @@ public final class PermissionsManager {
}
if (permission != null && cp.toPlayer() != null) {
permission.playerRemoveGroup(cp.toPlayer(), "clan_" + cp.getTag());
permission.playerRemoveGroup(cp.toPlayer(), "sc_untrusted");
permission.playerRemoveGroup(cp.toPlayer(), "sc_trusted");
permission.playerRemoveGroup(cp.toPlayer(), "sc_leader");
permission.playerRemoveGroup(null, cp.toPlayer(), "clan_" + cp.getTag());
permission.playerRemoveGroup(null, cp.toPlayer(), "sc_untrusted");
permission.playerRemoveGroup(null, cp.toPlayer(), "sc_trusted");
permission.playerRemoveGroup(null, cp.toPlayer(), "sc_leader");
}
}
@@ -166,22 +166,6 @@ public final class PermissionsManager {
return permissions.get(clan.getTag());
}
/**
* @return the PermissionsAttachments for every player
*/
public Map<Player, PermissionAttachment> getPermAttaches() {
return permAttaches;
}
/**
* Charge a player some money
*
*/
@Deprecated
public boolean playerChargeMoney(String player, double money) {
return economy.withdrawPlayer(player, money).transactionSuccess();
}
/**
* Charge a player some money
*
@@ -190,31 +174,6 @@ public final class PermissionsManager {
return economy.withdrawPlayer(player, money).transactionSuccess();
}
/**
* Charge a player some money
*
*/
public boolean playerChargeMoney(Player player, double money) {
return playerChargeMoney((OfflinePlayer) player, money);
}
/**
* Grants a player some money
*
*/
public boolean playerGrantMoney(Player player, double money) {
return economy.depositPlayer(player, money).transactionSuccess();
}
/**
* Grants a player some money
*
*/
@Deprecated
public boolean playerGrantMoney(String player, double money) {
return economy.depositPlayer(player, money).transactionSuccess();
}
/**
* Grants a player some money
*
@@ -228,7 +187,7 @@ public final class PermissionsManager {
*
* @return whether he has the money
*/
public boolean playerHasMoney(Player player, double money) {
public boolean playerHasMoney(OfflinePlayer player, double money) {
return economy.has(player, money);
}
@@ -237,28 +196,10 @@ public final class PermissionsManager {
*
* @return the players money
*/
public double playerGetMoney(Player player) {
public double playerGetMoney(OfflinePlayer player) {
return economy.getBalance(player);
}
/**
* Check if a player has permissions
*
* @param world the world
* @param player the player
* @param perm the permission
* @return whether he has the permission
*
* @deprecated use {@link PermissionsManager#has(Player, RankPermission, boolean)} or {@link PermissionsManager#has(Player, String)}
*/
public boolean has(@Nullable String world, OfflinePlayer player, String perm) {
if (player != null && permission != null) {
return permission.playerHas(world, player, perm);
}
return false;
}
/**
* Check if a player has permissions
*
@@ -266,7 +207,7 @@ public final class PermissionsManager {
* @param perm the permission
* @return whether he has the permission
*/
public boolean has(Player player, String perm) {
public boolean has(@Nullable Player player, String perm) {
if (player == null) {
SimpleClans.debug("null player");
return false;
@@ -409,21 +350,21 @@ public final class PermissionsManager {
return;
}
permission.playerRemoveGroup(player, "sc_leader");
permission.playerRemoveGroup(player, "sc_trusted");
permission.playerRemoveGroup(player, "sc_untrusted");
permission.playerRemoveGroup(null, player, "sc_leader");
permission.playerRemoveGroup(null, player, "sc_trusted");
permission.playerRemoveGroup(null, player, "sc_untrusted");
if (cp.getClan() != null) {
permission.playerAddGroup(player, "clan_" + cp.getTag());
permission.playerAddGroup(null, player, "clan_" + cp.getTag());
if (cp.isLeader()) {
permission.playerAddGroup(player, "sc_leader");
permission.playerAddGroup(null, player, "sc_leader");
return;
}
if (cp.isTrusted()) {
permission.playerAddGroup(player, "sc_trusted");
permission.playerAddGroup(null, player, "sc_trusted");
return;
}
permission.playerAddGroup(player, "sc_untrusted");
permission.playerAddGroup(null, player, "sc_untrusted");
}
}
@@ -17,6 +17,7 @@ import java.text.MessageFormat;
import java.util.*;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.CLAN_MAX_MEMBERS;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.REQUEST_FREQUENCY;
import static org.bukkit.ChatColor.RED;
@@ -194,24 +195,30 @@ public final class RequestManager {
}
public void processInvite(Request req, VoteResult vote) {
Clan clan = req.getClan();
String invited = req.getTarget();
requests.remove(req.getTarget().toLowerCase());
if (vote.equals(VoteResult.ACCEPT)) {
ClanPlayer cp = plugin.getClanManager().getCreateClanPlayerUUID(invited);
if (cp == null) {
return;
}
ChatBlock.sendMessageKey(Bukkit.getPlayerExact(invited), "accepted.invitation", clan.getName());
clan.addBb(ChatColor.AQUA + lang("joined.the.clan", invited));
plugin.getClanManager().serverAnnounce(lang("has.joined", invited, clan.getName()));
clan.addPlayerToClan(cp);
} else {
ChatBlock.sendMessageKey(Bukkit.getPlayerExact(invited), "denied.invitation", clan.getName());
clan.leaderAnnounce(RED + lang("membership.invitation", invited));
Clan clan = req.getClan();
Player invited = Bukkit.getPlayerExact(req.getTarget());
if (invited == null) {
return;
}
requests.remove(req.getTarget().toLowerCase());
if (vote.equals(VoteResult.ACCEPT)) {
ClanPlayer cp = plugin.getClanManager().getCreateClanPlayer(invited.getUniqueId());
int maxMembers = plugin.getSettingsManager().getInt(CLAN_MAX_MEMBERS);
if (maxMembers > 0 && maxMembers > clan.getSize()) {
ChatBlock.sendMessageKey(invited, "accepted.invitation", clan.getName());
clan.addBb(ChatColor.AQUA + lang("joined.the.clan", invited.getName()));
plugin.getClanManager().serverAnnounce(lang("has.joined", invited.getName(), clan.getName()));
clan.addPlayerToClan(cp);
} else {
ChatBlock.sendMessageKey(invited, "this.clan.has.reached.the.member.limit");
}
} else {
ChatBlock.sendMessageKey(invited, "denied.invitation", clan.getName());
clan.leaderAnnounce(RED + lang("membership.invitation", invited.getName()));
}
}
public void processResults(Request req) {
@@ -291,78 +298,78 @@ public final class RequestManager {
}
private void processDemote(Request req, Clan requestClan, UUID targetPlayer, List<String> denies) {
String demotedName = req.getTarget();
if (denies.isEmpty()) {
requestClan.addBb(lang("leaders"), ChatColor.AQUA
+ lang("demoted.back.to.member", demotedName));
requestClan.demote(targetPlayer);
} else {
String deniers = String.join(", ", denies);
requestClan.leaderAnnounce(
RED + lang("denied.demotion", deniers, demotedName));
}
}
String demotedName = req.getTarget();
if (denies.isEmpty()) {
requestClan.addBb(lang("leaders"), ChatColor.AQUA
+ lang("demoted.back.to.member", demotedName));
requestClan.demote(targetPlayer);
} else {
String deniers = String.join(", ", denies);
requestClan.leaderAnnounce(
RED + lang("denied.demotion", deniers, demotedName));
}
}
private void processBreakRivalry(ClanPlayer requester, Clan requestClan, Clan targetClan, List<String> accepts,
List<String> denies) {
if (targetClan != null && requestClan != null) {
if (!accepts.isEmpty()) {
requestClan.removeRival(targetClan);
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("broken.the.rivalry", accepts.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("broken.the.rivalry.with", requester.getName(), targetClan.getName()));
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.to.make.peace", denies.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("peace.agreement.denied", targetClan.getName()));
}
}
}
private void processBreakRivalry(ClanPlayer requester, Clan requestClan, @Nullable Clan targetClan,
List<String> accepts, List<String> denies) {
if (targetClan != null && requestClan != null) {
if (!accepts.isEmpty()) {
requestClan.removeRival(targetClan);
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("broken.the.rivalry", accepts.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("broken.the.rivalry.with", requester.getName(), targetClan.getName()));
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.to.make.peace", denies.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("peace.agreement.denied", targetClan.getName()));
}
}
}
private void processCreateAlly(ClanPlayer requester, Clan requestClan, Clan targetClan, List<String> accepts,
List<String> denies) {
if (targetClan != null && requestClan != null) {
if (!accepts.isEmpty()) {
requestClan.addAlly(targetClan);
private void processCreateAlly(ClanPlayer requester, Clan requestClan, @Nullable Clan targetClan,
List<String> accepts, List<String> denies) {
if (targetClan != null && requestClan != null) {
if (!accepts.isEmpty()) {
requestClan.addAlly(targetClan);
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("accepted.an.alliance", accepts.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("created.an.alliance", requester.getName(), targetClan.getName()));
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.an.alliance", denies.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("the.alliance.was.denied", targetClan.getName()));
}
}
}
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("accepted.an.alliance", accepts.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("created.an.alliance", requester.getName(), targetClan.getName()));
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.an.alliance", denies.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("the.alliance.was.denied", targetClan.getName()));
}
}
}
private void processEndWar(ClanPlayer requester, Clan requestClan, Clan targetClan, List<String> accepts,
private void processEndWar(ClanPlayer requester, Clan requestClan, @Nullable Clan targetClan, List<String> accepts,
List<String> denies) {
if (requestClan != null && targetClan != null) {
if (!accepts.isEmpty()) {
War war = plugin.getProtectionManager().getWar(requestClan, requestClan);
if (requestClan != null && targetClan != null) {
if (!accepts.isEmpty()) {
War war = plugin.getProtectionManager().getWar(requestClan, targetClan);
plugin.getProtectionManager().removeWar(war, WarEndEvent.Reason.REQUEST);
requestClan.removeWarringClan(targetClan);
targetClan.removeWarringClan(requestClan);
requestClan.removeWarringClan(targetClan);
targetClan.removeWarringClan(requestClan);
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("you.are.no.longer.at.war", accepts.get(0), requestClan.getColorTag()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("you.are.no.longer.at.war", requestClan.getName(), targetClan.getColorTag()));
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.war.end", denies.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("end.war.denied", targetClan.getName()));
}
}
}
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("you.are.no.longer.at.war", accepts.get(0), requestClan.getColorTag()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("you.are.no.longer.at.war", requestClan.getName(), targetClan.getColorTag()));
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.war.end", denies.get(0), requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("end.war.denied", targetClan.getName()));
}
}
}
private void processStartWar(ClanPlayer requester, Clan requestClan, Clan targetClan, List<String> accepts,
List<String> denies) {
if (requestClan != null && targetClan != null) {
if (!accepts.isEmpty()) {
plugin.getProtectionManager().addWar(requester, requestClan, targetClan);
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.war.req", denies.get(0),
private void processStartWar(ClanPlayer requester, Clan requestClan, @Nullable Clan targetClan,
List<String> accepts, List<String> denies) {
if (requestClan != null && targetClan != null) {
if (!accepts.isEmpty()) {
plugin.getProtectionManager().addWar(requester, requestClan, targetClan);
} else {
targetClan.addBb(requester.getName(), ChatColor.AQUA + lang("denied.war.req", denies.get(0),
requestClan.getName()));
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("end.war.denied",
requestClan.addBb(requester.getName(), ChatColor.AQUA + lang("end.war.denied",
targetClan.getName()));
}
}
}
}
}
}
/**
* End a pending request prematurely
@@ -1,6 +1,7 @@
package net.sacredlabyrinth.phaed.simpleclans.managers;
import com.cryptomorin.xseries.XMaterial;
import net.sacredlabyrinth.phaed.simpleclans.Rank;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.utils.ChatUtils;
import org.bukkit.Material;
@@ -250,6 +251,22 @@ public final class SettingsManager {
}
}
@SuppressWarnings("unchecked")
public @NotNull Collection<Rank> getStarterRanks() {
List<Rank> ranks = new ArrayList<>();
List<Map<?, ?>> mapList = config.getMapList("clan.starter-ranks");
for (Map<?, ?> rankMap : mapList) {
Set<String> names = (Set<String>) rankMap.keySet();
for (String name : names) {
Map<String, Object> rank = (Map<String, Object>) rankMap.get(name);
String displayName = (String) rank.get("display-name");
List<String> permissions = (List<String>) rank.get("permissions");
ranks.add(new Rank(name, displayName, new HashSet<>(permissions)));
}
}
return ranks;
}
public FileConfiguration getConfig() {
return config;
}
@@ -296,6 +313,7 @@ public final class SettingsManager {
LORE_LENGTH("settings.lore-length", 36),
PVP_ONLY_WHILE_IN_WAR("settings.pvp-only-while-at-war", false),
PAST_CLANS_LIMIT("settings.past-clans-limit", 10),
USERNAME_REGEX("settings.username-regex", "^\\**[a-zA-Z0-9_$]{1,16}$"),
/*
================
> Tag Settings
@@ -382,8 +400,8 @@ public final class SettingsManager {
ECONOMY_PURCHASE_HOME_TELEPORT_SET("economy.purchase-home-teleport-set", false),
ECONOMY_REGROUP_PRICE("economy.home-regroup-price", 5.0),
ECONOMY_PURCHASE_HOME_REGROUP("economy.purchase-home-regroup", false),
ECONOMY_PURCHASE_DISCORD_CREATE("purchase-discord-create", false),
ECONOMY_DISCORD_CREATION_PRICE("discord-creation-price", 1000.0),
ECONOMY_PURCHASE_DISCORD_CREATE("economy.purchase-discord-create", false),
ECONOMY_DISCORD_CREATION_PRICE("economy.discord-creation-price", 1000.0),
ECONOMY_UNIQUE_TAX_ON_REGROUP("economy.unique-tax-on-regroup", true),
ECONOMY_ISSUER_PAYS_REGROUP("economy.issuer-pays-regroup", true),
ECONOMY_MONEY_PER_KILL("economy.money-per-kill", false),
@@ -458,6 +476,7 @@ public final class SettingsManager {
PAGE_HEADINGS_COLOR("page.headings-color", "8"),
PAGE_SEPARATOR("page.separator", "-"),
PAGE_SIZE("page.size", 100),
HELP_SIZE("page.help-size", 10),
/*
================
> Clan Chat Settings
@@ -4,6 +4,7 @@ import com.google.common.base.Charsets;
import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.events.ClanBalanceUpdateEvent;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankLogger;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import net.sacredlabyrinth.phaed.simpleclans.storage.DBCore;
import net.sacredlabyrinth.phaed.simpleclans.storage.MySQLCore;
import net.sacredlabyrinth.phaed.simpleclans.storage.SQLiteCore;
@@ -18,7 +19,6 @@ import org.bukkit.inventory.ItemStack;
import org.bukkit.scheduler.BukkitRunnable;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.json.simple.JSONObject;
import java.sql.*;
import java.text.MessageFormat;
@@ -285,6 +285,7 @@ public final class StorageManager {
* Used for BungeeCord Reload ClanPlayer and your Clan
*
*/
@Deprecated
public void importFromDatabaseOnePlayer(Player player) {
plugin.getClanManager().deleteClanPlayerFromMemory(player.getUniqueId());
@@ -297,8 +298,8 @@ public final class StorageManager {
tm.importMember(cp);
}
plugin.getClanManager().importClanPlayer(cp);
plugin.getLogger().info("ClanPlayer Reloaded: " + player.getName() + ", UUID: " + player.getUniqueId().toString());
plugin.getLogger().info("ClanPlayer Reloaded: " + player.getName() + ", UUID: " + player.getUniqueId());
}
}
@@ -377,7 +378,7 @@ public final class StorageManager {
String packed_rivals = res.getString("packed_rivals");
String packed_bb = res.getString("packed_bb");
String flags = res.getString("flags");
JSONObject ranks = Helper.parseJson(res.getString("ranks"));
String ranksJson = res.getString("ranks");
long founded = res.getLong("founded");
long last_used = res.getLong("last_used");
double balance = res.getDouble("balance");
@@ -406,11 +407,11 @@ public final class StorageManager {
clan.setPackedBb(packed_bb);
clan.setFounded(founded);
clan.setLastUsed(last_used);
clan.setBalance(null, ClanBalanceUpdateEvent.Cause.LOADING, BankLogger.Operation.SET, balance);
clan.setBalance(BankOperator.INTERNAL, ClanBalanceUpdateEvent.Cause.LOADING, BankLogger.Operation.SET, balance);
clan.setMemberFee(feeValue);
clan.setMemberFeeEnabled(feeEnabled);
clan.setRanks(Helper.ranksFromJson(ranks));
clan.setDefaultRank(Helper.defaultRankFromJson(ranks));
clan.setRanks(Helper.ranksFromJson(ranksJson));
clan.setDefaultRank(Helper.defaultRankFromJson(ranksJson));
clan.setBanner(banner);
out.add(clan);
@@ -451,7 +452,7 @@ public final class StorageManager {
String packed_rivals = res.getString("packed_rivals");
String packed_bb = res.getString("packed_bb");
String flags = res.getString("flags");
JSONObject ranks = Helper.parseJson(res.getString("ranks"));
String ranksJson = res.getString("ranks");
long founded = res.getLong("founded");
long last_used = res.getLong("last_used");
double balance = res.getDouble("balance");
@@ -480,11 +481,11 @@ public final class StorageManager {
clan.setPackedBb(packed_bb);
clan.setFounded(founded);
clan.setLastUsed(last_used);
clan.setBalance(null, ClanBalanceUpdateEvent.Cause.LOADING, BankLogger.Operation.SET, balance);
clan.setBalance(BankOperator.INTERNAL, ClanBalanceUpdateEvent.Cause.LOADING, BankLogger.Operation.SET, balance);
clan.setMemberFee(feeValue);
clan.setMemberFeeEnabled(feeEnabled);
clan.setRanks(Helper.ranksFromJson(ranks));
clan.setDefaultRank(Helper.defaultRankFromJson(ranks));
clan.setRanks(Helper.ranksFromJson(ranksJson));
clan.setDefaultRank(Helper.defaultRankFromJson(ranksJson));
clan.setBanner(banner);
out = clan;
@@ -535,11 +536,7 @@ public final class StorageManager {
if (last_seen == 0) {
last_seen = (new Date()).getTime();
}
if (join_date == 0) {
join_date = (new Date()).getTime();
}
}
ClanPlayer cp = new ClanPlayer();
if (uuid != null) {
@@ -619,10 +616,6 @@ public final class StorageManager {
last_seen = (new Date()).getTime();
}
if (join_date == 0) {
join_date = (new Date()).getTime();
}
ClanPlayer cp = new ClanPlayer();
if (uuid != null) {
cp.setUniqueId(UUID.fromString(uuid));
@@ -660,7 +653,7 @@ public final class StorageManager {
clanReSync.setPackedBb(clanDB.getPackedBb());
clanReSync.setFounded(clanDB.getFounded());
clanReSync.setLastUsed(clanDB.getLastUsed());
clanReSync.setBalance(null, ClanBalanceUpdateEvent.Cause.LOADING, BankLogger.Operation.SET, clanDB.getBalance());
clanReSync.setBalance(BankOperator.INTERNAL, ClanBalanceUpdateEvent.Cause.LOADING, BankLogger.Operation.SET, clanDB.getBalance());
cp.setClan(clanReSync);
} else {
plugin.getClanManager().importClan(clanDB);
@@ -689,29 +682,31 @@ public final class StorageManager {
*
*/
public void insertClan(Clan clan) {
plugin.getProxyManager().sendUpdate(clan);
String query = "INSERT INTO `sc_clans` (`banner`, `ranks`, `description`, `fee_enabled`, `fee_value`, `verified`, `tag`," +
" `color_tag`, `name`, `friendly_fire`, `founded`, `last_used`, `packed_allies`, `packed_rivals`, " +
"`packed_bb`, `cape_url`, `flags`, `balance`) ";
String values = "VALUES ( '"
+ Helper.escapeQuotes(YAMLSerializer.serialize(clan.getBanner())) + "','"
+ Helper.escapeQuotes(Helper.ranksToJson(clan.getRanks(), clan.getDefaultRank())) + "','"
+ Helper.escapeQuotes(clan.getDescription())+ "',"
+ Helper.escapeQuotes(clan.getDescription())+ "',"
+ (clan.isMemberFeeEnabled() ? 1 : 0) +","
+ Helper.escapeQuotes(String.valueOf(clan.getMemberFee())) + ","
+ (clan.isVerified() ? 1 : 0) + ",'"
+ Helper.escapeQuotes(clan.getTag()) + "','"
+ Helper.escapeQuotes(clan.getColorTag()) + "','"
+ Helper.escapeQuotes(clan.getName()) + "',"
+ (clan.isFriendlyFire() ? 1 : 0) + ",'"
+ clan.getFounded() + "','"
+ clan.getLastUsed() + "','"
+ Helper.escapeQuotes(clan.getPackedAllies()) + "','"
+ Helper.escapeQuotes(clan.getPackedRivals()) + "','"
+ Helper.escapeQuotes(clan.getPackedBb()) + "','"
+ Helper.escapeQuotes(clan.getCapeUrl()) + "','"
+ Helper.escapeQuotes(clan.getFlags()) + "','"
+ Helper.escapeQuotes(String.valueOf(clan.getMemberFee())) + ","
+ (clan.isVerified() ? 1 : 0) + ",'"
+ Helper.escapeQuotes(clan.getTag()) + "','"
+ Helper.escapeQuotes(clan.getColorTag()) + "','"
+ Helper.escapeQuotes(clan.getName()) + "',"
+ (clan.isFriendlyFire() ? 1 : 0) + ",'"
+ clan.getFounded() + "','"
+ clan.getLastUsed() + "','"
+ Helper.escapeQuotes(clan.getPackedAllies()) + "','"
+ Helper.escapeQuotes(clan.getPackedRivals()) + "','"
+ Helper.escapeQuotes(clan.getPackedBb()) + "','"
+ Helper.escapeQuotes(clan.getCapeUrl()) + "','"
+ Helper.escapeQuotes(clan.getFlags()) + "','"
+ Helper.escapeQuotes(String.valueOf(clan.getBalance())) + "');";
core.insert(query + values);
core.executeUpdate(query + values);
}
/**
@@ -749,7 +744,7 @@ public final class StorageManager {
*/
public void updatePlayerName(final @NotNull ClanPlayer cp) {
String query = "UPDATE `sc_players` SET `name` = '" + cp.getName() + "' WHERE uuid = '" + cp.getUniqueId() + "';";
core.update(query);
core.executeUpdate(query);
}
/**
@@ -759,7 +754,7 @@ public final class StorageManager {
public void updateClan(Clan clan) {
updateClan(clan, true);
}
/**
* Update a clan to the database
*
@@ -771,6 +766,7 @@ public final class StorageManager {
if (updateLastUsed) {
clan.updateLastUsed();
}
plugin.getProxyManager().sendUpdate(clan);
if (plugin.getSettingsManager().is(PERFORMANCE_SAVE_PERIODICALLY)) {
modifiedClans.add(clan);
return;
@@ -815,8 +811,9 @@ public final class StorageManager {
* Delete a clan from the database
*/
public void deleteClan(Clan clan) {
plugin.getProxyManager().sendDelete(clan);
String query = "DELETE FROM `sc_clans` WHERE tag = '" + clan.getTag() + "';";
core.delete(query);
core.executeUpdate(query);
}
/**
@@ -824,9 +821,17 @@ public final class StorageManager {
*
*/
public void insertClanPlayer(ClanPlayer cp) {
String query = "INSERT INTO `sc_players` (`locale`, `resign_times`, `uuid`, `name`, `leader`, `tag`, `friendly_fire`, `neutral_kills`, `rival_kills`, `civilian_kills`, `deaths`, `last_seen`, `join_date`, `packed_past_clans`, `flags`) ";
String values = "VALUES ('"+cp.getLocale().toLanguageTag()+"', '"+ Helper.escapeQuotes(Helper.resignTimesToJson(cp.getResignTimes()))+ "', '" + cp.getUniqueId().toString() + "', '" + cp.getName() + "'," + (cp.isLeader() ? 1 : 0) + ",'" + Helper.escapeQuotes(cp.getTag()) + "'," + (cp.isFriendlyFire() ? 1 : 0) + "," + cp.getNeutralKills() + "," + cp.getRivalKills() + "," + cp.getCivilianKills() + "," + cp.getDeaths() + ",'" + cp.getLastSeen() + "',' " + cp.getJoinDate() + "','" + Helper.escapeQuotes(cp.getPackedPastClans()) + "','" + Helper.escapeQuotes(cp.getFlags()) + "');";
core.insert(query + values);
plugin.getProxyManager().sendUpdate(cp);
String query = "INSERT INTO `sc_players` (`uuid`, `name`, `leader`, `tag`, `friendly_fire`, `neutral_kills`, " +
"`rival_kills`, `civilian_kills`, `deaths`, `last_seen`, `join_date`, `packed_past_clans`, `flags`) ";
String values = "VALUES ('" + cp.getUniqueId().toString() + "', '" + cp.getName() + "',"
+ (cp.isLeader() ? 1 : 0) + ",'" + Helper.escapeQuotes(cp.getTag()) + "',"
+ (cp.isFriendlyFire() ? 1 : 0) + "," + cp.getNeutralKills() + "," + cp.getRivalKills()
+ "," + cp.getCivilianKills() + "," + cp.getDeaths() + ",'" + cp.getLastSeen() + "',' "
+ cp.getJoinDate() + "','" + Helper.escapeQuotes(cp.getPackedPastClans()) + "','"
+ Helper.escapeQuotes(cp.getFlags()) + "');";
core.executeUpdate(query + values);
}
/**
@@ -849,6 +854,7 @@ public final class StorageManager {
*/
public void updateClanPlayer(ClanPlayer cp) {
cp.updateLastSeen();
plugin.getProxyManager().sendUpdate(cp);
if (plugin.getSettingsManager().is(PERFORMANCE_SAVE_PERIODICALLY)) {
modifiedClanPlayers.add(cp);
return;
@@ -869,7 +875,7 @@ public final class StorageManager {
}
private void setValues(PreparedStatement statement, ClanPlayer cp) throws SQLException {
statement.setString(1, cp.getLocale().toLanguageTag());
statement.setString(1, Helper.toLanguageTag(cp.getLocale()));
statement.setString(2, Helper.resignTimesToJson(cp.getResignTimes()));
statement.setInt(3, cp.isLeader() ? 1 : 0);
statement.setString(4, cp.getTag());
@@ -896,8 +902,9 @@ public final class StorageManager {
clan.addBbWithoutSaving(ChatColor.AQUA + MessageFormat.format(lang("has.been.purged"), cp.getName()));
updateClan(clan, false);
}
plugin.getProxyManager().sendDelete(cp);
String query = "DELETE FROM `sc_players` WHERE uuid = '" + cp.getUniqueId() + "';";
core.delete(query);
core.executeUpdate(query);
deleteKills(cp.getUniqueId());
}
@@ -909,7 +916,7 @@ public final class StorageManager {
public void insertKill(Player attacker, String attackerTag, Player victim, String victimTag, String type) {
String query = "INSERT INTO `sc_kills` ( `attacker_uuid`, `attacker`, `attacker_tag`, `victim_uuid`, `victim`, `victim_tag`, `kill_type`) ";
String values = "VALUES ( '" + attacker.getUniqueId() + "','" + attacker.getName() + "','" + attackerTag + "','" + victim.getUniqueId() + "','" + victim.getName() + "','" + victimTag + "','" + type + "');";
core.insert(query + values);
core.executeUpdate(query + values);
}
/**
@@ -924,7 +931,7 @@ public final class StorageManager {
"`victim`, `victim_tag`, `kill_type`) ";
String values = "VALUES ( '" + attacker.getUniqueId() + "','" + attacker.getName() + "','" + attacker.getTag()
+ "','" + victim.getUniqueId() + "','" + victim.getName() + "','" + victim.getTag() + "','" + type + "');";
core.insert(query + values);
core.executeUpdate(query + values);
}
/**
@@ -934,7 +941,7 @@ public final class StorageManager {
@Deprecated
public void deleteKills(String playerName) {
String query = "DELETE FROM `sc_kills` WHERE `attacker` = '" + playerName + "'";
core.delete(query);
core.executeUpdate(query);
}
/**
@@ -943,7 +950,7 @@ public final class StorageManager {
*/
public void deleteKills(UUID playerUniqueId) {
String query = "DELETE FROM `sc_kills` WHERE `attacker_uuid` = '" + playerUniqueId + "'";
core.delete(query);
core.executeUpdate(query);
}
/**
@@ -1023,14 +1030,14 @@ public final class StorageManager {
*/
public void getMostKilled(DataCallback<Map<String, Integer>> callback) {
new BukkitRunnable() {
@Override
public void run() {
callback.onResultReady(getMostKilled());
}
}.runTaskAsynchronously(plugin);
}
/**
* Gets, asynchronously, a map of victim-{@literal >}count of all kills that specific player did and notifies via callback when it's ready
*
@@ -1043,21 +1050,21 @@ public final class StorageManager {
}
}.runTaskAsynchronously(plugin);
}
/**
* Callback that returns some data
*
*
* @author roinujnosde
*
*/
public interface DataCallback<T> {
/**
* Notifies when the result is ready
*
*
*/
void onResultReady(T data);
}
/**
* Updates the database to the latest version
*
@@ -1168,7 +1175,7 @@ public final class StorageManager {
* Updates the database to the latest version
*
*/
private void updatePlayersToUUID() {
plugin.getLogger().log(Level.WARNING, "Starting Migration to UUID Players !");
plugin.getLogger().log(Level.WARNING, "==================== ATTENTION DONT STOP BUKKIT ! ==================== ");
@@ -1187,13 +1194,13 @@ public final class StorageManager {
uuidPlayer = UUID.nameUUIDFromBytes(("OfflinePlayer:" + cp.getName()).getBytes(Charsets.UTF_8));
}
String query = "UPDATE `sc_players` SET uuid = '" + uuidPlayer.toString() + "' WHERE name = '" + cp.getName() + "';";
core.update(query);
core.executeUpdate(query);
String query2 = "UPDATE `sc_kills` SET attacker_uuid = '" + uuidPlayer.toString() + "' WHERE attacker = '" + cp.getName() + "';";
core.update(query2);
String query2 = "UPDATE `sc_kills` SET attacker_uuid = '" + uuidPlayer + "' WHERE attacker = '" + cp.getName() + "';";
core.executeUpdate(query2);
String query3 = "UPDATE `sc_kills` SET victim_uuid = '" + uuidPlayer.toString() + "' WHERE victim = '" + cp.getName() + "';";
core.update(query3);
String query3 = "UPDATE `sc_kills` SET victim_uuid = '" + uuidPlayer + "' WHERE victim = '" + cp.getName() + "';";
core.executeUpdate(query3);
plugin.getLogger().info("[" + i + " / " + cps.size() + "] Success: " + cp.getName() + "; UUID: " + uuidPlayer.toString());
} catch (Exception ex) {
plugin.getLogger().log(Level.WARNING, "[" + i + " / " + cps.size() + "] Failed [ERRO]: " + cp.getName() + "; UUID: ???");
@@ -1211,10 +1218,10 @@ public final class StorageManager {
SimpleClans.getInstance().setUUID(true);
}
/**
* Saves modified Clans and ClanPlayers to the database
*
*
* @author RoinujNosde
* @since 2.10.2
*/
@@ -2,9 +2,12 @@ package net.sacredlabyrinth.phaed.simpleclans.managers;
import io.papermc.lib.PaperLib;
import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.events.ClanPlayerTeleportEvent;
import net.sacredlabyrinth.phaed.simpleclans.utils.VanishUtils;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.block.Block;
import org.bukkit.entity.Player;
import org.bukkit.event.player.PlayerTeleportEvent;
import org.bukkit.inventory.ItemStack;
@@ -23,6 +26,9 @@ import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.Con
import static org.bukkit.ChatColor.AQUA;
import static org.bukkit.ChatColor.RED;
/**
* Class responsible for managing teleports and its queue
*/
public final class TeleportManager {
private final SimpleClans plugin;
private final HashMap<String, TeleportState> waitingPlayers = new HashMap<>();
@@ -40,67 +46,90 @@ public final class TeleportManager {
* @param clanName the Clan name
*/
public void addPlayer(Player player, Location destination, String clanName) {
PermissionsManager pm = plugin.getPermissionsManager();
int secs = SimpleClans.getInstance().getSettingsManager().getInt(CLAN_TELEPORT_DELAY);
if (plugin.getPermissionsManager().has(player, "simpleclans.mod.bypass")) {
if (pm.has(player, "simpleclans.mod.bypass") || pm.has(player, "simpleclans.vip.teleport-delay")) {
secs = 0;
}
waitingPlayers.put(player.getUniqueId().toString(), new TeleportState(player, destination, clanName, secs));
if (secs > 0) {
ChatBlock.sendMessage(player, AQUA
+ MessageFormat.format(lang("waiting.for.teleport.stand.still.for.0.seconds", player), secs));
}
}
@SuppressWarnings("deprecation")
private void sendTeleportBlocks(Player player, Location loc) {
int x = loc.getBlockX();
int z = loc.getBlockZ();
if (plugin.getSettingsManager().is(TELEPORT_BLOCKS)) {
player.sendBlockChange(new Location(loc.getWorld(), x + 1, loc.getBlockY() - 1, z + 1),
Material.GLASS, (byte) 0);
player.sendBlockChange(new Location(loc.getWorld(), x - 1, loc.getBlockY() - 1, z - 1),
Material.GLASS, (byte) 0);
player.sendBlockChange(new Location(loc.getWorld(), x + 1, loc.getBlockY() - 1, z - 1),
Material.GLASS, (byte) 0);
player.sendBlockChange(new Location(loc.getWorld(), x - 1, loc.getBlockY() - 1, z + 1),
Material.GLASS, (byte) 0);
}
}
private void teleport(Clan clan, Location location, List<ClanPlayer> members) {
for (ClanPlayer cp : members) {
Player player = cp.toPlayer();
if (player == null) {
continue;
}
int x = location.getBlockX();
int z = location.getBlockZ();
sendTeleportBlocks(player, location);
Random r = new Random();
int xx = r.nextInt(2) - 1;
int zz = r.nextInt(2) - 1;
if (xx == 0 && zz == 0) {
xx = 1;
}
x = x + xx;
z = z + zz;
plugin.getTeleportManager().addPlayer(player, new Location(location.getWorld(), x + .5,
location.getBlockY(), z + .5, location.getYaw(), location.getPitch()), clan.getName());
ChatBlock.sendMessage(player, AQUA + lang("waiting.for.teleport.stand.still.for.0.seconds", player, secs));
}
}
/**
* Teleports all online and non-vanished members of this {@link Clan} to the specified {@link Location}
*
* @param requester the Player requesting the teleport
* @param clan the Clan
* @param location the Location
*/
public void teleport(@NotNull Player requester, @NotNull Clan clan, @NotNull Location location) {
teleport(clan, location, VanishUtils.getNonVanished(requester, clan));
}
/**
* Teleports all online and non-vanished members of this {@link Clan} to the specified {@link Location}
*
* @param clan the Clan
* @param location the Location
*/
public void teleport(Clan clan, Location location) {
teleport(clan, location, VanishUtils.getNonVanished(null, clan));
}
public void teleportToHome(@NotNull Player player, @NotNull Location destination, @NotNull String clanName) {
PaperLib.teleportAsync(player, getSafe(destination), PlayerTeleportEvent.TeleportCause.COMMAND).thenAccept(result -> {
if (result) {
ChatBlock.sendMessage(player, AQUA + lang("now.at.homebase", player, clanName));
} else {
plugin.getLogger().log(Level.WARNING, "An error occurred while teleporting a player");
}
});
}
public void teleportToHome(@NotNull Player player, @NotNull Clan clan) {
if (clan.getHomeLocation() == null) {
return;
}
teleportToHome(player, clan.getHomeLocation(), clan.getName());
}
private boolean isSameBlock(Location loc, Location loc2) {
return loc.getBlockX() == loc2.getBlockX() && loc.getBlockY() == loc2.getBlockY() &&
loc.getBlockZ() == loc2.getBlockZ();
}
/**
* Converts the specified {@link Location} to a safe one, i.e. where there is no risk of suffocation
*
* @param location the Location
* @return the safe Location
*/
public @NotNull Location getSafe(@NotNull Location location) {
int counter = 0;
while (counter < 256) { //max world height
counter++;
Block bottom = location.getBlock();
Block top = location.add(0, 1, 0).getBlock();
if (!isAir(bottom)) {
continue;
}
if (!isAir(top)) {
location.add(0, 1, 0); //skips checking the same block again
continue;
}
location.subtract(0, 1, 0); //remove what was added above
return location;
}
//noinspection ConstantConditions
location.setY(location.getWorld().getHighestBlockYAt(location) + 1);
return location;
}
private void dropItems(Player player) {
if (plugin.getPermissionsManager().has(player, "simpleclans.mod.keep-items")) {
return;
@@ -155,6 +184,12 @@ public final class TeleportManager {
if (player == null) {
return;
}
ClanPlayer cp = plugin.getClanManager().getCreateClanPlayer(player.getUniqueId());
ClanPlayerTeleportEvent event = new ClanPlayerTeleportEvent(cp, state.getLocation(), state.getDestination());
Bukkit.getPluginManager().callEvent(event);
if (event.isCancelled()) {
return;
}
Location loc = state.getDestination();
sendTeleportBlocks(player, loc);
dropItems(player);
@@ -162,26 +197,61 @@ public final class TeleportManager {
teleportToHome(player, loc, state.getClanName());
}
public void teleportToHome(@NotNull Player player, @NotNull Location destination, @NotNull String clanName) {
PaperLib.teleportAsync(player, destination, PlayerTeleportEvent.TeleportCause.COMMAND).thenAccept(result -> {
if (result) {
ChatBlock.sendMessage(player, AQUA + lang("now.at.homebase", player, clanName));
} else {
plugin.getLogger().log(Level.WARNING, "An error occurred while teleporting a player");
}
});
}
@SuppressWarnings("deprecation")
private void sendTeleportBlocks(Player player, Location loc) {
int x = loc.getBlockX();
int z = loc.getBlockZ();
public void teleportToHome(@NotNull Player player, @NotNull Clan clan) {
if (clan.getHomeLocation() == null) {
return;
if (plugin.getSettingsManager().is(TELEPORT_BLOCKS)) {
player.sendBlockChange(new Location(loc.getWorld(), x + 1, loc.getBlockY() - 1, z + 1),
Material.GLASS, (byte) 0);
player.sendBlockChange(new Location(loc.getWorld(), x - 1, loc.getBlockY() - 1, z - 1),
Material.GLASS, (byte) 0);
player.sendBlockChange(new Location(loc.getWorld(), x + 1, loc.getBlockY() - 1, z - 1),
Material.GLASS, (byte) 0);
player.sendBlockChange(new Location(loc.getWorld(), x - 1, loc.getBlockY() - 1, z + 1),
Material.GLASS, (byte) 0);
}
teleportToHome(player, clan.getHomeLocation(), clan.getName());
}
private boolean isSameBlock(Location loc, Location loc2) {
return loc.getBlockX() == loc2.getBlockX() && loc.getBlockY() == loc2.getBlockY() &&
loc.getBlockZ() == loc2.getBlockZ();
private void teleport(Clan clan, Location location, List<ClanPlayer> members) {
for (ClanPlayer cp : members) {
Player player = cp.toPlayer();
if (player == null) {
continue;
}
int x = location.getBlockX();
int z = location.getBlockZ();
sendTeleportBlocks(player, location);
Random r = new Random();
int xx = r.nextInt(2) - 1;
int zz = r.nextInt(2) - 1;
if (xx == 0 && zz == 0) {
xx = 1;
}
x = x + xx;
z = z + zz;
plugin.getTeleportManager().addPlayer(player, new Location(location.getWorld(), x + .5,
location.getBlockY(), z + .5, location.getYaw(), location.getPitch()), clan.getName());
}
}
/**
* Checks if all passed blocks are some kind of AIR
*
* @param blocks blocks to test
* @return true if all blocks are AIR
*/
@SuppressWarnings("BooleanMethodIsAlwaysInverted")
private boolean isAir(@NotNull Block... blocks) {
for (Block b : blocks) {
if (!b.getType().name().contains("AIR")) {
return false;
}
}
return true;
}
}
@@ -0,0 +1,213 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy;
import com.google.common.io.ByteArrayDataInput;
import com.google.common.io.ByteArrayDataOutput;
import com.google.common.io.ByteStreams;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField;
import net.sacredlabyrinth.phaed.simpleclans.proxy.adapters.ClanPlayerListAdapter;
import net.sacredlabyrinth.phaed.simpleclans.proxy.adapters.ClanPlayerTypeAdapterFactory;
import net.sacredlabyrinth.phaed.simpleclans.proxy.adapters.ConfigurationSerializableAdapter;
import net.sacredlabyrinth.phaed.simpleclans.proxy.adapters.SCMessageAdapter;
import net.sacredlabyrinth.phaed.simpleclans.proxy.listeners.MessageListener;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.PlayerJoinEvent;
import org.bukkit.plugin.messaging.PluginMessageListener;
import org.jetbrains.annotations.NotNull;
import java.util.*;
import java.util.logging.Level;
public final class BungeeManager implements ProxyManager, PluginMessageListener {
private static final String UPDATE_CLAN_CHANNEL = "UpdateClan";
private static final String UPDATE_CLANPLAYER_CHANNEL = "UpdateClanPlayer";
private static final String DELETE_CLAN_CHANNEL = "DeleteClan";
private static final String DELETE_CLANPLAYER_CHANNEL = "DeleteClanPlayer";
private static final String CHAT_CHANNEL = "Chat";
private final SimpleClans plugin;
private final Gson gson;
private final List<String> onlinePlayers = new ArrayList<>();
private String serverName = "";
private final Set<String> unknownChannels = new HashSet<>();
public BungeeManager(SimpleClans plugin) {
this.plugin = plugin;
gson = new GsonBuilder().registerTypeAdapterFactory(new ClanPlayerTypeAdapterFactory(plugin))
.registerTypeAdapterFactory(new ConfigurationSerializableAdapter())
.registerTypeAdapter(ClanPlayerListAdapter.getType(), new ClanPlayerListAdapter(plugin))
.registerTypeAdapter(SCMessage.class, new SCMessageAdapter(plugin)).setExclusionStrategies()
.create();
if (!plugin.getSettingsManager().is(ConfigField.PERFORMANCE_USE_BUNGEECORD)) {
return;
}
Bukkit.getMessenger().registerOutgoingPluginChannel(plugin, "BungeeCord");
Bukkit.getMessenger().registerIncomingPluginChannel(plugin, "BungeeCord", this);
Bukkit.getScheduler().runTaskTimer(plugin, this::requestPlayerList, 0, 60 * 20);
requestServerName();
}
@SuppressWarnings("UnstableApiUsage")
public void onPluginMessageReceived(@NotNull String channel, @NotNull Player player, byte[] data) {
ByteArrayDataInput input = ByteStreams.newDataInput(data);
String subChannel = input.readUTF();
if (unknownChannels.contains(subChannel)) {
return;
}
SimpleClans.debug("Message received, sub-channel: " + subChannel);
try {
Class<?> clazz = Class.forName("net.sacredlabyrinth.phaed.simpleclans.proxy.listeners." + subChannel);
MessageListener listener = (MessageListener) clazz.getConstructor(BungeeManager.class).newInstance(this);
listener.accept(input);
SimpleClans.debug("Message processed");
} catch (ClassNotFoundException e) {
SimpleClans.debug(String.format("Unknown channel: %s", subChannel));
unknownChannels.add(subChannel);
} catch (ReflectiveOperationException ex) {
plugin.getLogger().log(Level.SEVERE, String.format("Error processing channel %s", subChannel), ex);
}
}
@Override
public boolean isOnline(String playerName) {
if (Bukkit.getOnlinePlayers().stream().anyMatch(player -> player.getName().equals(playerName))) {
return true;
}
return onlinePlayers.contains(playerName);
}
public void setOnlinePlayers(@NotNull List<String> onlinePlayers) {
this.onlinePlayers.clear();
this.onlinePlayers.addAll(onlinePlayers);
}
@Override
public String getServerName() {
return serverName;
}
public void setServerName(@NotNull String name) {
this.serverName = name;
}
@Override
public void sendMessage(SCMessage message) {
forwardPluginMessage(CHAT_CHANNEL, gson.toJson(message), false);
}
@SuppressWarnings("UnstableApiUsage")
@Override
public void sendMessage(@NotNull String target, @NotNull String message) {
if (isChannelRegistered()) {
ByteArrayDataOutput output = ByteStreams.newDataOutput();
output.writeUTF("Message");
output.writeUTF(target);
output.writeUTF(message);
sendOnBungeeChannel(output);
} else {
if ("ALL".equals(target)) {
Bukkit.getOnlinePlayers().forEach(p -> p.sendMessage(message));
} else {
Optional.ofNullable(Bukkit.getPlayer(target)).ifPresent(p -> p.sendMessage(message));
}
}
}
@Override
public void sendDelete(Clan clan) {
forwardPluginMessage(DELETE_CLAN_CHANNEL, clan.getTag());
}
@Override
public void sendDelete(ClanPlayer cp) {
forwardPluginMessage(DELETE_CLANPLAYER_CHANNEL, cp.getUniqueId().toString());
}
@Override
public void sendUpdate(Clan clan) {
forwardPluginMessage(UPDATE_CLAN_CHANNEL, gson.toJson(clan));
}
@Override
public void sendUpdate(ClanPlayer cp) {
forwardPluginMessage(UPDATE_CLANPLAYER_CHANNEL, gson.toJson(cp));
}
public SimpleClans getPlugin() {
return plugin;
}
public Gson getGson() {
return gson;
}
@SuppressWarnings("UnstableApiUsage")
private void requestPlayerList() {
if (!isChannelRegistered()) {
return;
}
ByteArrayDataOutput output = ByteStreams.newDataOutput();
output.writeUTF("PlayerList");
output.writeUTF("ALL");
sendOnBungeeChannel(output);
}
private void requestServerName() {
Listener listener = new Listener() {
@SuppressWarnings("UnstableApiUsage")
@EventHandler
void on(PlayerJoinEvent event) {
ByteArrayDataOutput output = ByteStreams.newDataOutput();
output.writeUTF("GetServer");
Bukkit.getScheduler().runTask(plugin, () -> {
event.getPlayer().sendPluginMessage(plugin, "BungeeCord", output.toByteArray());
PlayerJoinEvent.getHandlerList().unregister(this); //only needed once
});
}
};
Bukkit.getPluginManager().registerEvents(listener, plugin);
}
private void forwardPluginMessage(final String subChannel, final String message) {
forwardPluginMessage(subChannel, message, true);
}
@SuppressWarnings("UnstableApiUsage")
private void forwardPluginMessage(final String subChannel, final String message, final boolean all) {
SimpleClans.debug(String.format("Forwarding message, channel %s, message %s, all %s", subChannel, message, all));
if (!isChannelRegistered()) {
SimpleClans.debug("Not registered");
return;
}
String target = all ? "ALL" : "ONLINE";
ByteArrayDataOutput output = ByteStreams.newDataOutput();
output.writeUTF("Forward");
output.writeUTF(target);
output.writeUTF(subChannel);
output.writeUTF(message);
sendOnBungeeChannel(output);
}
private void sendOnBungeeChannel(ByteArrayDataOutput output) {
Bukkit.getOnlinePlayers().stream().findAny().ifPresent(player ->
player.sendPluginMessage(plugin, "BungeeCord", output.toByteArray()));
}
private boolean isChannelRegistered() {
return Bukkit.getMessenger().isOutgoingChannelRegistered(plugin, "BungeeCord");
}
}
@@ -0,0 +1,24 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
public interface ProxyManager {
String getServerName();
boolean isOnline(String playerName);
void sendMessage(SCMessage message);
void sendMessage(String target, String message);
void sendUpdate(Clan clan);
void sendUpdate(ClanPlayer cp);
void sendDelete(Clan clan);
void sendDelete(ClanPlayer cp);
}
@@ -0,0 +1,57 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.adapters;
import com.google.gson.TypeAdapter;
import com.google.gson.reflect.TypeToken;
import com.google.gson.stream.JsonReader;
import com.google.gson.stream.JsonToken;
import com.google.gson.stream.JsonWriter;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import java.io.IOException;
import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;
public class ClanPlayerListAdapter extends TypeAdapter<List<ClanPlayer>> {
private final SimpleClans plugin;
public ClanPlayerListAdapter(SimpleClans plugin) {
this.plugin = plugin;
}
@Override
public void write(JsonWriter out, List<ClanPlayer> value) throws IOException {
out.beginArray();
for (ClanPlayer clanPlayer : value) {
out.beginObject();
out.name("uuid");
out.value(clanPlayer.getUniqueId().toString());
out.endObject();
}
out.endArray();
}
@Override
public List<ClanPlayer> read(JsonReader in) throws IOException {
List<ClanPlayer> list = new ArrayList<>();
in.beginArray();
while (in.peek() == JsonToken.BEGIN_OBJECT) {
in.beginObject();
in.nextName();
UUID uuid = UUID.fromString(in.nextString());
ClanPlayer cp = plugin.getClanManager().getAnyClanPlayer(uuid);
in.endObject();
if (cp != null) {
list.add(cp);
}
}
in.endArray();
return list;
}
public static Type getType() {
return TypeToken.getParameterized(List.class, ClanPlayer.class).getType();
}
}
@@ -0,0 +1,52 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.adapters;
import com.google.gson.Gson;
import com.google.gson.JsonObject;
import com.google.gson.TypeAdapter;
import com.google.gson.TypeAdapterFactory;
import com.google.gson.reflect.TypeToken;
import com.google.gson.stream.JsonReader;
import com.google.gson.stream.JsonWriter;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import org.jetbrains.annotations.Nullable;
public class ClanPlayerTypeAdapterFactory implements TypeAdapterFactory {
private final SimpleClans plugin;
public ClanPlayerTypeAdapterFactory(SimpleClans plugin) {
this.plugin = plugin;
}
@SuppressWarnings("unchecked")
@Override
public <T> @Nullable TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
if (type.getType() != ClanPlayer.class) {
return null;
}
final TypeAdapter<ClanPlayer> delegate = (TypeAdapter<ClanPlayer>) gson.getDelegateAdapter(this, type);
return (TypeAdapter<T>) new TypeAdapter<ClanPlayer>() {
@Override
public void write(JsonWriter out, ClanPlayer value) {
JsonObject object = delegate.toJsonTree(value).getAsJsonObject();
object.addProperty("clan", value.getTag());
gson.toJson(object, out);
}
@Override
public ClanPlayer read(JsonReader in) {
JsonObject object = gson.fromJson(in, JsonObject.class);
String tag = object.get("clan").getAsString();
Clan clan = plugin.getClanManager().getClan(tag);
object.add("clan", null);
ClanPlayer cp = delegate.fromJsonTree(object);
cp.setClan(clan);
return cp;
}
};
}
}
@@ -0,0 +1,47 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.adapters;
import com.google.gson.Gson;
import com.google.gson.TypeAdapter;
import com.google.gson.TypeAdapterFactory;
import com.google.gson.reflect.TypeToken;
import com.google.gson.stream.JsonReader;
import com.google.gson.stream.JsonWriter;
import com.google.gson.stream.JsonToken;
import org.bukkit.configuration.serialization.ConfigurationSerializable;
import org.bukkit.configuration.serialization.ConfigurationSerialization;
import java.io.IOException;
import java.util.Map;
@SuppressWarnings({"unchecked", "rawtypes"})
public class ConfigurationSerializableAdapter implements TypeAdapterFactory {
@Override
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
if (!ConfigurationSerializable.class.isAssignableFrom(type.getRawType())) {
return null;
}
TypeAdapter<Map> adapter = gson.getAdapter(Map.class);
return (TypeAdapter<T>) new TypeAdapter<ConfigurationSerializable>() {
@Override
public void write(JsonWriter out, ConfigurationSerializable value) throws IOException {
if (value == null) {
out.nullValue();
} else {
adapter.write(out, value.serialize());
}
}
@Override
public ConfigurationSerializable read(JsonReader in) throws IOException {
if (in.peek() == JsonToken.NULL) { //could be replaced with map == null?
in.nextNull();
return null;
}
Map map = adapter.read(in);
return ConfigurationSerialization.deserializeObject(map,
(Class<? extends ConfigurationSerializable>) type.getRawType());
}
};
}
}
@@ -0,0 +1,52 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.adapters;
import com.google.gson.TypeAdapter;
import com.google.gson.stream.JsonReader;
import com.google.gson.stream.JsonWriter;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage.Source;
import org.jetbrains.annotations.Nullable;
import java.io.IOException;
import java.util.UUID;
public class SCMessageAdapter extends TypeAdapter<SCMessage> {
private final SimpleClans plugin;
public SCMessageAdapter(SimpleClans plugin) {
this.plugin = plugin;
}
@Override
public void write(JsonWriter out, SCMessage value) throws IOException {
out.beginObject();
out.name("channel");
out.value(value.getChannel().toString());
out.name("sender");
out.value(value.getSender().getUniqueId().toString());
out.name("content");
out.value(value.getContent());
out.endObject();
}
@Override
public @Nullable SCMessage read(JsonReader in) throws IOException {
in.beginObject();
in.nextName();
ClanPlayer.Channel channel = ClanPlayer.Channel.valueOf(in.nextString());
in.nextName();
UUID uuid = UUID.fromString(in.nextString());
ClanPlayer sender = plugin.getClanManager().getAnyClanPlayer(uuid);
in.nextName();
String content = in.nextString();
in.endObject();
if (sender == null) {
return null;
}
return new SCMessage(Source.PROXY, channel, sender, content);
}
}
@@ -0,0 +1,21 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import com.google.common.io.ByteArrayDataInput;
import net.sacredlabyrinth.phaed.simpleclans.chat.SCMessage;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
public class Chat extends MessageListener {
public Chat(BungeeManager bungee) {
super(bungee);
}
@Override
public void accept(ByteArrayDataInput data) {
SCMessage message = getGson().fromJson(data.readUTF(), SCMessage.class);
if (message.getSender().getClan() == null) {
return;
}
bungee.getPlugin().getChatManager().processChat(message);
}
}
@@ -0,0 +1,20 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import com.google.common.io.ByteArrayDataInput;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.debug;
public class DeleteClan extends MessageListener {
public DeleteClan(BungeeManager bungee) {
super(bungee);
}
@Override
public void accept(ByteArrayDataInput data) {
String tag = data.readUTF();
getClanManager().removeClan(tag);
debug(String.format("Deleted clan %s", tag));
}
}
@@ -0,0 +1,22 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import com.google.common.io.ByteArrayDataInput;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
import java.util.UUID;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.debug;
public class DeleteClanPlayer extends MessageListener {
public DeleteClanPlayer(BungeeManager bungee) {
super(bungee);
}
@Override
public void accept(ByteArrayDataInput data) {
UUID uuid = UUID.fromString(data.readUTF());
getClanManager().deleteClanPlayerFromMemory(uuid);
debug(String.format("Deleted cp %s", uuid));
}
}
@@ -0,0 +1,17 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import com.google.common.io.ByteArrayDataInput;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
public class GetServer extends MessageListener {
public GetServer(BungeeManager bungee) {
super(bungee);
}
@Override
public void accept(ByteArrayDataInput data) {
String name = data.readUTF();
bungee.setServerName(name);
}
}
@@ -0,0 +1,26 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import com.google.common.io.ByteArrayDataInput;
import com.google.gson.Gson;
import net.sacredlabyrinth.phaed.simpleclans.managers.ClanManager;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
public abstract class MessageListener {
protected final BungeeManager bungee;
public MessageListener(BungeeManager bungee) {
this.bungee = bungee;
}
public abstract void accept(ByteArrayDataInput data);
protected ClanManager getClanManager() {
return bungee.getPlugin().getClanManager();
}
protected Gson getGson() {
return bungee.getGson();
}
}
@@ -0,0 +1,23 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import com.google.common.io.ByteArrayDataInput;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
import java.util.Arrays;
import java.util.List;
public class PlayerList extends MessageListener {
public PlayerList(BungeeManager bungee) {
super(bungee);
}
@Override
public void accept(ByteArrayDataInput data) {
data.readUTF(); // target
List<String> players = Arrays.asList(data.readUTF().split(", "));
bungee.setOnlinePlayers(players);
SimpleClans.debug("Updated player list");
}
}
@@ -0,0 +1,40 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import com.google.common.io.ByteArrayDataInput;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
import net.sacredlabyrinth.phaed.simpleclans.utils.ObjectUtils;
import org.jetbrains.annotations.Nullable;
import java.util.logging.Level;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.debug;
public abstract class Update<T> extends MessageListener {
public Update(BungeeManager bungee) {
super(bungee);
}
protected abstract Class<T> getType();
protected abstract @Nullable T getCurrent(T t);
protected abstract void insert(T t);
@Override
public final void accept(ByteArrayDataInput data) {
T t = getGson().fromJson(data.readUTF(), getType());
T current = getCurrent(t);
if (current == null) {
insert(t);
debug(String.format("Inserted %s", t));
return;
}
try {
ObjectUtils.updateFields(t, current);
} catch (IllegalAccessException e) {
bungee.getPlugin().getLogger().log(Level.SEVERE, String.format("An error happened while updating %s", t), e);
}
debug(String.format("Updated %s", t));
}
}
@@ -0,0 +1,28 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import net.sacredlabyrinth.phaed.simpleclans.Clan;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
import org.jetbrains.annotations.Nullable;
public class UpdateClan extends Update<Clan> {
public UpdateClan(BungeeManager bungee) {
super(bungee);
}
@Override
protected Class<Clan> getType() {
return Clan.class;
}
@Override
protected @Nullable Clan getCurrent(Clan clan) {
return getClanManager().getClan(clan.getTag());
}
@Override
protected void insert(Clan clan) {
getClanManager().importClan(clan);
}
}
@@ -0,0 +1,28 @@
package net.sacredlabyrinth.phaed.simpleclans.proxy.listeners;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.proxy.BungeeManager;
import org.jetbrains.annotations.Nullable;
public class UpdateClanPlayer extends Update<ClanPlayer> {
public UpdateClanPlayer(BungeeManager bungee) {
super(bungee);
}
@Override
protected Class<ClanPlayer> getType() {
return ClanPlayer.class;
}
@Override
protected @Nullable ClanPlayer getCurrent(ClanPlayer clanPlayer) {
return getClanManager().getAnyClanPlayer(clanPlayer.getUniqueId());
}
@Override
protected void insert(ClanPlayer clanPlayer) {
getClanManager().importClanPlayer(clanPlayer);
}
}
@@ -1,7 +1,9 @@
package net.sacredlabyrinth.phaed.simpleclans.storage;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import org.bukkit.scheduler.BukkitRunnable;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField;
import org.bukkit.Bukkit;
import org.jetbrains.annotations.Nullable;
import java.sql.Connection;
import java.sql.ResultSet;
@@ -10,11 +12,12 @@ import java.util.logging.Level;
import java.util.logging.Logger;
/**
*
* @author phaed
*/
public interface DBCore
{
public interface DBCore {
SimpleClans plugin = SimpleClans.getInstance();
Logger log = plugin.getLogger();
/**
* @return connection
@@ -24,7 +27,9 @@ public interface DBCore
/**
* @return whether connection can be established
*/
Boolean checkConnection();
default boolean checkConnection() {
return getConnection() != null;
}
/**
* Close connection
@@ -33,69 +38,83 @@ public interface DBCore
/**
* Execute a select statement
* @param query
* @return
* @param query the query
* @return the result set or null if the query failed
*/
ResultSet select(String query);
/**
* Execute an insert statement
* @param query
*/
void insert(String query);
/**
* Execute an update statement
* @param query
*/
void update(String query);
/**
* Execute a delete statement
* @param query
*/
void delete(String query);
default @Nullable ResultSet select(String query) {
try {
return getConnection().createStatement().executeQuery(query);
} catch (SQLException ex) {
log.log(Level.SEVERE, String.format("Error executing query: %s", query), ex);
}
return null;
}
/**
* Execute a statement
* @param query
* @return
* @param query the query
* @return true if the statement was executed
*/
Boolean execute(String query);
default boolean execute(String query) {
try {
getConnection().createStatement().execute(query);
return true;
} catch (SQLException ex) {
log.log(Level.SEVERE, String.format("Error executing query: %s", query), ex);
return false;
}
}
/**
* Check whether a table exists
* @param table
* @return
* @param table the table
* @return true if the table exists
*/
Boolean existsTable(String table);
/**
* Check whether a colum exists
*
* @param tabell
* @param colum
* @return
*/
Boolean existsColumn(String tabell, String colum);
default boolean existsTable(String table) {
try {
ResultSet tables = getConnection().getMetaData().getTables(null, null, table, null);
return tables.next();
} catch (SQLException ex) {
log.log(Level.SEVERE, String.format("Error checking if table %s exists", table), ex);
return false;
}
}
default void executeAsync(String query, String sqlType) {
new BukkitRunnable() {
@Override
public void run() {
/**
* Check whether a column exists
*
* @param table the table
* @param column the column
* @return true if the column exists
*/
default boolean existsColumn(String table, String column) {
try {
ResultSet col = getConnection().getMetaData().getColumns(null, null, table, column);
return col.next();
} catch (Exception ex) {
log.log(Level.SEVERE, String.format("Error checking if column %s exists in table %s", column, table), ex);
return false;
}
}
default void executeUpdate(String query) {
final Exception exception = new Exception(); // Stores a reference to the caller's stack trace for async tasks
Runnable executeUpdate = () -> {
if (getConnection() != null) {
try {
if (getConnection() != null) {
getConnection().createStatement().executeUpdate(query);
}
}
catch (SQLException ex) {
if (!ex.toString().contains("not return ResultSet")) {
Logger.getLogger("SimpleClans")
.log(Level.SEVERE, String.format("Error at SQL %s query: %s", sqlType, query), ex);
getConnection().createStatement().executeUpdate(query);
} catch (SQLException ex) {
log.log(Level.SEVERE, String.format("Error executing query: %s", query), ex);
if (!Bukkit.isPrimaryThread()) {
log.log(Level.SEVERE, "Caller's stack trace:", exception);
}
}
}
}.runTaskAsynchronously(SimpleClans.getInstance());
};
if (plugin.getSettingsManager().is(ConfigField.PERFORMANCE_USE_THREADS)) {
Bukkit.getScheduler().runTaskAsynchronously(plugin, executeUpdate);
} else {
executeUpdate.run();
}
}
}
@@ -4,12 +4,9 @@ import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.logging.Logger;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.PERFORMANCE_USE_THREADS;
/**
* @author cc_madelg
*/
@@ -24,10 +21,10 @@ public class MySQLCore implements DBCore {
private final int port;
/**
* @param host
* @param database
* @param username
* @param password
* @param host The host
* @param database The database
* @param username The username
* @param password The password
*/
public MySQLCore(String host, String database, int port, String username, String password) {
this.database = database;
@@ -42,7 +39,7 @@ public class MySQLCore implements DBCore {
private void initialize() {
try {
Class.forName("com.mysql.jdbc.Driver");
connection = DriverManager.getConnection("jdbc:mysql://" + host + ":" + port + "/" + database + "?useUnicode=true&characterEncoding=utf-8&autoReconnect=true", username, password);
connection = DriverManager.getConnection("jdbc:mysql://" + host + ":" + port + "/" + database + "?useUnicode=true&characterEncoding=utf-8&autoReconnect=true&useSSL=false", username, password);
} catch (ClassNotFoundException e) {
log.severe("ClassNotFoundException! " + e.getMessage());
} catch (SQLException e) {
@@ -50,9 +47,6 @@ public class MySQLCore implements DBCore {
}
}
/**
* @return connection
*/
@Override
public Connection getConnection() {
try {
@@ -65,17 +59,6 @@ public class MySQLCore implements DBCore {
return connection;
}
/**
* @return whether connection can be established
*/
@Override
public Boolean checkConnection() {
return getConnection() != null;
}
/**
* Close connection
*/
@Override
public void close() {
try {
@@ -87,134 +70,4 @@ public class MySQLCore implements DBCore {
}
}
/**
* Execute a select statement
*
* @param query
* @return
*/
@Override
public ResultSet select(String query) {
try {
return getConnection().createStatement().executeQuery(query);
} catch (SQLException ex) {
log.severe("Error at SQL Query: " + ex.getMessage());
log.severe("Query: " + query);
}
return null;
}
/**
* Execute an insert statement
*
* @param query
*/
@Override
public void insert(String query) {
if (SimpleClans.getInstance().getSettingsManager().is(PERFORMANCE_USE_THREADS)) {
executeAsync(query, "INSERT");
} else {
try {
getConnection().createStatement().executeUpdate(query);
} catch (SQLException ex) {
if (!ex.toString().contains("not return ResultSet")) {
log.severe("Error at SQL INSERT Query: " + ex);
log.severe("Query: " + query);
}
}
}
}
/**
* Execute an update statement
*
* @param query
*/
@Override
public void update(String query) {
if (SimpleClans.getInstance().getSettingsManager().is(PERFORMANCE_USE_THREADS)) {
executeAsync(query, "UPDATE");
} else {
try {
getConnection().createStatement().executeUpdate(query);
} catch (SQLException ex) {
if (!ex.toString().contains("not return ResultSet")) {
log.severe("Error at SQL UPDATE Query: " + ex);
log.severe("Query: " + query);
}
}
}
}
/**
* Execute a delete statement
*
* @param query
*/
@Override
public void delete(String query) {
if (SimpleClans.getInstance().getSettingsManager().is(PERFORMANCE_USE_THREADS)) {
executeAsync(query, "DELETE");
} else {
try {
getConnection().createStatement().executeUpdate(query);
} catch (SQLException ex) {
if (!ex.toString().contains("not return ResultSet")) {
log.severe("Error at SQL DELETE Query: " + ex);
log.severe("Query: " + query);
}
}
}
}
/**
* Execute a statement
*
* @param query
* @return
*/
@Override
public Boolean execute(String query) {
try {
getConnection().createStatement().execute(query);
return true;
} catch (SQLException ex) {
log.severe(ex.getMessage());
log.severe("Query: " + query);
return false;
}
}
/**
* Check whether a table exists
*
* @param table
* @return
*/
public Boolean existsTable(String table) {
try {
ResultSet tables = getConnection().getMetaData().getTables(null, null, table, null);
return tables.next();
} catch (SQLException e) {
log.severe("Failed to check if table " + table + " exists: " + e.getMessage());
return false;
}
}
/**
* Check whether a column exists
*
* @param table
* @param column
* @return
*/
public Boolean existsColumn(String table, String column) {
try {
ResultSet col = getConnection().getMetaData().getColumns(null, null, table, column);
return col.next();
} catch (Exception e) {
log.severe("Failed to check if column " + column + " exists in table " + table + " : " + e.getMessage());
return false;
}
}
}
@@ -5,24 +5,21 @@ import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import java.io.File;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.logging.Logger;
import static net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager.ConfigField.PERFORMANCE_USE_THREADS;
/**
* @author cc_madelg
*/
public class SQLiteCore implements DBCore {
private Logger log;
private final Logger log;
private Connection connection;
private String dbLocation;
private String dbName;
private final String dbLocation;
private final String dbName;
private File file;
/**
* @param dbLocation
* @param dbLocation the dbLocation to set
*/
public SQLiteCore(String dbLocation) {
this.dbName = "SimpleClans";
@@ -33,20 +30,14 @@ public class SQLiteCore implements DBCore {
private void initialize() {
if (file == null) {
File dbFolder = new File(dbLocation);
if (dbName.contains("/") || dbName.contains("\\") || dbName.endsWith(".db")) {
log.severe("The database name can not contain: /, \\, or .db");
if (!dbFolder.exists() && !dbFolder.mkdir()) {
log.severe("Failed to create database folder!");
return;
}
if (!dbFolder.exists()) {
dbFolder.mkdir();
}
file = new File(dbFolder.getAbsolutePath() + File.separator + dbName + ".db");
}
try {
@@ -61,9 +52,6 @@ public class SQLiteCore implements DBCore {
}
}
/**
* @return connection
*/
@Override
public Connection getConnection() {
if (connection == null) {
@@ -73,17 +61,6 @@ public class SQLiteCore implements DBCore {
return connection;
}
/**
* @return whether connection can be established
*/
@Override
public Boolean checkConnection() {
return getConnection() != null;
}
/**
* Close connection
*/
@Override
public void close() {
try {
@@ -95,134 +72,4 @@ public class SQLiteCore implements DBCore {
}
}
/**
* Execute a select statement
*
* @param query
* @return
*/
@Override
public ResultSet select(String query) {
try {
return getConnection().createStatement().executeQuery(query);
} catch (SQLException ex) {
log.severe("Error at SQL Query: " + ex.getMessage());
log.severe("Query: " + query);
}
return null;
}
/**
* Execute an insert statement
*
* @param query
*/
@Override
public void insert(String query) {
if (SimpleClans.getInstance().getSettingsManager().is(PERFORMANCE_USE_THREADS)) {
executeAsync(query, "INSERT");
} else {
try {
getConnection().createStatement().executeQuery(query);
} catch (SQLException ex) {
if (!ex.toString().contains("not return ResultSet")) {
log.severe("Error at SQL INSERT Query: " + ex);
log.severe("Query: " + query);
}
}
}
}
/**
* Execute an update statement
*
* @param query
*/
@Override
public void update(String query) {
if (SimpleClans.getInstance().getSettingsManager().is(PERFORMANCE_USE_THREADS)) {
executeAsync(query, "UPDATE");
} else {
try {
getConnection().createStatement().executeQuery(query);
} catch (SQLException ex) {
if (!ex.toString().contains("not return ResultSet")) {
log.severe("Error at SQL UPDATE Query: " + ex);
log.severe("Query: " + query);
}
}
}
}
/**
* Execute a delete statement
*
* @param query
*/
@Override
public void delete(String query) {
if (SimpleClans.getInstance().getSettingsManager().is(PERFORMANCE_USE_THREADS)) {
executeAsync(query, "DELETE");
} else {
try {
getConnection().createStatement().executeQuery(query);
} catch (SQLException ex) {
if (!ex.toString().contains("not return ResultSet")) {
log.severe("Error at SQL DELETE Query: " + ex);
log.severe("Query: " + query);
}
}
}
}
/**
* Execute a statement
*
* @param query
* @return
*/
@Override
public Boolean execute(String query) {
try {
getConnection().createStatement().execute(query);
return true;
} catch (SQLException ex) {
log.severe(ex.getMessage());
log.severe("Query: " + query);
return false;
}
}
/**
* Check whether a table exists
*
* @param table
* @return
*/
public Boolean existsTable(String table) {
try {
ResultSet tables = getConnection().getMetaData().getTables(null, null, table, null);
return tables.next();
} catch (SQLException e) {
log.severe("Failed to check if table " + table + " exists: " + e.getMessage());
return false;
}
}
/**
* Check whether a column exists
*
* @param table
* @param column
* @return
*/
public Boolean existsColumn(String table, String column) {
try {
ResultSet col = getConnection().getMetaData().getColumns(null, null, table, column);
return col.next();
} catch (Exception e) {
log.severe("Failed to check if column " + column + " exists in table " + table + " : " + e.getMessage());
return false;
}
}
}
@@ -1,8 +1,11 @@
package net.sacredlabyrinth.phaed.simpleclans.tasks;
import net.sacredlabyrinth.phaed.simpleclans.*;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import net.sacredlabyrinth.phaed.simpleclans.managers.PermissionsManager;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
import org.bukkit.Bukkit;
import org.bukkit.OfflinePlayer;
import org.bukkit.scheduler.BukkitRunnable;
import static net.sacredlabyrinth.phaed.simpleclans.SimpleClans.lang;
@@ -40,22 +43,24 @@ public class CollectFeeTask extends BukkitRunnable {
*/
@Override
public void run() {
PermissionsManager pm = plugin.getPermissionsManager();
for (Clan clan : plugin.getClanManager().getClans()) {
final double memberFee = clan.getMemberFee();
if (clan.isMemberFeeEnabled() && memberFee > 0) {
for (ClanPlayer cp : clan.getFeePayers()) {
boolean success = plugin.getPermissionsManager()
.playerChargeMoney(Bukkit.getOfflinePlayer(cp.getUniqueId()), memberFee);
if (success) {
ChatBlock.sendMessage(cp.toPlayer(), AQUA + lang("fee.collected", cp, memberFee));
clan.deposit(cp.toPlayer(), Cause.MEMBER_FEE, memberFee);
plugin.getStorageManager().updateClan(clan);
} else {
clan.removePlayerFromClan(cp.getUniqueId());
clan.addBb(AQUA + lang("bb.fee.player.kicked", cp.getName()));
}
if (!clan.isMemberFeeEnabled() || memberFee <= 0) {
continue;
}
for (ClanPlayer cp : clan.getFeePayers()) {
OfflinePlayer player = Bukkit.getOfflinePlayer(cp.getUniqueId());
boolean success = pm.playerChargeMoney(player, memberFee);
if (success) {
ChatBlock.sendMessage(cp, AQUA + lang("fee.collected", cp, memberFee));
clan.deposit(new BankOperator(cp, pm.playerGetMoney(player)), Cause.MEMBER_FEE, memberFee);
plugin.getStorageManager().updateClan(clan);
} else {
clan.removePlayerFromClan(cp.getUniqueId());
clan.addBb(AQUA + lang("bb.fee.player.kicked", cp.getName()));
}
}
}
@@ -4,6 +4,7 @@ import net.sacredlabyrinth.phaed.simpleclans.EconomyResponse;
import net.sacredlabyrinth.phaed.simpleclans.Helper;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import net.sacredlabyrinth.phaed.simpleclans.events.ClanBalanceUpdateEvent;
import net.sacredlabyrinth.phaed.simpleclans.loggers.BankOperator;
import net.sacredlabyrinth.phaed.simpleclans.managers.SettingsManager;
import org.bukkit.scheduler.BukkitRunnable;
@@ -54,7 +55,7 @@ public class CollectUpkeepTask extends BukkitRunnable {
upkeep = upkeep * clan.getSize();
}
EconomyResponse response = clan.withdraw(null, ClanBalanceUpdateEvent.Cause.UPKEEP, upkeep);
EconomyResponse response = clan.withdraw(BankOperator.INTERNAL, ClanBalanceUpdateEvent.Cause.UPKEEP, upkeep);
if (response == EconomyResponse.NOT_ENOUGH_BALANCE) {
clan.disband(null, true, false);
}
@@ -1,9 +1,9 @@
package net.sacredlabyrinth.phaed.simpleclans.tasks;
import com.cryptomorin.xseries.XMaterial;
import net.sacredlabyrinth.phaed.simpleclans.ClanPlayer;
import net.sacredlabyrinth.phaed.simpleclans.SimpleClans;
import org.bukkit.Bukkit;
import org.bukkit.Material;
import org.bukkit.inventory.Inventory;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.SkullMeta;
@@ -12,6 +12,7 @@ import org.jetbrains.annotations.NotNull;
import java.util.Comparator;
import java.util.List;
import java.util.Objects;
public class PlayerHeadCacheTask extends BukkitRunnable {
@@ -42,8 +43,8 @@ public class PlayerHeadCacheTask extends BukkitRunnable {
plugin.getLogger().info("Player heads caching task cancelled!");
return;
}
ItemStack itemStack = new ItemStack(Material.PLAYER_HEAD);
SkullMeta itemMeta = (SkullMeta) itemStack.getItemMeta();
ItemStack itemStack = XMaterial.PLAYER_HEAD.parseItem();
SkullMeta itemMeta = (SkullMeta) Objects.requireNonNull(itemStack).getItemMeta();
if (itemMeta != null) {
itemMeta.setOwningPlayer(Bukkit.getOfflinePlayer(player.getUniqueId()));
}
@@ -81,7 +81,7 @@ public class AddPermissionFrame extends SCFrame {
@Override
public int getSize() {
return 4 * 9;
return 3 * 9;
}
}
@@ -138,7 +138,6 @@ public class ClanDetailsFrame extends SCFrame {
Collections.singletonList(lang("gui.clandetails.disband.lore", getViewer())), XMaterial.BARRIER,
50);
disband.setListener(ClickType.DROP, () -> InventoryController.runSubcommand(getViewer(), "disband", false));
disband.setConfirmationRequired(ClickType.DROP);
disband.setPermission(ClickType.DROP, "simpleclans.leader.disband");
add(disband);
}
@@ -37,7 +37,11 @@ public class LanguageSelectorFrame extends SCFrame {
@Override
public @NotNull String getTitle() {
return lang("gui.languageselector.title", getViewer(), clanPlayer.getLocale().toLanguageTag());
Locale locale = clanPlayer.getLocale();
if (locale == null) {
locale = plugin.getSettingsManager().getLanguage();
}
return lang("gui.languageselector.title", getViewer(), locale.toLanguageTag());
}
@Override
@@ -110,7 +110,7 @@ public class MainFrame extends SCFrame {
@Override
public int getSize() {
return 9;
return 3 * 9;
}
}
@@ -26,7 +26,6 @@ public class PermissionsFrame extends SCFrame {
@Override
public void createComponents() {
for (int slot = 0; slot < 9; slot++) {
if (slot == 2 || slot == 4 || slot == 6 || slot == 7)
continue;
@@ -82,7 +81,7 @@ public class PermissionsFrame extends SCFrame {
@Override
public int getSize() {
return 4 * 9;
return 3 * 9;
}
}
@@ -120,7 +120,7 @@ public class PlayerDetailsFrame extends SCFrame {
public int getSize() {
int size = 3;
if (isSameClan()) {
size = 5;
size = 6;
}
return size * 9;
}
@@ -75,7 +75,7 @@ public class WarningFrame extends SCFrame {
@Override
public int getSize() {
return 4 * 9;
return 6 * 9;
}
}
@@ -126,7 +126,7 @@ public class ClanDetailsFrame extends SCFrame {
@Override
public int getSize() {
return 5 * 9;
return 6 * 9;
}
}
@@ -114,7 +114,7 @@ public class PlayerDetailsFrame extends SCFrame {
@Override
public int getSize() {
return 5 * 9;
return 6 * 9;
}
}
@@ -27,7 +27,7 @@ public class StaffFrame extends SCFrame {
@Override
public int getSize() {
return 2 * 9;
return 3 * 9;
}
@Override
@@ -0,0 +1,53 @@
package net.sacredlabyrinth.phaed.simpleclans.utils;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.util.Collection;
import java.util.Map;
public final class ObjectUtils {
private ObjectUtils() {
}
public static void updateFields(Object origin, Object destination) throws IllegalAccessException {
if (origin.getClass() != destination.getClass()) {
throw new IllegalArgumentException("origin and destination must be of the same type");
}
Field[] fields = origin.getClass().getDeclaredFields();
for (Field field : fields) {
field.setAccessible(true);
if (Modifier.isFinal(field.getModifiers())) {
copyValues(field, field.get(origin), field.get(destination));
continue;
}
field.set(destination, field.get(origin));
}
}
private static boolean isPrimitive(Field field) {
Class<?> type = field.getType();
return type.isPrimitive() || Number.class.isAssignableFrom(type) || type == String.class;
}
@SuppressWarnings({"rawtypes", "unchecked"})
private static void copyValues(Field field, Object originValue, Object destValue) {
if (isPrimitive(field)) {
return;
}
if (originValue instanceof Collection) {
Collection<?> destColl = (Collection<?>) destValue;
destColl.clear();
destColl.addAll((Collection) originValue);
return;
}
if (originValue instanceof Map) {
Map<?, ?> destMap = (Map<?, ?>) destValue;
destMap.clear();
destMap.putAll((Map) originValue);
return;
}
throw new UnsupportedOperationException(String.format("unknown field type: %s", originValue.getClass()));
}
}
@@ -57,8 +57,8 @@ public class TagValidator {
lang("your.tag.cannot.contain.the.following.colors", player,
plugin.getSettingsManager().getDisallowedColorString());
}
checkAlphabet();
}
checkAlphabet();
return error;
}
@@ -68,7 +68,7 @@ public class TagValidator {
String alphabetError = RED + lang("your.clan.tag.can.only.contain.letters.numbers.and.color.codes", player);
if (plugin.getSettingsManager().is(ACCEPT_OTHER_ALPHABETS_LETTERS)) {
for (char c : cleanTag.toCharArray()) {
if (!Character.isLetterOrDigit(c)) {
if (!Character.isLetterOrDigit(c) || Character.isSpaceChar(c)) {
error = alphabetError;
return;
}
Loaded 100 of 137 files, more files were not shown because too many files have changed in this diff. Show more