Release Vanish-OG
This commit is contained in:
1 parent
84627afee6
commit
5b11813ff7
104 files changed
+5332
-2061
No files matched your search
+6
-1
@@ -1,6 +1,12 @@
|
||||
*.class
|
||||
target/
|
||||
out/
|
||||
build/
|
||||
.gradle/
|
||||
bin/
|
||||
.classpath
|
||||
.project
|
||||
.checkstyle
|
||||
|
||||
# Mobile Tools for Java (J2ME)
|
||||
.mtj.tmp/
|
||||
@@ -10,7 +16,6 @@ out/
|
||||
*.eml
|
||||
*.iml
|
||||
|
||||
|
||||
# Eclipse files
|
||||
.settings
|
||||
|
||||
|
||||
@@ -1,34 +0,0 @@
|
||||
image: maven:3-jdk-9-slim
|
||||
|
||||
cache:
|
||||
paths:
|
||||
- .m2/repository
|
||||
|
||||
variables:
|
||||
MAVEN_OPTS: "-Dmaven.repo.local=.m2/repository -Dorg.slf4j.simpleLogger.log.org.apache.maven.cli.transfer.Slf4jMavenTransferListener=WARN -Dorg.slf4j.simpleLogger.showDateTime=true -Djava.awt.headless=true"
|
||||
MAVEN_CLI_OPTS: "--batch-mode --errors --fail-at-end --show-version -DinstallAtEnd=true -DdeployAtEnd=true"
|
||||
|
||||
stages:
|
||||
- build
|
||||
- deploy
|
||||
|
||||
build:
|
||||
stage: build
|
||||
script:
|
||||
- apt update
|
||||
- apt install wget -y
|
||||
- wget https://gitlab.com/cubekrowd/mavenrepo/raw/master/build2.sh
|
||||
- bash build2.sh
|
||||
artifacts:
|
||||
paths:
|
||||
- "*.jar"
|
||||
|
||||
deploy:
|
||||
stage: deploy
|
||||
script:
|
||||
- apt update
|
||||
- apt install wget -y
|
||||
- wget https://gitlab.com/cubekrowd/mavenrepo/raw/master/deploy1.sh
|
||||
- bash deploy1.sh
|
||||
only:
|
||||
- master
|
||||
@@ -0,0 +1,3 @@
|
||||
[submodule "libs/Utilities-OG"]
|
||||
path = libs/Utilities-OG
|
||||
url = https://github.com/true-og/Utilities-OG
|
||||
@@ -1,27 +1,171 @@
|
||||
# SuperVanish
|
||||
Website: https://www.spigotmc.org/resources/supervanish-be-invisible.1331/
|
||||
# Vanish-OG
|
||||
|
||||
Bukkit-Plugin for Spigot/CraftBukkit (modded Minecraft server)
|
||||
A fork of [SuperVanish](https://www.spigotmc.org/resources/supervanish-be-invisible.1331/) for [TrueOG Network](https://trueog.net). Lets staff become completely invisible so they can quietly observe and moderate.
|
||||
|
||||
Allows server admins to be completely invisible and undetectable for other players, which helps them with their administrative work.
|
||||
Built for **Purpur 1.19.4**. Clients from **Minecraft 1.8 through 1.21.11** can connect through ViaSuite (ViaVersion / ViaBackwards / ViaRewind) and vanish works correctly across the board.
|
||||
|
||||
Please note that I currently do not have much time to dedicate to this plugin and as such can not do extensive testing of pull requests. I appreciate pull requests, but please keep them as small and simple as possible. Please report issues on SpigotMC via PM!
|
||||
### What's different from SuperVanish?
|
||||
|
||||
## Maven Repository
|
||||
- **Tab list hiding works on 1.19+** Upstream switched it off after a Mojang change broke it. Vanish-OG handles the new format so vanished staff stay hidden from the tab list.
|
||||
- **Spectator indication works on 1.19.4 again.** `MarkVanishedPlayersAsSpectators` now uses the native 1.19.4 player info update packet, so staff who can see vanished players still get the dark-gray/head-only tab list cue across Via-served 1.8-1.21.11 clients.
|
||||
- **Silent chest opening works on 1.19+ again.** Same fix — peeking into containers looks completely normal to other players.
|
||||
- **All connected clients see the same thing.** Whether someone joins from 1.8 or the latest 1.21.11 release through ViaSuite, vanish behaves identically.
|
||||
- **[Chat-OG](https://github.com/true-og/Chat-OG) owns announcement visibility.** Vanish-OG no longer rewrites join/quit, death, or advancement messages and no longer emits fake join/quit broadcasts on vanish toggles. Chat-OG is responsible for hiding vanished-player activity from Discord-facing announcements.
|
||||
- **OpenInv support.** If installed, Vanish-OG hands off chest viewing to OpenInv so staff never enter spectator mode and can't get stuck there after a crash.
|
||||
- **MiniPlaceholders support** (via Utilities-OG) for use in chat, tab, and hologram plugins.
|
||||
- **Safer chest peeking.** Staff no longer occasionally fall through the floor when finishing a peek. Pair with [WGamemode](https://github.com/true-og/WGamemode) to auto-restore gamemodes after crashes if OpenInv is not installed.
|
||||
- **Removed old clutter.** Deprecated functions are removed and the code is updated for java 17 conventions.
|
||||
|
||||
### Chat-OG handles some events that used to be handled by SuperVanish
|
||||
|
||||
If your stack includes [Chat-OG](https://github.com/true-og/Chat-OG), think of the split like this:
|
||||
|
||||
- Vanish-OG manages vanish state, player/entity visibility, tab list hiding, spectator indication, and silent chest behavior.
|
||||
- Chat-OG manages whether vanished-player join/quit, kick, advancement, death, and Discord bridge announcements are surfaced.
|
||||
|
||||
This avoids two plugins trying to suppress or fake the same announcement events.
|
||||
|
||||
### API
|
||||
|
||||
Vanish-OG ships the same Bukkit-facing API package as SuperVanish: `de.myzelyam.api.vanish`.
|
||||
|
||||
### Main entry point
|
||||
|
||||
Use [`VanishAPI`](/home/notalexnoyle/eclipse-workspace/Vanish-OG/src/main/java/de/myzelyam/api/vanish/VanishAPI.java) for all direct integrations.
|
||||
|
||||
```java
|
||||
import de.myzelyam.api.vanish.VanishAPI;
|
||||
import net.trueog.utilitiesog.UtilitiesOG;
|
||||
```
|
||||
<repositories>
|
||||
<repository>
|
||||
<id>jitpack.io</id>
|
||||
<url>https://jitpack.io</url>
|
||||
</repository>
|
||||
</repositories>
|
||||
|
||||
<dependencies>
|
||||
<!-- SuperVanish -->
|
||||
<dependency>
|
||||
<groupId>com.github.LeonMangler</groupId>
|
||||
<artifactId>SuperVanish</artifactId>
|
||||
<version>6.2.18-3</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
### Commands
|
||||
|
||||
Main command: `/vanish` (also `/v`, `/sv`, `/supervanish`).
|
||||
|
||||
### State queries
|
||||
|
||||
- `VanishAPI.getInvisiblePlayers()`
|
||||
Returns the UUIDs of all online vanished players. Run this on the main server thread.
|
||||
- `VanishAPI.getAllInvisiblePlayers()`
|
||||
Returns the UUIDs of all vanished players, including offline players stored in `data.yml`. Run this on the main server thread.
|
||||
- `VanishAPI.isPlayerVanished(Player player)`
|
||||
Preferred asynchronous check for an online player. Safe to call from either thread. The returned `CompletableFuture<Boolean>` completes off the main thread.
|
||||
- `VanishAPI.isUUIDVanished(UUID uuid)`
|
||||
Preferred asynchronous check for any player UUID. Safe to call from either thread. The returned `CompletableFuture<Boolean>` completes off the main thread.
|
||||
|
||||
If you touch Bukkit APIs in an async completion callback, switch back to the server thread first.
|
||||
|
||||
Java:
|
||||
|
||||
```java
|
||||
VanishAPI.isUUIDVanished(player.getUniqueId()).thenAccept(vanished ->
|
||||
Bukkit.getScheduler().runTask(plugin, () -> {
|
||||
if (vanished) {
|
||||
UtilitiesOG.trueogMessage(player, "You are vanished.");
|
||||
}
|
||||
})
|
||||
);
|
||||
```
|
||||
|
||||
Kotlin:
|
||||
|
||||
```kotlin
|
||||
VanishAPI.isUUIDVanished(player.uniqueId).thenAccept { vanished ->
|
||||
Bukkit.getScheduler().runTask(plugin) {
|
||||
if (vanished) {
|
||||
UtilitiesOG.trueogMessage(player, "You are vanished.")
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Visibility control
|
||||
|
||||
- `VanishAPI.hidePlayer(Player player)`
|
||||
Vanishes the player through the normal SuperVanish pipeline and fires the related events. Main thread only.
|
||||
- `VanishAPI.showPlayer(Player player)`
|
||||
Reveals the player through the normal SuperVanish pipeline and fires the related events. Main thread only.
|
||||
- `VanishAPI.canSee(Player viewer, Player viewed)`
|
||||
Returns whether `viewer` should currently be able to see `viewed`. Main thread only.
|
||||
|
||||
Java:
|
||||
|
||||
```java
|
||||
if (!VanishAPI.canSee(viewer, target)) {
|
||||
UtilitiesOG.trueogMessage(viewer, "<red>That player is hidden from you.");
|
||||
}
|
||||
|
||||
VanishAPI.hidePlayer(target);
|
||||
VanishAPI.showPlayer(target);
|
||||
```
|
||||
|
||||
Kotlin:
|
||||
|
||||
```kotlin
|
||||
if (!VanishAPI.canSee(viewer, target)) {
|
||||
UtilitiesOG.trueogMessage(viewer, "<red>That player is hidden from you.")
|
||||
}
|
||||
|
||||
VanishAPI.hidePlayer(target)
|
||||
VanishAPI.showPlayer(target)
|
||||
```
|
||||
|
||||
### Configuration access
|
||||
|
||||
- `VanishAPI.getConfiguration()`
|
||||
Returns `config.yml`. Main thread only; treat the returned `FileConfiguration` as Bukkit-owned mutable state.
|
||||
- `VanishAPI.getMessages()`
|
||||
Returns `messages.yml`. Main thread only; treat the returned `FileConfiguration` as Bukkit-owned mutable state.
|
||||
- `VanishAPI.getPlayerData()`
|
||||
Returns the persistent player storage file (`data.yml` / player data config). Main thread only.
|
||||
- `VanishAPI.reloadConfig()`
|
||||
Reloads the plugin. Main thread only.
|
||||
- `VanishAPI.getPlugin()`
|
||||
Returns the active `SuperVanish` plugin instance. Fetching the reference is cheap, but any interaction with the plugin or Bukkit APIs should stay on the main thread.
|
||||
|
||||
### Events
|
||||
|
||||
The API exposes the following Bukkit events in `de.myzelyam.api.vanish`:
|
||||
|
||||
All of these are normal Bukkit events and should be handled on the main server thread. Do not assume they fire asynchronously.
|
||||
|
||||
- [`PlayerHideEvent`](/home/notalexnoyle/eclipse-workspace/Vanish-OG/src/main/java/de/myzelyam/api/vanish/PlayerHideEvent.java)
|
||||
Fired before a player is hidden. Cancellable. Includes `isSilent()` / `setSilent(boolean)`.
|
||||
- [`PostPlayerHideEvent`](/home/notalexnoyle/eclipse-workspace/Vanish-OG/src/main/java/de/myzelyam/api/vanish/PostPlayerHideEvent.java)
|
||||
Fired after a player has been hidden. Not cancellable. Includes `isSilent()`.
|
||||
- [`PlayerShowEvent`](/home/notalexnoyle/eclipse-workspace/Vanish-OG/src/main/java/de/myzelyam/api/vanish/PlayerShowEvent.java)
|
||||
Fired before a player is shown. Cancellable. Includes `isSilent()` / `setSilent(boolean)`.
|
||||
- [`PostPlayerShowEvent`](/home/notalexnoyle/eclipse-workspace/Vanish-OG/src/main/java/de/myzelyam/api/vanish/PostPlayerShowEvent.java)
|
||||
Fired after a player has been shown. Not cancellable. Includes `isSilent()`.
|
||||
- [`PlayerVanishStateChangeEvent`](/home/notalexnoyle/eclipse-workspace/Vanish-OG/src/main/java/de/myzelyam/api/vanish/PlayerVanishStateChangeEvent.java)
|
||||
Fired when persisted vanish state changes for a UUID. Cancellable. Exposes `isVanishing()`, `getUUID()`, `getName()`, and `getCause()`.
|
||||
|
||||
### Example listener
|
||||
|
||||
Java:
|
||||
|
||||
```java
|
||||
@EventHandler
|
||||
public void onPlayerHide(PlayerHideEvent event) {
|
||||
if (!event.getPlayer().hasPermission("myplugin.allowvanish")) {
|
||||
UtilitiesOG.trueogMessage(event.getPlayer(), "<red>You are not allowed to vanish.");
|
||||
event.setCancelled(true);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
Kotlin:
|
||||
|
||||
```kotlin
|
||||
@EventHandler
|
||||
fun onPlayerHide(event: PlayerHideEvent) {
|
||||
if (!event.player.hasPermission("myplugin.allowvanish")) {
|
||||
UtilitiesOG.trueogMessage(event.player, "<red>You are not allowed to vanish.")
|
||||
event.isCancelled = true
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Reporting issues
|
||||
|
||||
Open an issue on the [Vanish-OG GitHub repository](https://github.com/true-og/Vanish-OG/issues).
|
||||
Executable
+4
@@ -0,0 +1,4 @@
|
||||
#!/usr/bin/bash
|
||||
|
||||
# Fetch all submodule content.
|
||||
git submodule update --force --recursive --init
|
||||
@@ -0,0 +1,151 @@
|
||||
/* This is free and unencumbered software released into the public domain */
|
||||
|
||||
/* ------------------------------ Plugins ------------------------------ */
|
||||
plugins {
|
||||
id("java") // Import Java plugin.
|
||||
id("java-library") // Import Java Library plugin.
|
||||
id("com.diffplug.spotless") version "8.1.0" // Import Spotless plugin.
|
||||
id("com.gradleup.shadow") version "8.3.9" // Import Shadow plugin.
|
||||
id("checkstyle") // Import Checkstyle plugin.
|
||||
eclipse // Import Eclipse plugin.
|
||||
}
|
||||
|
||||
/* --------------------------- JDK / Kotlin ---------------------------- */
|
||||
java {
|
||||
sourceCompatibility = JavaVersion.VERSION_17 // Compile with JDK 17 compatibility.
|
||||
toolchain { // Select Java toolchain.
|
||||
languageVersion.set(JavaLanguageVersion.of(17)) // Use JDK 17.
|
||||
vendor.set(JvmVendorSpec.GRAAL_VM) // Use GraalVM CE.
|
||||
}
|
||||
}
|
||||
|
||||
/* ----------------------------- Metadata ------------------------------ */
|
||||
group = "de.myzelyam.vanishog" // Declare bundle identifier.
|
||||
|
||||
version = "6.2.22" // Declare plugin version (will be in .jar).
|
||||
|
||||
val apiVersion = "1.13" // Declare minecraft server target version.
|
||||
|
||||
/* ----------------------------- Resources ----------------------------- */
|
||||
tasks.named<ProcessResources>("processResources") {
|
||||
val props = mapOf("version" to version, "apiVersion" to apiVersion)
|
||||
inputs.properties(props) // Indicates to rerun if version changes.
|
||||
filesMatching("plugin.yml") { expand(props) }
|
||||
from("LICENSE") { into("/") } // Bundle licenses into jarfiles.
|
||||
}
|
||||
|
||||
/* ---------------------------- Repos ---------------------------------- */
|
||||
repositories {
|
||||
mavenCentral() // Import the Maven Central Maven Repository.
|
||||
gradlePluginPortal() // Import the Gradle Plugin Portal Maven Repository.
|
||||
maven { url = uri("https://repo.purpurmc.org/snapshots") } // Import the PurpurMC Maven Repository.
|
||||
maven { url = uri("https://repo.papermc.io/repository/maven-public/") } // PaperMC.
|
||||
maven { url = uri("https://repo.essentialsx.net/releases/") } // EssentialsX.
|
||||
maven { url = uri("https://jitpack.io") } // JitPack (VaultAPI, TrailGUI, OpenInv).
|
||||
maven { url = uri("https://repo.citizensnpcs.co/") } // Citizens.
|
||||
maven { url = uri("https://repo.mikeprimm.com/") } // Dynmap.
|
||||
maven { url = uri("https://libraries.minecraft.net") } // Mojang Brigadier.
|
||||
}
|
||||
|
||||
/* ---------------------- Java project deps ---------------------------- */
|
||||
dependencies {
|
||||
// Purpur API (server target).
|
||||
compileOnly("org.purpurmc.purpur:purpur-api:1.19.4-R0.1-SNAPSHOT")
|
||||
|
||||
// Import TrueOG Network Utilities-OG Java API (from source).
|
||||
compileOnlyApi(project(":libs:Utilities-OG"))
|
||||
|
||||
// EssentialsX API.
|
||||
compileOnly("net.essentialsx:EssentialsX:2.21.0") {
|
||||
exclude(group = "org.bstats", module = "bstats-bukkit") // Exclude bstats.
|
||||
}
|
||||
|
||||
// LuckPerms API (group, prefix, suffix lookups).
|
||||
compileOnly("net.luckperms:api:5.5")
|
||||
|
||||
// ProtocolLib (local jar in libs/).
|
||||
compileOnly(files("libs/ProtocolLib-5.0.jar"))
|
||||
|
||||
// Citizens API.
|
||||
compileOnly("net.citizensnpcs:citizensapi:2.0.28-SNAPSHOT")
|
||||
|
||||
// TrailGUI (via JitPack).
|
||||
compileOnly("com.github.SinnDevelopment:TrailGUI:37659dda03")
|
||||
|
||||
// Dynmap API.
|
||||
compileOnly("us.dynmap:dynmap-api:3.1")
|
||||
|
||||
// Import MiniPlaceholders API.
|
||||
compileOnly("io.github.miniplaceholders:miniplaceholders-api:2.2.3")
|
||||
|
||||
// Mojang Brigadier (provided at runtime by Purpur).
|
||||
compileOnly("com.mojang:brigadier:1.0.18")
|
||||
}
|
||||
|
||||
apply(from = "eclipse.gradle.kts") // Import eclipse classpath support script.
|
||||
|
||||
/* ---------------------- Reproducible jars ---------------------------- */
|
||||
tasks.withType<AbstractArchiveTask>().configureEach { // Ensure reproducible .jars
|
||||
isPreserveFileTimestamps = false
|
||||
isReproducibleFileOrder = true
|
||||
}
|
||||
|
||||
/* ----------------------------- Shadow -------------------------------- */
|
||||
tasks.shadowJar {
|
||||
exclude("io.github.miniplaceholders.*") // Exclude the MiniPlaceholders package from being shadowed.
|
||||
isEnableRelocation = true
|
||||
relocationPrefix = "${project.group}.shadow"
|
||||
archiveClassifier.set("") // Use empty string instead of null.
|
||||
archiveBaseName.set(rootProject.name) // Vanish-OG-${version}.jar
|
||||
minimize()
|
||||
}
|
||||
|
||||
tasks.jar { archiveClassifier.set("part") } // Applies to root jarfile only.
|
||||
|
||||
tasks.build { dependsOn(tasks.spotlessApply, tasks.shadowJar) } // Build depends on spotless and shadow.
|
||||
|
||||
/* --------------------------- Javac opts ------------------------------- */
|
||||
tasks.withType<JavaCompile>().configureEach {
|
||||
options.compilerArgs.add("-parameters") // Enable reflection for java code.
|
||||
options.isFork = true // Run javac in its own process.
|
||||
options.compilerArgs.add("-Xlint:deprecation") // Trigger deprecation warning messages.
|
||||
options.encoding = "UTF-8" // Use UTF-8 file encoding.
|
||||
}
|
||||
|
||||
/* ----------------------------- Auto Formatting ------------------------ */
|
||||
spotless {
|
||||
java {
|
||||
eclipse().configFile("config/formatter/eclipse-java-formatter.xml") // Eclipse java formatting.
|
||||
leadingTabsToSpaces() // Convert leftover leading tabs to spaces.
|
||||
removeUnusedImports() // Remove imports that aren't being called.
|
||||
}
|
||||
kotlinGradle {
|
||||
ktfmt().kotlinlangStyle().configure { it.setMaxWidth(120) } // JetBrains Kotlin formatting.
|
||||
target("build.gradle.kts", "settings.gradle.kts") // Gradle files to format.
|
||||
}
|
||||
}
|
||||
|
||||
checkstyle {
|
||||
toolVersion = "10.18.1" // Declare checkstyle version to use.
|
||||
configFile = file("config/checkstyle/checkstyle.xml") // Point checkstyle to config file.
|
||||
isIgnoreFailures = true // Don't fail the build if checkstyle does not pass.
|
||||
isShowViolations = true // Show the violations in any IDE with the checkstyle plugin.
|
||||
}
|
||||
|
||||
tasks.named("compileJava") {
|
||||
dependsOn("spotlessApply") // Run spotless before compiling with the JDK.
|
||||
}
|
||||
|
||||
tasks.named("spotlessCheck") {
|
||||
dependsOn("spotlessApply") // Run spotless before checking if spotless ran.
|
||||
}
|
||||
|
||||
/* ------------------------------ Eclipse SHIM ------------------------- */
|
||||
|
||||
// This can't be put in eclipse.gradle.kts because Gradle is weird.
|
||||
subprojects {
|
||||
apply(plugin = "java-library")
|
||||
apply(plugin = "eclipse")
|
||||
eclipse.project.name = "${project.name}-${rootProject.name}"
|
||||
tasks.withType<Jar>().configureEach { archiveBaseName.set("${project.name}-${rootProject.name}") }
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
<?xml version="1.0"?>
|
||||
<!DOCTYPE module PUBLIC
|
||||
"-//Checkstyle//DTD Checkstyle Configuration 1.3//EN"
|
||||
"https://checkstyle.org/dtds/configuration_1_3.dtd">
|
||||
<module name="Checker">
|
||||
|
||||
<module name="FileTabCharacter">
|
||||
<property name="eachLine" value="true"/>
|
||||
<property name="severity" value="error"/>
|
||||
</module>
|
||||
|
||||
<module name="TreeWalker">
|
||||
<module name="FinalLocalVariable"/>
|
||||
<module name="AvoidStarImport"/>
|
||||
<module name="Indentation">
|
||||
<property name="severity" value="ignore"/>
|
||||
</module>
|
||||
</module>
|
||||
|
||||
<module name="RegexpSingleline">
|
||||
<property name="format" value="\borg\.junit\.jupiter\.api\.Assertions\.fail\s*\(\s*"Not yet implemented"\s*\)\s*;"/>
|
||||
<property name="message" value="Remove placeholder fail() and implement the test."/>
|
||||
<property name="ignoreCase" value="true"/>
|
||||
<property name="severity" value="warning"/>
|
||||
</module>
|
||||
|
||||
<module name="RegexpSingleline">
|
||||
<property name="format" value="(?<!\w)fail\s*\(\s*"Not yet implemented"\s*\)\s*;"/>
|
||||
<property name="message" value="Remove placeholder fail() and implement the test."/>
|
||||
<property name="severity" value="warning"/>
|
||||
</module>
|
||||
|
||||
</module>
|
||||
|
||||
@@ -0,0 +1,404 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<profiles version="23">
|
||||
<profile kind="CodeFormatterProfile" name="TrueOG Network Formatting" version="23">
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_ellipsis" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_for_statment" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_package" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_javadoc_comments" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indentation.size" value="4"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_enum_constant_declaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_with_spaces" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.continuation_indentation" value="2"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_before_code_block" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_switch_case_expressions" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_package" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.indent_root_tags" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_or_operator_multicatch" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.enabling_tag" value="@formatter:on"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.count_line_length_from_starting_position" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_record_components" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_multiplicative_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_method" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameterized_type_references" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_logical_operator" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_annotation_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_record_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_enum_constant" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_multiplicative_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.preserve_white_space_between_code_and_line_comments" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_abstract_method" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_enum_constant_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_variable_declarations_on_columns" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_union_type_in_multicatch" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_catch_clause" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiplicative_operator" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_anonymous_type_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_switch_case_expressions" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_shift_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_end_of_code_block" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_bitwise_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_parameters" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_loops" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_for_body_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_switch_case_arrow_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_unary_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.format_line_comment_starting_on_first_column" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_annotation" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_ellipsis" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_try_resources" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_enum_constant" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.text_block_indentation" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_type_members_on_columns" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_assignment" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_module_statements" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.align_tags_names_descriptions" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_if_then_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_assignment_statements_on_columns" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_permitted_types" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block_in_case" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression_chain" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_header" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_annotations" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_assertion_message_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_method_declaration" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_fields_grouping_blank_lines" value="2147483647"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_bitwise_operator" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_resources_in_try" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_source_code" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_field" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_method" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_not_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_type_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_html" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_method_delcaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_if" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_empty_lines" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_arguments" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_unary_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_package" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_label" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_arrow_in_switch_case" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_permitted_types_in_type_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_record_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_bitwise_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.javadoc_do_not_separate_block_tags" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_try" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_lambda_arrow" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.indent_tag_description" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_record_constructor" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_string_concatenation" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiple_fields" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_array_initializer" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_shift_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_shift_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_do_while_body_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_record_components" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_outer_expressions_when_nested" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_for_loop_header" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_additive_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_getter_setter_on_one_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block_in_case_after_arrow" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_string_concatenation" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_lambda_arrow" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.join_lines_in_comments" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_record_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_relational_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_import_groups" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_logical_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_method_invocation" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_imports" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_record_declaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_switch_statement" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_arrow_in_switch_default" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.disabling_tag" value="@formatter:off"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_enum_constants" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_imports" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_end_of_method_body" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_if_while_statement" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_arrow_in_switch_case" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_field" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_switch_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_block" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_switch_case_with_arrow" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.align_tags_descriptions_grouped" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.line_length" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.use_on_off_tags" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_method_body_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_loop_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_method_declaration" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_type_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_additive_operator" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_record_constructor" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_relational_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_record_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_lambda_body" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.compact_else_if" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_try" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_parameter" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_relational_operator" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_arrows_in_switch_on_columns" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_additive_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_string_concatenation" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_line_comments" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.align_selector_in_method_invocation_on_expression_first_line" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_record_declaration" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_switch_case_with_arrow_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_switch_case_with_colon" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_after_code_block" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression" value="80"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_type" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_type" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_local_variable" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_arrow_in_switch_default" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_between_different_tags" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_additive_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.join_wrapped_lines" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_field" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_conditional_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.join_line_comments" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_shift_operator" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_try_clause" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_code_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_record_components" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.tabulation.size" value="4"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_bitwise_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_try" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_try_resources" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer" value="2"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_record_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_assignment_operator" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_switch" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_switch_case_with_arrow" value="20"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_lambda_body_block_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_annotations_on_method" value="49"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_record_constructor_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_record_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_assertion_message" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_member_type" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_logical_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_record_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_relational_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.format_block_comments" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration" value="16"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_last_class_body_declaration" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_body" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_simple_while_body_on_same_line" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_logical_operator" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_statement_group_in_switch" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_lambda_declaration" value="common_lines"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_permitted_types" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.keep_enum_declaration_on_one_line" value="one_line_never"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_constant" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_type_declaration" value="next_line_on_wrap"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_multiplicative_operator" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_package" value="0"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional" value="insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.comment.indent_parameter_description" value="false"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_code_block" value="1"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.tabulation.char" value="space"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.wrap_before_string_concatenation" value="true"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.lineSplit" value="120"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation" value="do not insert"/>
|
||||
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch" value="insert"/>
|
||||
</profile>
|
||||
</profiles>
|
||||
@@ -0,0 +1,158 @@
|
||||
/* This is free and unencumbered software released into the public domain */
|
||||
|
||||
import org.gradle.api.tasks.bundling.Jar
|
||||
import org.gradle.plugins.ide.eclipse.model.EclipseModel
|
||||
import java.nio.file.Files
|
||||
import javax.xml.parsers.DocumentBuilderFactory
|
||||
import javax.xml.transform.OutputKeys
|
||||
import javax.xml.transform.TransformerFactory
|
||||
import javax.xml.transform.dom.DOMSource
|
||||
import javax.xml.transform.stream.StreamResult
|
||||
|
||||
val sourcePluginProjects =
|
||||
configurations
|
||||
.getByName("compileClasspath")
|
||||
.allDependencies
|
||||
.filterIsInstance<ProjectDependency>()
|
||||
.map { it.path }
|
||||
.filter { it.startsWith(":libs:") }
|
||||
.distinct()
|
||||
val sourcePluginProjectNames = sourcePluginProjects.map { it.substringAfterLast(":") }.toSet()
|
||||
sourcePluginProjects.forEach { evaluationDependsOn(it) }
|
||||
|
||||
val ideLibs: Configuration by
|
||||
configurations.creating {
|
||||
isCanBeResolved = true
|
||||
isCanBeConsumed = false
|
||||
}
|
||||
|
||||
configure<EclipseModel> {
|
||||
project {
|
||||
name = "${rootProject.name}-Plugin"
|
||||
}
|
||||
classpath {
|
||||
plusConfigurations.add(ideLibs)
|
||||
}
|
||||
}
|
||||
|
||||
val ideLibDir = layout.buildDirectory.dir("ide-libs")
|
||||
val hashRegex = Regex("-[0-9a-fA-F]{10}(?=\\.jar$)") // Black magic.
|
||||
|
||||
val copyTasks = mutableListOf<TaskProvider<Copy>>()
|
||||
|
||||
sourcePluginProjects.forEach { path ->
|
||||
val sub = project(path)
|
||||
val archiveTaskName = if ("shadowJar" in sub.tasks.names) "shadowJar" else "jar"
|
||||
val archiveTask = sub.tasks.named<Jar>(archiveTaskName)
|
||||
val copyTask =
|
||||
tasks.register<Copy>("ideCopy${sub.name.replaceFirstChar(Char::titlecase)}") {
|
||||
dependsOn(archiveTask)
|
||||
from(archiveTask.flatMap { it.archiveFile })
|
||||
into(ideLibDir)
|
||||
rename { it.replace(hashRegex, "") } // Remove git commit hash from jarfile.
|
||||
}
|
||||
copyTasks += copyTask
|
||||
}
|
||||
|
||||
/* Ensure the jars exist before .classpath is generated */
|
||||
tasks.named("eclipseClasspath").configure { dependsOn(copyTasks) }
|
||||
|
||||
/* Supply those jars to the ideLibs configuration (after evaluation) */
|
||||
afterEvaluate { dependencies { add("ideLibs", fileTree(ideLibDir) { include("*.jar") }) } }
|
||||
|
||||
val injectIdeLibs =
|
||||
tasks.register("injectIdeLibs") {
|
||||
dependsOn("eclipse") // run after all eclipse files are generated
|
||||
doLast {
|
||||
val cpFile = file(".classpath")
|
||||
if (!cpFile.exists()) return@doLast
|
||||
|
||||
val jars = fileTree(ideLibDir.get()) { include("*.jar") }.files.sortedBy { it.name }
|
||||
if (jars.isEmpty()) return@doLast
|
||||
|
||||
// Parse DOM
|
||||
val dbf = DocumentBuilderFactory.newInstance()
|
||||
val doc = dbf.newDocumentBuilder().parse(cpFile)
|
||||
val root = doc.documentElement
|
||||
|
||||
// Helper to see if an entry already exists
|
||||
fun exists(path: String): Boolean =
|
||||
root.getElementsByTagName("classpathentry").let { list ->
|
||||
(0 until list.length).any { i ->
|
||||
val n = list.item(i)
|
||||
val kind = n.attributes?.getNamedItem("kind")?.nodeValue
|
||||
val p = n.attributes?.getNamedItem("path")?.nodeValue
|
||||
kind == "lib" && p == path
|
||||
}
|
||||
}
|
||||
|
||||
// Remove any entry that points to ide-libs dir or unresolved :libs: project refs.
|
||||
val toRemove = mutableListOf<org.w3c.dom.Node>()
|
||||
val list = root.getElementsByTagName("classpathentry")
|
||||
val dirPath = ideLibDir.get().asFile.absolutePath
|
||||
for (i in 0 until list.length) {
|
||||
val n = list.item(i)
|
||||
val kind = n.attributes?.getNamedItem("kind")?.nodeValue
|
||||
val p = n.attributes?.getNamedItem("path")?.nodeValue ?: ""
|
||||
val isIdeLibEntry = kind == "lib" && (p == dirPath || p.startsWith("$dirPath/"))
|
||||
val sourceProjectPath = p.removePrefix("/")
|
||||
val isHalfImportedSourceModule = kind == "src" && p.startsWith("/libs:")
|
||||
val isSourcePluginModule = kind == "src" && sourceProjectPath in sourcePluginProjectNames
|
||||
if (isIdeLibEntry || isHalfImportedSourceModule || isSourcePluginModule) {
|
||||
toRemove += n
|
||||
}
|
||||
}
|
||||
toRemove.forEach { root.removeChild(it) }
|
||||
|
||||
// Append our jar entries LAST
|
||||
jars.forEach { f ->
|
||||
val abs = f.absolutePath
|
||||
if (!exists(abs)) {
|
||||
val entry = doc.createElement("classpathentry")
|
||||
entry.setAttribute("kind", "lib")
|
||||
entry.setAttribute("path", abs)
|
||||
root.appendChild(entry)
|
||||
}
|
||||
}
|
||||
|
||||
// Write back pretty
|
||||
val tf =
|
||||
TransformerFactory.newInstance().newTransformer().apply {
|
||||
setOutputProperty(OutputKeys.INDENT, "yes")
|
||||
setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "1")
|
||||
setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "no")
|
||||
setOutputProperty(OutputKeys.ENCODING, "UTF-8")
|
||||
}
|
||||
Files.newBufferedWriter(cpFile.toPath()).use { w -> tf.transform(DOMSource(doc), StreamResult(w)) }
|
||||
}
|
||||
}
|
||||
|
||||
tasks.named("eclipse").configure { finalizedBy(injectIdeLibs) }
|
||||
|
||||
val eclipseModel = extensions.getByType<EclipseModel>()
|
||||
|
||||
fun Project.addResolvableEclipseConfigs() {
|
||||
val jarAttr =
|
||||
objects.named(org.gradle.api.attributes.LibraryElements::class, org.gradle.api.attributes.LibraryElements.JAR)
|
||||
val apiAttr = objects.named(org.gradle.api.attributes.Usage::class, org.gradle.api.attributes.Usage.JAVA_API)
|
||||
|
||||
val compileOnlyRes =
|
||||
configurations.create("eclipseCompileOnly") {
|
||||
extendsFrom(configurations.getByName("compileOnly"))
|
||||
isCanBeResolved = true
|
||||
isCanBeConsumed = false
|
||||
attributes.attribute(org.gradle.api.attributes.Usage.USAGE_ATTRIBUTE, apiAttr)
|
||||
attributes.attribute(org.gradle.api.attributes.LibraryElements.LIBRARY_ELEMENTS_ATTRIBUTE, jarAttr)
|
||||
}
|
||||
val compileOnlyApiRes =
|
||||
configurations.create("eclipseCompileOnlyApi") {
|
||||
extendsFrom(configurations.getByName("compileOnlyApi"))
|
||||
isCanBeResolved = true
|
||||
isCanBeConsumed = false
|
||||
attributes.attribute(org.gradle.api.attributes.Usage.USAGE_ATTRIBUTE, apiAttr)
|
||||
attributes.attribute(org.gradle.api.attributes.LibraryElements.LIBRARY_ELEMENTS_ATTRIBUTE, jarAttr)
|
||||
}
|
||||
eclipseModel.classpath.plusConfigurations.addAll(listOf(compileOnlyRes, compileOnlyApiRes))
|
||||
}
|
||||
|
||||
addResolvableEclipseConfigs()
|
||||
@@ -0,0 +1 @@
|
||||
org.gradle.java.home=/home/notalexnoyle/.sdkman/candidates/java/17.0.9-graalce
|
||||
Vendored
BIN
Binary file not shown.
+7
@@ -0,0 +1,7 @@
|
||||
distributionBase=GRADLE_USER_HOME
|
||||
distributionPath=wrapper/dists
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-8.14.3-bin.zip
|
||||
networkTimeout=10000
|
||||
validateDistributionUrl=true
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
zipStorePath=wrapper/dists
|
||||
@@ -0,0 +1,251 @@
|
||||
#!/bin/sh
|
||||
|
||||
#
|
||||
# Copyright © 2015-2021 the original authors.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# https://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
#
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
#
|
||||
|
||||
##############################################################################
|
||||
#
|
||||
# Gradle start up script for POSIX generated by Gradle.
|
||||
#
|
||||
# Important for running:
|
||||
#
|
||||
# (1) You need a POSIX-compliant shell to run this script. If your /bin/sh is
|
||||
# noncompliant, but you have some other compliant shell such as ksh or
|
||||
# bash, then to run this script, type that shell name before the whole
|
||||
# command line, like:
|
||||
#
|
||||
# ksh Gradle
|
||||
#
|
||||
# Busybox and similar reduced shells will NOT work, because this script
|
||||
# requires all of these POSIX shell features:
|
||||
# * functions;
|
||||
# * expansions «$var», «${var}», «${var:-default}», «${var+SET}»,
|
||||
# «${var#prefix}», «${var%suffix}», and «$( cmd )»;
|
||||
# * compound commands having a testable exit status, especially «case»;
|
||||
# * various built-in commands including «command», «set», and «ulimit».
|
||||
#
|
||||
# Important for patching:
|
||||
#
|
||||
# (2) This script targets any POSIX shell, so it avoids extensions provided
|
||||
# by Bash, Ksh, etc; in particular arrays are avoided.
|
||||
#
|
||||
# The "traditional" practice of packing multiple parameters into a
|
||||
# space-separated string is a well documented source of bugs and security
|
||||
# problems, so this is (mostly) avoided, by progressively accumulating
|
||||
# options in "$@", and eventually passing that to Java.
|
||||
#
|
||||
# Where the inherited environment variables (DEFAULT_JVM_OPTS, JAVA_OPTS,
|
||||
# and GRADLE_OPTS) rely on word-splitting, this is performed explicitly;
|
||||
# see the in-line comments for details.
|
||||
#
|
||||
# There are tweaks for specific operating systems such as AIX, CygWin,
|
||||
# Darwin, MinGW, and NonStop.
|
||||
#
|
||||
# (3) This script is generated from the Groovy template
|
||||
# https://github.com/gradle/gradle/blob/HEAD/platforms/jvm/plugins-application/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
|
||||
# within the Gradle project.
|
||||
#
|
||||
# You can find Gradle at https://github.com/gradle/gradle/.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
# Attempt to set APP_HOME
|
||||
|
||||
# Resolve links: $0 may be a link
|
||||
app_path=$0
|
||||
|
||||
# Need this for daisy-chained symlinks.
|
||||
while
|
||||
APP_HOME=${app_path%"${app_path##*/}"} # leaves a trailing /; empty if no leading path
|
||||
[ -h "$app_path" ]
|
||||
do
|
||||
ls=$( ls -ld "$app_path" )
|
||||
link=${ls#*' -> '}
|
||||
case $link in #(
|
||||
/*) app_path=$link ;; #(
|
||||
*) app_path=$APP_HOME$link ;;
|
||||
esac
|
||||
done
|
||||
|
||||
# This is normally unused
|
||||
# shellcheck disable=SC2034
|
||||
APP_BASE_NAME=${0##*/}
|
||||
# Discard cd standard output in case $CDPATH is set (https://github.com/gradle/gradle/issues/25036)
|
||||
APP_HOME=$( cd -P "${APP_HOME:-./}" > /dev/null && printf '%s\n' "$PWD" ) || exit
|
||||
|
||||
# Use the maximum available, or set MAX_FD != -1 to use that value.
|
||||
MAX_FD=maximum
|
||||
|
||||
warn () {
|
||||
echo "$*"
|
||||
} >&2
|
||||
|
||||
die () {
|
||||
echo
|
||||
echo "$*"
|
||||
echo
|
||||
exit 1
|
||||
} >&2
|
||||
|
||||
# OS specific support (must be 'true' or 'false').
|
||||
cygwin=false
|
||||
msys=false
|
||||
darwin=false
|
||||
nonstop=false
|
||||
case "$( uname )" in #(
|
||||
CYGWIN* ) cygwin=true ;; #(
|
||||
Darwin* ) darwin=true ;; #(
|
||||
MSYS* | MINGW* ) msys=true ;; #(
|
||||
NONSTOP* ) nonstop=true ;;
|
||||
esac
|
||||
|
||||
CLASSPATH="\\\"\\\""
|
||||
|
||||
|
||||
# Determine the Java command to use to start the JVM.
|
||||
if [ -n "$JAVA_HOME" ] ; then
|
||||
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
|
||||
# IBM's JDK on AIX uses strange locations for the executables
|
||||
JAVACMD=$JAVA_HOME/jre/sh/java
|
||||
else
|
||||
JAVACMD=$JAVA_HOME/bin/java
|
||||
fi
|
||||
if [ ! -x "$JAVACMD" ] ; then
|
||||
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
|
||||
|
||||
Please set the JAVA_HOME variable in your environment to match the
|
||||
location of your Java installation."
|
||||
fi
|
||||
else
|
||||
JAVACMD=java
|
||||
if ! command -v java >/dev/null 2>&1
|
||||
then
|
||||
die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
|
||||
|
||||
Please set the JAVA_HOME variable in your environment to match the
|
||||
location of your Java installation."
|
||||
fi
|
||||
fi
|
||||
|
||||
# Increase the maximum file descriptors if we can.
|
||||
if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then
|
||||
case $MAX_FD in #(
|
||||
max*)
|
||||
# In POSIX sh, ulimit -H is undefined. That's why the result is checked to see if it worked.
|
||||
# shellcheck disable=SC2039,SC3045
|
||||
MAX_FD=$( ulimit -H -n ) ||
|
||||
warn "Could not query maximum file descriptor limit"
|
||||
esac
|
||||
case $MAX_FD in #(
|
||||
'' | soft) :;; #(
|
||||
*)
|
||||
# In POSIX sh, ulimit -n is undefined. That's why the result is checked to see if it worked.
|
||||
# shellcheck disable=SC2039,SC3045
|
||||
ulimit -n "$MAX_FD" ||
|
||||
warn "Could not set maximum file descriptor limit to $MAX_FD"
|
||||
esac
|
||||
fi
|
||||
|
||||
# Collect all arguments for the java command, stacking in reverse order:
|
||||
# * args from the command line
|
||||
# * the main class name
|
||||
# * -classpath
|
||||
# * -D...appname settings
|
||||
# * --module-path (only if needed)
|
||||
# * DEFAULT_JVM_OPTS, JAVA_OPTS, and GRADLE_OPTS environment variables.
|
||||
|
||||
# For Cygwin or MSYS, switch paths to Windows format before running java
|
||||
if "$cygwin" || "$msys" ; then
|
||||
APP_HOME=$( cygpath --path --mixed "$APP_HOME" )
|
||||
CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" )
|
||||
|
||||
JAVACMD=$( cygpath --unix "$JAVACMD" )
|
||||
|
||||
# Now convert the arguments - kludge to limit ourselves to /bin/sh
|
||||
for arg do
|
||||
if
|
||||
case $arg in #(
|
||||
-*) false ;; # don't mess with options #(
|
||||
/?*) t=${arg#/} t=/${t%%/*} # looks like a POSIX filepath
|
||||
[ -e "$t" ] ;; #(
|
||||
*) false ;;
|
||||
esac
|
||||
then
|
||||
arg=$( cygpath --path --ignore --mixed "$arg" )
|
||||
fi
|
||||
# Roll the args list around exactly as many times as the number of
|
||||
# args, so each arg winds up back in the position where it started, but
|
||||
# possibly modified.
|
||||
#
|
||||
# NB: a `for` loop captures its iteration list before it begins, so
|
||||
# changing the positional parameters here affects neither the number of
|
||||
# iterations, nor the values presented in `arg`.
|
||||
shift # remove old arg
|
||||
set -- "$@" "$arg" # push replacement arg
|
||||
done
|
||||
fi
|
||||
|
||||
|
||||
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
|
||||
|
||||
# Collect all arguments for the java command:
|
||||
# * DEFAULT_JVM_OPTS, JAVA_OPTS, and optsEnvironmentVar are not allowed to contain shell fragments,
|
||||
# and any embedded shellness will be escaped.
|
||||
# * For example: A user cannot expect ${Hostname} to be expanded, as it is an environment variable and will be
|
||||
# treated as '${Hostname}' itself on the command line.
|
||||
|
||||
set -- \
|
||||
"-Dorg.gradle.appname=$APP_BASE_NAME" \
|
||||
-classpath "$CLASSPATH" \
|
||||
-jar "$APP_HOME/gradle/wrapper/gradle-wrapper.jar" \
|
||||
"$@"
|
||||
|
||||
# Stop when "xargs" is not available.
|
||||
if ! command -v xargs >/dev/null 2>&1
|
||||
then
|
||||
die "xargs is not available"
|
||||
fi
|
||||
|
||||
# Use "xargs" to parse quoted args.
|
||||
#
|
||||
# With -n1 it outputs one arg per line, with the quotes and backslashes removed.
|
||||
#
|
||||
# In Bash we could simply go:
|
||||
#
|
||||
# readarray ARGS < <( xargs -n1 <<<"$var" ) &&
|
||||
# set -- "${ARGS[@]}" "$@"
|
||||
#
|
||||
# but POSIX shell has neither arrays nor command substitution, so instead we
|
||||
# post-process each arg (as a line of input to sed) to backslash-escape any
|
||||
# character that might be a shell metacharacter, then use eval to reverse
|
||||
# that process (while maintaining the separation between arguments), and wrap
|
||||
# the whole thing up as a single "set" statement.
|
||||
#
|
||||
# This will of course break if any of these variables contains a newline or
|
||||
# an unmatched quote.
|
||||
#
|
||||
|
||||
eval "set -- $(
|
||||
printf '%s\n' "$DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS" |
|
||||
xargs -n1 |
|
||||
sed ' s~[^-[:alnum:]+,./:=@_]~\\&~g; ' |
|
||||
tr '\n' ' '
|
||||
)" '"$@"'
|
||||
|
||||
exec "$JAVACMD" "$@"
|
||||
Vendored
+94
@@ -0,0 +1,94 @@
|
||||
@rem
|
||||
@rem Copyright 2015 the original author or authors.
|
||||
@rem
|
||||
@rem Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@rem you may not use this file except in compliance with the License.
|
||||
@rem You may obtain a copy of the License at
|
||||
@rem
|
||||
@rem https://www.apache.org/licenses/LICENSE-2.0
|
||||
@rem
|
||||
@rem Unless required by applicable law or agreed to in writing, software
|
||||
@rem distributed under the License is distributed on an "AS IS" BASIS,
|
||||
@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
@rem See the License for the specific language governing permissions and
|
||||
@rem limitations under the License.
|
||||
@rem
|
||||
@rem SPDX-License-Identifier: Apache-2.0
|
||||
@rem
|
||||
|
||||
@if "%DEBUG%"=="" @echo off
|
||||
@rem ##########################################################################
|
||||
@rem
|
||||
@rem Gradle startup script for Windows
|
||||
@rem
|
||||
@rem ##########################################################################
|
||||
|
||||
@rem Set local scope for the variables with windows NT shell
|
||||
if "%OS%"=="Windows_NT" setlocal
|
||||
|
||||
set DIRNAME=%~dp0
|
||||
if "%DIRNAME%"=="" set DIRNAME=.
|
||||
@rem This is normally unused
|
||||
set APP_BASE_NAME=%~n0
|
||||
set APP_HOME=%DIRNAME%
|
||||
|
||||
@rem Resolve any "." and ".." in APP_HOME to make it shorter.
|
||||
for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
|
||||
|
||||
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||
set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
|
||||
|
||||
@rem Find java.exe
|
||||
if defined JAVA_HOME goto findJavaFromJavaHome
|
||||
|
||||
set JAVA_EXE=java.exe
|
||||
%JAVA_EXE% -version >NUL 2>&1
|
||||
if %ERRORLEVEL% equ 0 goto execute
|
||||
|
||||
echo. 1>&2
|
||||
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 1>&2
|
||||
echo. 1>&2
|
||||
echo Please set the JAVA_HOME variable in your environment to match the 1>&2
|
||||
echo location of your Java installation. 1>&2
|
||||
|
||||
goto fail
|
||||
|
||||
:findJavaFromJavaHome
|
||||
set JAVA_HOME=%JAVA_HOME:"=%
|
||||
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
|
||||
|
||||
if exist "%JAVA_EXE%" goto execute
|
||||
|
||||
echo. 1>&2
|
||||
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% 1>&2
|
||||
echo. 1>&2
|
||||
echo Please set the JAVA_HOME variable in your environment to match the 1>&2
|
||||
echo location of your Java installation. 1>&2
|
||||
|
||||
goto fail
|
||||
|
||||
:execute
|
||||
@rem Setup the command line
|
||||
|
||||
set CLASSPATH=
|
||||
|
||||
|
||||
@rem Execute Gradle
|
||||
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" -jar "%APP_HOME%\gradle\wrapper\gradle-wrapper.jar" %*
|
||||
|
||||
:end
|
||||
@rem End local scope for the variables with windows NT shell
|
||||
if %ERRORLEVEL% equ 0 goto mainEnd
|
||||
|
||||
:fail
|
||||
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
|
||||
rem the _cmd.exe /c_ return code!
|
||||
set EXIT_CODE=%ERRORLEVEL%
|
||||
if %EXIT_CODE% equ 0 set EXIT_CODE=1
|
||||
if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE%
|
||||
exit /b %EXIT_CODE%
|
||||
|
||||
:mainEnd
|
||||
if "%OS%"=="Windows_NT" endlocal
|
||||
|
||||
:omega
|
||||
@@ -0,0 +1,339 @@
|
||||
GNU GENERAL PUBLIC LICENSE
|
||||
Version 2, June 1991
|
||||
|
||||
Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
Everyone is permitted to copy and distribute verbatim copies
|
||||
of this license document, but changing it is not allowed.
|
||||
|
||||
Preamble
|
||||
|
||||
The licenses for most software are designed to take away your
|
||||
freedom to share and change it. By contrast, the GNU General Public
|
||||
License is intended to guarantee your freedom to share and change free
|
||||
software--to make sure the software is free for all its users. This
|
||||
General Public License applies to most of the Free Software
|
||||
Foundation's software and to any other program whose authors commit to
|
||||
using it. (Some other Free Software Foundation software is covered by
|
||||
the GNU Lesser General Public License instead.) You can apply it to
|
||||
your programs, too.
|
||||
|
||||
When we speak of free software, we are referring to freedom, not
|
||||
price. Our General Public Licenses are designed to make sure that you
|
||||
have the freedom to distribute copies of free software (and charge for
|
||||
this service if you wish), that you receive source code or can get it
|
||||
if you want it, that you can change the software or use pieces of it
|
||||
in new free programs; and that you know you can do these things.
|
||||
|
||||
To protect your rights, we need to make restrictions that forbid
|
||||
anyone to deny you these rights or to ask you to surrender the rights.
|
||||
These restrictions translate to certain responsibilities for you if you
|
||||
distribute copies of the software, or if you modify it.
|
||||
|
||||
For example, if you distribute copies of such a program, whether
|
||||
gratis or for a fee, you must give the recipients all the rights that
|
||||
you have. You must make sure that they, too, receive or can get the
|
||||
source code. And you must show them these terms so they know their
|
||||
rights.
|
||||
|
||||
We protect your rights with two steps: (1) copyright the software, and
|
||||
(2) offer you this license which gives you legal permission to copy,
|
||||
distribute and/or modify the software.
|
||||
|
||||
Also, for each author's protection and ours, we want to make certain
|
||||
that everyone understands that there is no warranty for this free
|
||||
software. If the software is modified by someone else and passed on, we
|
||||
want its recipients to know that what they have is not the original, so
|
||||
that any problems introduced by others will not reflect on the original
|
||||
authors' reputations.
|
||||
|
||||
Finally, any free program is threatened constantly by software
|
||||
patents. We wish to avoid the danger that redistributors of a free
|
||||
program will individually obtain patent licenses, in effect making the
|
||||
program proprietary. To prevent this, we have made it clear that any
|
||||
patent must be licensed for everyone's free use or not licensed at all.
|
||||
|
||||
The precise terms and conditions for copying, distribution and
|
||||
modification follow.
|
||||
|
||||
GNU GENERAL PUBLIC LICENSE
|
||||
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
||||
|
||||
0. This License applies to any program or other work which contains
|
||||
a notice placed by the copyright holder saying it may be distributed
|
||||
under the terms of this General Public License. The "Program", below,
|
||||
refers to any such program or work, and a "work based on the Program"
|
||||
means either the Program or any derivative work under copyright law:
|
||||
that is to say, a work containing the Program or a portion of it,
|
||||
either verbatim or with modifications and/or translated into another
|
||||
language. (Hereinafter, translation is included without limitation in
|
||||
the term "modification".) Each licensee is addressed as "you".
|
||||
|
||||
Activities other than copying, distribution and modification are not
|
||||
covered by this License; they are outside its scope. The act of
|
||||
running the Program is not restricted, and the output from the Program
|
||||
is covered only if its contents constitute a work based on the
|
||||
Program (independent of having been made by running the Program).
|
||||
Whether that is true depends on what the Program does.
|
||||
|
||||
1. You may copy and distribute verbatim copies of the Program's
|
||||
source code as you receive it, in any medium, provided that you
|
||||
conspicuously and appropriately publish on each copy an appropriate
|
||||
copyright notice and disclaimer of warranty; keep intact all the
|
||||
notices that refer to this License and to the absence of any warranty;
|
||||
and give any other recipients of the Program a copy of this License
|
||||
along with the Program.
|
||||
|
||||
You may charge a fee for the physical act of transferring a copy, and
|
||||
you may at your option offer warranty protection in exchange for a fee.
|
||||
|
||||
2. You may modify your copy or copies of the Program or any portion
|
||||
of it, thus forming a work based on the Program, and copy and
|
||||
distribute such modifications or work under the terms of Section 1
|
||||
above, provided that you also meet all of these conditions:
|
||||
|
||||
a) You must cause the modified files to carry prominent notices
|
||||
stating that you changed the files and the date of any change.
|
||||
|
||||
b) You must cause any work that you distribute or publish, that in
|
||||
whole or in part contains or is derived from the Program or any
|
||||
part thereof, to be licensed as a whole at no charge to all third
|
||||
parties under the terms of this License.
|
||||
|
||||
c) If the modified program normally reads commands interactively
|
||||
when run, you must cause it, when started running for such
|
||||
interactive use in the most ordinary way, to print or display an
|
||||
announcement including an appropriate copyright notice and a
|
||||
notice that there is no warranty (or else, saying that you provide
|
||||
a warranty) and that users may redistribute the program under
|
||||
these conditions, and telling the user how to view a copy of this
|
||||
License. (Exception: if the Program itself is interactive but
|
||||
does not normally print such an announcement, your work based on
|
||||
the Program is not required to print an announcement.)
|
||||
|
||||
These requirements apply to the modified work as a whole. If
|
||||
identifiable sections of that work are not derived from the Program,
|
||||
and can be reasonably considered independent and separate works in
|
||||
themselves, then this License, and its terms, do not apply to those
|
||||
sections when you distribute them as separate works. But when you
|
||||
distribute the same sections as part of a whole which is a work based
|
||||
on the Program, the distribution of the whole must be on the terms of
|
||||
this License, whose permissions for other licensees extend to the
|
||||
entire whole, and thus to each and every part regardless of who wrote it.
|
||||
|
||||
Thus, it is not the intent of this section to claim rights or contest
|
||||
your rights to work written entirely by you; rather, the intent is to
|
||||
exercise the right to control the distribution of derivative or
|
||||
collective works based on the Program.
|
||||
|
||||
In addition, mere aggregation of another work not based on the Program
|
||||
with the Program (or with a work based on the Program) on a volume of
|
||||
a storage or distribution medium does not bring the other work under
|
||||
the scope of this License.
|
||||
|
||||
3. You may copy and distribute the Program (or a work based on it,
|
||||
under Section 2) in object code or executable form under the terms of
|
||||
Sections 1 and 2 above provided that you also do one of the following:
|
||||
|
||||
a) Accompany it with the complete corresponding machine-readable
|
||||
source code, which must be distributed under the terms of Sections
|
||||
1 and 2 above on a medium customarily used for software interchange; or,
|
||||
|
||||
b) Accompany it with a written offer, valid for at least three
|
||||
years, to give any third party, for a charge no more than your
|
||||
cost of physically performing source distribution, a complete
|
||||
machine-readable copy of the corresponding source code, to be
|
||||
distributed under the terms of Sections 1 and 2 above on a medium
|
||||
customarily used for software interchange; or,
|
||||
|
||||
c) Accompany it with the information you received as to the offer
|
||||
to distribute corresponding source code. (This alternative is
|
||||
allowed only for noncommercial distribution and only if you
|
||||
received the program in object code or executable form with such
|
||||
an offer, in accord with Subsection b above.)
|
||||
|
||||
The source code for a work means the preferred form of the work for
|
||||
making modifications to it. For an executable work, complete source
|
||||
code means all the source code for all modules it contains, plus any
|
||||
associated interface definition files, plus the scripts used to
|
||||
control compilation and installation of the executable. However, as a
|
||||
special exception, the source code distributed need not include
|
||||
anything that is normally distributed (in either source or binary
|
||||
form) with the major components (compiler, kernel, and so on) of the
|
||||
operating system on which the executable runs, unless that component
|
||||
itself accompanies the executable.
|
||||
|
||||
If distribution of executable or object code is made by offering
|
||||
access to copy from a designated place, then offering equivalent
|
||||
access to copy the source code from the same place counts as
|
||||
distribution of the source code, even though third parties are not
|
||||
compelled to copy the source along with the object code.
|
||||
|
||||
4. You may not copy, modify, sublicense, or distribute the Program
|
||||
except as expressly provided under this License. Any attempt
|
||||
otherwise to copy, modify, sublicense or distribute the Program is
|
||||
void, and will automatically terminate your rights under this License.
|
||||
However, parties who have received copies, or rights, from you under
|
||||
this License will not have their licenses terminated so long as such
|
||||
parties remain in full compliance.
|
||||
|
||||
5. You are not required to accept this License, since you have not
|
||||
signed it. However, nothing else grants you permission to modify or
|
||||
distribute the Program or its derivative works. These actions are
|
||||
prohibited by law if you do not accept this License. Therefore, by
|
||||
modifying or distributing the Program (or any work based on the
|
||||
Program), you indicate your acceptance of this License to do so, and
|
||||
all its terms and conditions for copying, distributing or modifying
|
||||
the Program or works based on it.
|
||||
|
||||
6. Each time you redistribute the Program (or any work based on the
|
||||
Program), the recipient automatically receives a license from the
|
||||
original licensor to copy, distribute or modify the Program subject to
|
||||
these terms and conditions. You may not impose any further
|
||||
restrictions on the recipients' exercise of the rights granted herein.
|
||||
You are not responsible for enforcing compliance by third parties to
|
||||
this License.
|
||||
|
||||
7. If, as a consequence of a court judgment or allegation of patent
|
||||
infringement or for any other reason (not limited to patent issues),
|
||||
conditions are imposed on you (whether by court order, agreement or
|
||||
otherwise) that contradict the conditions of this License, they do not
|
||||
excuse you from the conditions of this License. If you cannot
|
||||
distribute so as to satisfy simultaneously your obligations under this
|
||||
License and any other pertinent obligations, then as a consequence you
|
||||
may not distribute the Program at all. For example, if a patent
|
||||
license would not permit royalty-free redistribution of the Program by
|
||||
all those who receive copies directly or indirectly through you, then
|
||||
the only way you could satisfy both it and this License would be to
|
||||
refrain entirely from distribution of the Program.
|
||||
|
||||
If any portion of this section is held invalid or unenforceable under
|
||||
any particular circumstance, the balance of the section is intended to
|
||||
apply and the section as a whole is intended to apply in other
|
||||
circumstances.
|
||||
|
||||
It is not the purpose of this section to induce you to infringe any
|
||||
patents or other property right claims or to contest validity of any
|
||||
such claims; this section has the sole purpose of protecting the
|
||||
integrity of the free software distribution system, which is
|
||||
implemented by public license practices. Many people have made
|
||||
generous contributions to the wide range of software distributed
|
||||
through that system in reliance on consistent application of that
|
||||
system; it is up to the author/donor to decide if he or she is willing
|
||||
to distribute software through any other system and a licensee cannot
|
||||
impose that choice.
|
||||
|
||||
This section is intended to make thoroughly clear what is believed to
|
||||
be a consequence of the rest of this License.
|
||||
|
||||
8. If the distribution and/or use of the Program is restricted in
|
||||
certain countries either by patents or by copyrighted interfaces, the
|
||||
original copyright holder who places the Program under this License
|
||||
may add an explicit geographical distribution limitation excluding
|
||||
those countries, so that distribution is permitted only in or among
|
||||
countries not thus excluded. In such case, this License incorporates
|
||||
the limitation as if written in the body of this License.
|
||||
|
||||
9. The Free Software Foundation may publish revised and/or new versions
|
||||
of the General Public License from time to time. Such new versions will
|
||||
be similar in spirit to the present version, but may differ in detail to
|
||||
address new problems or concerns.
|
||||
|
||||
Each version is given a distinguishing version number. If the Program
|
||||
specifies a version number of this License which applies to it and "any
|
||||
later version", you have the option of following the terms and conditions
|
||||
either of that version or of any later version published by the Free
|
||||
Software Foundation. If the Program does not specify a version number of
|
||||
this License, you may choose any version ever published by the Free Software
|
||||
Foundation.
|
||||
|
||||
10. If you wish to incorporate parts of the Program into other free
|
||||
programs whose distribution conditions are different, write to the author
|
||||
to ask for permission. For software which is copyrighted by the Free
|
||||
Software Foundation, write to the Free Software Foundation; we sometimes
|
||||
make exceptions for this. Our decision will be guided by the two goals
|
||||
of preserving the free status of all derivatives of our free software and
|
||||
of promoting the sharing and reuse of software generally.
|
||||
|
||||
NO WARRANTY
|
||||
|
||||
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
|
||||
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
|
||||
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
|
||||
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
|
||||
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
|
||||
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
|
||||
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
|
||||
REPAIR OR CORRECTION.
|
||||
|
||||
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
||||
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
|
||||
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
|
||||
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
|
||||
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
|
||||
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
|
||||
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
|
||||
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
|
||||
POSSIBILITY OF SUCH DAMAGES.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
How to Apply These Terms to Your New Programs
|
||||
|
||||
If you develop a new program, and you want it to be of the greatest
|
||||
possible use to the public, the best way to achieve this is to make it
|
||||
free software which everyone can redistribute and change under these terms.
|
||||
|
||||
To do so, attach the following notices to the program. It is safest
|
||||
to attach them to the start of each source file to most effectively
|
||||
convey the exclusion of warranty; and each file should have at least
|
||||
the "copyright" line and a pointer to where the full notice is found.
|
||||
|
||||
<one line to give the program's name and a brief idea of what it does.>
|
||||
Copyright (C) <year> <name of author>
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with this program; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
|
||||
Also add information on how to contact you by electronic and paper mail.
|
||||
|
||||
If the program is interactive, make it output a short notice like this
|
||||
when it starts in an interactive mode:
|
||||
|
||||
Gnomovision version 69, Copyright (C) year name of author
|
||||
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
||||
This is free software, and you are welcome to redistribute it
|
||||
under certain conditions; type `show c' for details.
|
||||
|
||||
The hypothetical commands `show w' and `show c' should show the appropriate
|
||||
parts of the General Public License. Of course, the commands you use may
|
||||
be called something other than `show w' and `show c'; they could even be
|
||||
mouse-clicks or menu items--whatever suits your program.
|
||||
|
||||
You should also get your employer (if you work as a programmer) or your
|
||||
school, if any, to sign a "copyright disclaimer" for the program, if
|
||||
necessary. Here is a sample; alter the names:
|
||||
|
||||
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
|
||||
`Gnomovision' (which makes passes at compilers) written by James Hacker.
|
||||
|
||||
<signature of Ty Coon>, 1 April 1989
|
||||
Ty Coon, President of Vice
|
||||
|
||||
This General Public License does not permit incorporating your program into
|
||||
proprietary programs. If your program is a subroutine library, you may
|
||||
consider it more useful to permit linking proprietary applications with the
|
||||
library. If this is what you want to do, use the GNU Lesser General
|
||||
Public License instead of this License.
|
||||
Binary file not shown.
Submodule
+1
Submodule libs/Utilities-OG added at 20c2947f83.
@@ -1,189 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-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">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<groupId>de.myzelyam</groupId>
|
||||
<artifactId>SuperVanish</artifactId>
|
||||
<version>6.2.21</version>
|
||||
|
||||
<properties>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.8.1</version>
|
||||
<configuration>
|
||||
<source>17</source>
|
||||
<target>17</target>
|
||||
<annotationProcessorPaths>
|
||||
<path>
|
||||
<groupId>org.projectlombok</groupId>
|
||||
<artifactId>lombok</artifactId>
|
||||
<version>1.18.30</version>
|
||||
</path>
|
||||
</annotationProcessorPaths>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
<resources>
|
||||
<resource>
|
||||
<directory>src/main/resources</directory>
|
||||
<filtering>true</filtering>
|
||||
</resource>
|
||||
</resources>
|
||||
</build>
|
||||
|
||||
<repositories>
|
||||
<repository>
|
||||
<id>papermc-repo</id>
|
||||
<url>https://papermc.io/repo/repository/maven-public/</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>essentials-repo</id>
|
||||
<url>https://repo.essentialsx.net/releases</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>dmulloy2-repo</id>
|
||||
<url>https://repo.dmulloy2.net/nexus/repository/public/</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>jitpack.io</id>
|
||||
<url>https://jitpack.io</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>citizens-repo</id>
|
||||
<url>https://repo.citizensnpcs.co/</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>placeholderapi-repo</id>
|
||||
<url>https://repo.extendedclip.com/content/repositories/placeholderapi/</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>dynmap-repo</id>
|
||||
<url>https://repo.mikeprimm.com/</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>minecraft-libraries</id>
|
||||
<name>Minecraft Libraries</name>
|
||||
<url>https://libraries.minecraft.net</url>
|
||||
</repository>
|
||||
<repository>
|
||||
<id>mvdw-software-repo</id>
|
||||
<name>MVdW Public Repositories</name>
|
||||
<url>https://repo.mvdw-software.com/content/groups/public/</url>
|
||||
</repository>
|
||||
</repositories>
|
||||
<dependencies>
|
||||
<!--Paper API-->
|
||||
<dependency>
|
||||
<groupId>io.papermc.paper</groupId>
|
||||
<artifactId>paper-api</artifactId>
|
||||
<version>1.20.1-R0.1-SNAPSHOT</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<!--Lombok-->
|
||||
<dependency>
|
||||
<groupId>org.projectlombok</groupId>
|
||||
<artifactId>lombok</artifactId>
|
||||
<version>1.18.30</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<!--EssentialsX API-->
|
||||
<dependency>
|
||||
<groupId>net.essentialsx</groupId>
|
||||
<artifactId>EssentialsX</artifactId>
|
||||
<version>2.19.0</version>
|
||||
<scope>provided</scope>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>org.bstats</groupId>
|
||||
<artifactId>bstats-bukkit</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
<!--ProtocolLib-->
|
||||
<dependency>
|
||||
<groupId>com.comphenix.protocol</groupId>
|
||||
<artifactId>ProtocolLib</artifactId>
|
||||
<version>4.8.0</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<!--Vault API-->
|
||||
<dependency>
|
||||
<groupId>com.github.MilkBowl</groupId>
|
||||
<artifactId>VaultAPI</artifactId>
|
||||
<version>1.7.1</version>
|
||||
<scope>provided</scope>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>org.bukkit</groupId>
|
||||
<artifactId>bukkit</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>org.bukkit</groupId>
|
||||
<artifactId>craftbukkit</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
<!--Citizens API-->
|
||||
<dependency>
|
||||
<groupId>net.citizensnpcs</groupId>
|
||||
<artifactId>citizensapi</artifactId>
|
||||
<version>2.0.28-SNAPSHOT</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<!--TrailGUI-->
|
||||
<dependency>
|
||||
<groupId>com.github.SinnDevelopment</groupId>
|
||||
<artifactId>TrailGUI</artifactId>
|
||||
<version>37659dda03</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<!--Dynmap-->
|
||||
<dependency>
|
||||
<groupId>us.dynmap</groupId>
|
||||
<artifactId>dynmap-api</artifactId>
|
||||
<version>3.1</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<!--MVdWPlaceholderAPI-->
|
||||
<dependency>
|
||||
<groupId>be.maximvdw</groupId>
|
||||
<artifactId>MVdWPlaceholderAPI</artifactId>
|
||||
<version>3.1.1-SNAPSHOT</version>
|
||||
<scope>provided</scope>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>org.spigotmc</groupId>
|
||||
<artifactId>spigot</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
<!--PlaceholderAPI-->
|
||||
<dependency>
|
||||
<groupId>me.clip</groupId>
|
||||
<artifactId>placeholderapi</artifactId>
|
||||
<version>2.10.10</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<!--BrigadierAPI-->
|
||||
<dependency>
|
||||
<groupId>com.mojang</groupId>
|
||||
<artifactId>brigadier</artifactId>
|
||||
<version>1.0.18</version>
|
||||
</dependency>
|
||||
<!--OpenInv-->
|
||||
<dependency>
|
||||
<groupId>com.github.Jikoo</groupId>
|
||||
<artifactId>OpenInv</artifactId>
|
||||
<version>5.1.12</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</project>
|
||||
@@ -0,0 +1,13 @@
|
||||
rootProject.name = "Vanish-OG"
|
||||
|
||||
ProcessBuilder("sh", "bootstrap.sh").directory(rootDir).inheritIO().start().let {
|
||||
if (it.waitFor() != 0) throw GradleException("bootstrap.sh failed")
|
||||
}
|
||||
|
||||
file("libs")
|
||||
.listFiles()
|
||||
?.filter { it.isDirectory && !it.name.startsWith(".") }
|
||||
?.forEach { dir ->
|
||||
include(":libs:${dir.name}")
|
||||
project(":libs:${dir.name}").projectDir = dir
|
||||
}
|
||||
@@ -20,34 +20,49 @@ public class PlayerHideEvent extends PlayerEvent implements Cancellable {
|
||||
private boolean isCancelled = false;
|
||||
|
||||
public PlayerHideEvent(Player p, boolean silent) {
|
||||
|
||||
super(p);
|
||||
this.silent = silent;
|
||||
|
||||
}
|
||||
|
||||
public static HandlerList getHandlerList() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
public boolean isSilent() {
|
||||
|
||||
return silent;
|
||||
|
||||
}
|
||||
|
||||
public void setSilent(boolean silent) {
|
||||
|
||||
this.silent = silent;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isCancelled() {
|
||||
|
||||
return isCancelled;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCancelled(boolean cancel) {
|
||||
|
||||
isCancelled = cancel;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public HandlerList getHandlers() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -20,34 +20,49 @@ public class PlayerShowEvent extends PlayerEvent implements Cancellable {
|
||||
private boolean isCancelled = false;
|
||||
|
||||
public PlayerShowEvent(Player p, boolean silent) {
|
||||
|
||||
super(p);
|
||||
this.silent = silent;
|
||||
|
||||
}
|
||||
|
||||
public static HandlerList getHandlerList() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
public boolean isSilent() {
|
||||
|
||||
return silent;
|
||||
|
||||
}
|
||||
|
||||
public void setSilent(boolean silent) {
|
||||
|
||||
this.silent = silent;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isCancelled() {
|
||||
|
||||
return isCancelled;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCancelled(boolean cancel) {
|
||||
|
||||
isCancelled = cancel;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public HandlerList getHandlers() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -25,19 +25,25 @@ public class PlayerVanishStateChangeEvent extends Event implements Cancellable {
|
||||
private boolean isCancelled = false;
|
||||
|
||||
public PlayerVanishStateChangeEvent(UUID uuid, String name, boolean vanishing, String cause) {
|
||||
|
||||
this.vanishing = vanishing;
|
||||
this.uuid = uuid;
|
||||
this.name = name;
|
||||
this.cause = cause;
|
||||
|
||||
}
|
||||
|
||||
public static HandlerList getHandlerList() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isCancelled() {
|
||||
|
||||
return isCancelled;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -45,41 +51,55 @@ public class PlayerVanishStateChangeEvent extends Event implements Cancellable {
|
||||
*/
|
||||
@Override
|
||||
public void setCancelled(boolean cancel) {
|
||||
|
||||
isCancelled = cancel;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return TRUE if the player is vanishing, FALSE if the player is reappearing
|
||||
*/
|
||||
public boolean isVanishing() {
|
||||
|
||||
return vanishing;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The name of the player who is vanishing/reappearing
|
||||
*/
|
||||
public String getName() {
|
||||
|
||||
return name;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The UUID of the player who is vanishing/reappearing
|
||||
*/
|
||||
public UUID getUUID() {
|
||||
|
||||
return uuid;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The name of the command sender who caused the vanish state change or null if the cause is
|
||||
* either not specified or it's SuperVanish itself, please note that if this returns 'CONSOLE' then it's
|
||||
* the console which caused this state change
|
||||
* @return The name of the command sender who caused the vanish state change or
|
||||
* null if the cause is either not specified or it's SuperVanish itself,
|
||||
* please note that if this returns 'CONSOLE' then it's the console
|
||||
* which caused this state change
|
||||
*/
|
||||
public String getCause() {
|
||||
|
||||
return cause;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public HandlerList getHandlers() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,20 +18,29 @@ public class PostPlayerHideEvent extends PlayerEvent {
|
||||
private final boolean silent;
|
||||
|
||||
public PostPlayerHideEvent(Player p, boolean silent) {
|
||||
|
||||
super(p);
|
||||
this.silent = silent;
|
||||
|
||||
}
|
||||
|
||||
public static HandlerList getHandlerList() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
public boolean isSilent() {
|
||||
|
||||
return silent;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public HandlerList getHandlers() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,20 +18,29 @@ public class PostPlayerShowEvent extends PlayerEvent {
|
||||
private final boolean silent;
|
||||
|
||||
public PostPlayerShowEvent(Player p, boolean silent) {
|
||||
|
||||
super(p);
|
||||
this.silent = silent;
|
||||
|
||||
}
|
||||
|
||||
public static HandlerList getHandlerList() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
public boolean isSilent() {
|
||||
|
||||
return silent;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public HandlerList getHandlers() {
|
||||
|
||||
return handlers;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -11,10 +11,12 @@ package de.myzelyam.api.vanish;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.utils.Validation;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.configuration.file.FileConfiguration;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.concurrent.CompletableFuture;
|
||||
import java.util.List;
|
||||
import java.util.UUID;
|
||||
|
||||
@@ -30,38 +32,48 @@ public class VanishAPI {
|
||||
* @return A collection of the UUIDs of all online vanished players
|
||||
*/
|
||||
public static List<UUID> getInvisiblePlayers() {
|
||||
|
||||
return new ArrayList<>(PLUGIN.getVanishStateMgr().getOnlineVanishedPlayers());
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return A collection of the UUIDs of all vanished players, both online and offline players
|
||||
* @return A collection of the UUIDs of all vanished players, both online and
|
||||
* offline players
|
||||
*/
|
||||
public static List<UUID> getAllInvisiblePlayers() {
|
||||
|
||||
return new ArrayList<>(PLUGIN.getVanishStateMgr().getVanishedPlayers());
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Player must be online for this to return true if MySQL is enabled
|
||||
* Asynchronously checks if an online player is currently vanished.
|
||||
*
|
||||
* @param p - the player.
|
||||
* @return TRUE if the player is invisible, FALSE otherwise.
|
||||
* @return A future that completes with TRUE if the player is vanished, FALSE
|
||||
* otherwise.
|
||||
*/
|
||||
public static boolean isInvisible(Player p) {
|
||||
public static CompletableFuture<Boolean> isPlayerVanished(Player p) {
|
||||
|
||||
Validation.checkNotNull("Player cannot be null!", p);
|
||||
return PLUGIN.getVanishStateMgr().isVanished(p.getUniqueId());
|
||||
return isUUIDVanished(p.getUniqueId());
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if a player is invisible, online or not
|
||||
* <p/>
|
||||
* Deprecated: Will cause minor lag if mysql is enabled, use asynchronously or sparingly
|
||||
* Asynchronously checks if a player is vanished, online or offline.
|
||||
*
|
||||
* @param uuid - the player's UUID.
|
||||
* @return TRUE if the player is invisible, FALSE otherwise.
|
||||
* @return A future that completes with TRUE if the player is vanished, FALSE
|
||||
* otherwise.
|
||||
*/
|
||||
public static boolean isInvisibleOffline(UUID uuid) {
|
||||
public static CompletableFuture<Boolean> isUUIDVanished(UUID uuid) {
|
||||
|
||||
Validation.checkNotNull("UUID cannot be null!", uuid);
|
||||
return PLUGIN.getVanishStateMgr().isVanished(uuid);
|
||||
return CompletableFuture.supplyAsync(() -> PLUGIN.getVanishStateMgr().isVanished(uuid),
|
||||
runnable -> Bukkit.getScheduler().runTaskAsynchronously(PLUGIN, runnable));
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -70,8 +82,10 @@ public class VanishAPI {
|
||||
* @param p - the player.
|
||||
*/
|
||||
public static void hidePlayer(Player p) {
|
||||
|
||||
Validation.checkNotNull("Player cannot be null!", p);
|
||||
PLUGIN.getVisibilityChanger().hidePlayer(p);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -80,8 +94,10 @@ public class VanishAPI {
|
||||
* @param p - the player.
|
||||
*/
|
||||
public static void showPlayer(Player p) {
|
||||
|
||||
Validation.checkNotNull("Player cannot be null!", p);
|
||||
PLUGIN.getVisibilityChanger().showPlayer(p);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -89,33 +105,49 @@ public class VanishAPI {
|
||||
*
|
||||
* @param viewer - the viewer
|
||||
* @param viewed - the viewed player
|
||||
* @return TRUE if viewed is not vanished or viewer has the permission to see viewed
|
||||
* @return TRUE if viewed is not vanished or viewer has the permission to see
|
||||
* viewed
|
||||
*/
|
||||
public static boolean canSee(Player viewer, Player viewed) {
|
||||
|
||||
return PLUGIN.canSee(viewer, viewed);
|
||||
|
||||
}
|
||||
|
||||
public static FileConfiguration getConfiguration() {
|
||||
|
||||
return PLUGIN.getSettings();
|
||||
|
||||
}
|
||||
|
||||
public static FileConfiguration getMessages() {
|
||||
|
||||
return PLUGIN.getMessages();
|
||||
|
||||
}
|
||||
|
||||
public static FileConfiguration getPlayerData() {
|
||||
|
||||
return PLUGIN.getPlayerData();
|
||||
|
||||
}
|
||||
|
||||
public static void reloadConfig() {
|
||||
|
||||
PLUGIN.reload();
|
||||
|
||||
}
|
||||
|
||||
public static SuperVanish getPlugin() {
|
||||
|
||||
return PLUGIN;
|
||||
|
||||
}
|
||||
|
||||
public static void setPlugin(SuperVanish plugin) {
|
||||
|
||||
VanishAPI.PLUGIN = plugin;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,48 +18,64 @@ public class LayeredPermissionChecker {
|
||||
private final FileConfiguration settings;
|
||||
|
||||
public LayeredPermissionChecker(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
settings = plugin.getSettings();
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return TRUE if sender has *permission* to use /sv on, else FALSE; TRUE doesn't mean that sender can
|
||||
* actually use /sv on
|
||||
* @return TRUE if sender has *permission* to use /sv on, else FALSE; TRUE
|
||||
* doesn't mean that sender can actually use /sv on
|
||||
*/
|
||||
public boolean hasPermissionToVanish(CommandSender sender) {
|
||||
if (settings.getBoolean(
|
||||
"IndicationFeatures.LayeredPermissions.LayeredSeeAndUsePermissions", false)) {
|
||||
if (sender.hasPermission("sv.use")) return true;
|
||||
|
||||
if (settings.getBoolean("IndicationFeatures.LayeredPermissions.LayeredSeeAndUsePermissions", false)) {
|
||||
|
||||
if (sender.hasPermission("sv.use"))
|
||||
return true;
|
||||
int permissionLevel;
|
||||
if (sender instanceof Player)
|
||||
permissionLevel = plugin.getVanishPlayer((Player) sender).getUsePermissionLevel();
|
||||
else permissionLevel = getLayeredPermissionLevel(sender, "use");
|
||||
else
|
||||
permissionLevel = getLayeredPermissionLevel(sender, "use");
|
||||
return permissionLevel > 0 && sender.hasPermission("sv.use.level" + permissionLevel);
|
||||
} else return sender.hasPermission("sv.use");
|
||||
|
||||
} else
|
||||
return sender.hasPermission("sv.use");
|
||||
|
||||
}
|
||||
|
||||
public boolean hasPermissionToSee(Player viewer, Player viewed) {
|
||||
|
||||
if (viewer == null)
|
||||
throw new IllegalArgumentException("viewer cannot be null");
|
||||
if (viewer == viewed) return true;
|
||||
if (settings.getBoolean(
|
||||
"IndicationFeatures.LayeredPermissions.LayeredSeeAndUsePermissions", false)) {
|
||||
if (viewer == viewed)
|
||||
return true;
|
||||
if (settings.getBoolean("IndicationFeatures.LayeredPermissions.LayeredSeeAndUsePermissions", false)) {
|
||||
|
||||
VanishPlayer vanishViewer = plugin.getVanishPlayer(viewer);
|
||||
VanishPlayer vanishViewed = plugin.getVanishPlayer(viewed);
|
||||
int viewerLevel = vanishViewer.getSeePermissionLevel();
|
||||
if (viewerLevel == 0) return false;
|
||||
if (viewerLevel == 0)
|
||||
return false;
|
||||
int viewedLevel = Math.max(1, vanishViewed.getUsePermissionLevel());
|
||||
return viewerLevel >= viewedLevel;
|
||||
|
||||
} else {
|
||||
|
||||
boolean enableSeePermission = settings
|
||||
.getBoolean("IndicationFeatures.LayeredPermissions.EnableSeePermission", true);
|
||||
return enableSeePermission && viewer.hasPermission("sv.see");
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public int getLayeredPermissionLevel(CommandSender sender, String permission) {
|
||||
boolean enableSeePermission = settings
|
||||
.getBoolean("IndicationFeatures.LayeredPermissions.EnableSeePermission", true);
|
||||
|
||||
boolean enableSeePermission = settings.getBoolean("IndicationFeatures.LayeredPermissions.EnableSeePermission",
|
||||
true);
|
||||
if (!enableSeePermission && permission.equalsIgnoreCase("see"))
|
||||
return 0;
|
||||
int maxLevel = settings.getInt("IndicationFeatures.LayeredPermissions.MaxLevel", 100);
|
||||
@@ -68,5 +84,7 @@ public class LayeredPermissionChecker {
|
||||
if (sender.hasPermission("sv." + permission + ".level" + i))
|
||||
level = i;
|
||||
return level;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,169 +8,297 @@
|
||||
|
||||
package de.myzelyam.supervanish;
|
||||
|
||||
import com.earth2me.essentials.Essentials;
|
||||
import com.earth2me.essentials.User;
|
||||
|
||||
import de.myzelyam.supervanish.hooks.PlaceholderAPIHook;
|
||||
import de.myzelyam.supervanish.utils.Validation;
|
||||
|
||||
import net.milkbowl.vault.chat.Chat;
|
||||
import net.milkbowl.vault.permission.Permission;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.OfflinePlayer;
|
||||
import org.bukkit.command.CommandSender;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.plugin.RegisteredServiceProvider;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
import com.earth2me.essentials.Essentials;
|
||||
import com.earth2me.essentials.User;
|
||||
|
||||
import be.maximvdw.placeholderapi.PlaceholderAPI;
|
||||
import de.myzelyam.supervanish.utils.Validation;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer;
|
||||
import net.luckperms.api.LuckPerms;
|
||||
import net.luckperms.api.LuckPermsProvider;
|
||||
import net.luckperms.api.cacheddata.CachedMetaData;
|
||||
import net.trueog.utilitiesog.UtilitiesOG;
|
||||
|
||||
public class PlaceholderConverter {
|
||||
|
||||
private final SuperVanish plugin;
|
||||
private static final LegacyComponentSerializer LEGACY_SERIALIZER = LegacyComponentSerializer.legacySection();
|
||||
|
||||
public PlaceholderConverter(SuperVanish plugin) {
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
public String replacePlaceholders(String msg, Object... additionalPlayerInfo) {
|
||||
Validation.checkIsTrue("Failed to replace variables (Illegal arguments)",
|
||||
msg != null, additionalPlayerInfo != null);
|
||||
//noinspection ConstantConditions
|
||||
Validation.checkIsTrue(additionalPlayerInfo.length > 0);
|
||||
// check vararg
|
||||
final List<Object> additionalPlayerInfoList = Arrays
|
||||
.asList(additionalPlayerInfo);
|
||||
Object unspecifiedPlayer = additionalPlayerInfoList.get(0);
|
||||
String unspecifiedOtherPlayersName = null;
|
||||
if (additionalPlayerInfoList.size() > 1
|
||||
&& (additionalPlayerInfoList.get(1) instanceof String
|
||||
|| additionalPlayerInfoList.get(1) instanceof Player)) {
|
||||
unspecifiedOtherPlayersName = (String) (additionalPlayerInfoList
|
||||
.get(1) instanceof Player
|
||||
? ((Player) additionalPlayerInfoList.get(1)).getName()
|
||||
: additionalPlayerInfoList.get(1));
|
||||
|
||||
return LEGACY_SERIALIZER.serialize(expandPlaceholders(msg, additionalPlayerInfo));
|
||||
|
||||
}
|
||||
//noinspection ConstantConditions
|
||||
msg = msg.replace("\\n", "\n");
|
||||
// replace sender specific variables
|
||||
replaceVariables:
|
||||
{
|
||||
if (unspecifiedPlayer instanceof OfflinePlayer
|
||||
&& !(unspecifiedPlayer instanceof Player)) {
|
||||
// offline player
|
||||
OfflinePlayer specifiedPlayer = (OfflinePlayer) unspecifiedPlayer;
|
||||
// MVdWPlaceholderAPI
|
||||
if (Bukkit.getPluginManager().isPluginEnabled("MVdWPlaceholderAPI")
|
||||
&& plugin.getSettings().getBoolean("HookOptions.EnableMVdWPlaceholderAPIHook", true)) {
|
||||
String replaced = PlaceholderAPI.replacePlaceholders(specifiedPlayer, msg);
|
||||
msg = replaced == null ? msg : replaced;
|
||||
|
||||
public Component expandPlaceholders(String msg, Object... additionalPlayerInfo) {
|
||||
|
||||
return expandPlaceholders(null, msg, additionalPlayerInfo);
|
||||
|
||||
}
|
||||
// replace essentials nick names
|
||||
if (Bukkit.getPluginManager()
|
||||
.getPlugin("Essentials") != null) {
|
||||
msg = msg.replace("%nick%", specifiedPlayer.getName());
|
||||
|
||||
public Component expandPlaceholders(CommandSender recipient, String msg, Object... additionalPlayerInfo) {
|
||||
|
||||
Validation.checkNotNull("Failed to replace variables (Illegal arguments)", msg, additionalPlayerInfo);
|
||||
final PlaceholderContext context = parseContext(additionalPlayerInfo);
|
||||
final String preparedMessage = applyInlinePlaceholders(msg.replace("\\n", "\n"), context);
|
||||
|
||||
if (recipient instanceof Player player) {
|
||||
|
||||
if (context.primaryPlayer != null) {
|
||||
|
||||
return UtilitiesOG.trueogExpand(preparedMessage, player, context.primaryPlayer);
|
||||
|
||||
}
|
||||
// replace general variables
|
||||
msg = msg.replace("%d%", specifiedPlayer.getName())
|
||||
.replace("%p%", specifiedPlayer.getName())
|
||||
.replace("%tab%", specifiedPlayer.getName());
|
||||
// replace other player's name if possible
|
||||
msg = msg.replace("%other%", unspecifiedOtherPlayersName != null
|
||||
? unspecifiedOtherPlayersName : "UNKNOWN");
|
||||
break replaceVariables;
|
||||
|
||||
return UtilitiesOG.trueogExpand(preparedMessage, player);
|
||||
|
||||
}
|
||||
if (unspecifiedPlayer instanceof Player) {
|
||||
// player
|
||||
Player specifiedPlayer = (Player) unspecifiedPlayer;
|
||||
// PlaceholderAPI
|
||||
if (Bukkit.getPluginManager().isPluginEnabled("PlaceholderAPI")
|
||||
&& plugin.getSettings().getBoolean("HookOptions.EnablePlaceholderAPIHook", true)) {
|
||||
String replaced = PlaceholderAPIHook.translatePlaceholders(msg, specifiedPlayer);
|
||||
//noinspection ConstantConditions
|
||||
msg = replaced == null ? msg : replaced;
|
||||
|
||||
if (context.primaryPlayer != null) {
|
||||
|
||||
return UtilitiesOG.trueogExpand(preparedMessage, context.primaryPlayer);
|
||||
|
||||
}
|
||||
// MVdWPlaceholderAPI
|
||||
if (Bukkit.getPluginManager().isPluginEnabled("MVdWPlaceholderAPI")
|
||||
&& plugin.getSettings().getBoolean("HookOptions.EnableMVdWPlaceholderAPIHook", true)) {
|
||||
String replaced = PlaceholderAPI.replacePlaceholders(specifiedPlayer, msg);
|
||||
msg = replaced == null ? msg : replaced;
|
||||
|
||||
return UtilitiesOG.trueogExpand(preparedMessage);
|
||||
|
||||
}
|
||||
// replace essentials nick names
|
||||
if (Bukkit.getPluginManager().getPlugin("Essentials") != null) {
|
||||
Essentials ess = (Essentials) Bukkit.getServer()
|
||||
.getPluginManager().getPlugin("Essentials");
|
||||
User u = ess.getUser(specifiedPlayer);
|
||||
if (u != null)
|
||||
if (u.getNickname() != null)
|
||||
msg = msg.replace("%nick%", u.getNickname());
|
||||
|
||||
public static MessagePlaceholder placeholder(String name, Object value) {
|
||||
|
||||
return new MessagePlaceholder(name, value == null ? "" : String.valueOf(value));
|
||||
|
||||
}
|
||||
// replace vault info
|
||||
if (Bukkit.getPluginManager().getPlugin("Vault") != null) {
|
||||
RegisteredServiceProvider<Permission> permService = plugin.getServer()
|
||||
.getServicesManager().getRegistration(Permission.class);
|
||||
RegisteredServiceProvider<Chat> chatService = plugin.getServer()
|
||||
.getServicesManager().getRegistration(Chat.class);
|
||||
Permission permAPI = permService != null ? permService.getProvider() : null;
|
||||
Chat chatAPI = chatService != null ? chatService.getProvider() : null;
|
||||
|
||||
private PlaceholderContext parseContext(Object... additionalPlayerInfo) {
|
||||
|
||||
final PlaceholderContext context = new PlaceholderContext();
|
||||
if (additionalPlayerInfo == null) {
|
||||
|
||||
return context;
|
||||
|
||||
}
|
||||
|
||||
for (Object entry : additionalPlayerInfo) {
|
||||
|
||||
if (entry instanceof MessagePlaceholder messagePlaceholder) {
|
||||
|
||||
context.inlinePlaceholders.add(messagePlaceholder);
|
||||
continue;
|
||||
|
||||
}
|
||||
|
||||
if (context.primaryObject == null) {
|
||||
|
||||
context.primaryObject = entry;
|
||||
if (entry instanceof Player player) {
|
||||
|
||||
context.primaryPlayer = player;
|
||||
|
||||
}
|
||||
|
||||
continue;
|
||||
|
||||
}
|
||||
|
||||
if (context.otherName == null && (entry instanceof Player || entry instanceof String)) {
|
||||
|
||||
if (entry instanceof Player player) {
|
||||
|
||||
context.otherName = player.getName();
|
||||
|
||||
} else {
|
||||
|
||||
context.otherName = String.valueOf(entry);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return context;
|
||||
|
||||
}
|
||||
|
||||
private String applyInlinePlaceholders(String message, PlaceholderContext context) {
|
||||
|
||||
message = replaceTag(message, "sv_player_name", getPrimaryName(context.primaryObject));
|
||||
message = replaceTag(message, "sv_player_display_name", getPrimaryDisplayName(context.primaryObject));
|
||||
message = replaceTag(message, "sv_player_tab_name", getPrimaryTabName(context.primaryObject));
|
||||
message = replaceTag(message, "sv_player_prefix", getPrimaryPrefix(context.primaryObject));
|
||||
message = replaceTag(message, "sv_player_suffix", getPrimarySuffix(context.primaryObject));
|
||||
message = replaceTag(message, "sv_player_group", getPrimaryGroup(context.primaryObject));
|
||||
message = replaceTag(message, "sv_player_nick", getPrimaryNick(context.primaryObject));
|
||||
message = replaceTag(message, "sv_other_name", context.otherName != null ? context.otherName : "UNKNOWN");
|
||||
|
||||
for (MessagePlaceholder inlinePlaceholder : context.inlinePlaceholders) {
|
||||
|
||||
message = replaceTag(message, inlinePlaceholder.name(), inlinePlaceholder.value());
|
||||
|
||||
}
|
||||
|
||||
return message;
|
||||
|
||||
}
|
||||
|
||||
private String getPrimaryName(Object primaryObject) {
|
||||
|
||||
if (primaryObject instanceof OfflinePlayer offlinePlayer) {
|
||||
|
||||
return offlinePlayer.getName();
|
||||
|
||||
}
|
||||
|
||||
if (primaryObject instanceof CommandSender) {
|
||||
|
||||
return "Console";
|
||||
|
||||
}
|
||||
|
||||
return "";
|
||||
|
||||
}
|
||||
|
||||
private String getPrimaryDisplayName(Object primaryObject) {
|
||||
|
||||
if (primaryObject instanceof Player player) {
|
||||
|
||||
return LEGACY_SERIALIZER.serialize(player.displayName());
|
||||
|
||||
}
|
||||
|
||||
return getPrimaryName(primaryObject);
|
||||
|
||||
}
|
||||
|
||||
private String getPrimaryTabName(Object primaryObject) {
|
||||
|
||||
if (primaryObject instanceof Player player) {
|
||||
|
||||
return LEGACY_SERIALIZER.serialize(player.playerListName());
|
||||
|
||||
}
|
||||
|
||||
return getPrimaryName(primaryObject);
|
||||
|
||||
}
|
||||
|
||||
private String getPrimaryNick(Object primaryObject) {
|
||||
|
||||
if (!(primaryObject instanceof Player player) || Bukkit.getPluginManager().getPlugin("Essentials") == null) {
|
||||
|
||||
return getPrimaryName(primaryObject);
|
||||
|
||||
}
|
||||
|
||||
final Essentials essentials = (Essentials) Bukkit.getServer().getPluginManager().getPlugin("Essentials");
|
||||
final User user = essentials.getUser(player);
|
||||
if (user == null || user.getNickname() == null) {
|
||||
|
||||
return player.getName();
|
||||
|
||||
}
|
||||
|
||||
return user.getNickname();
|
||||
|
||||
}
|
||||
|
||||
private String getPrimaryGroup(Object primaryObject) {
|
||||
|
||||
if (!(primaryObject instanceof OfflinePlayer offlinePlayer)) {
|
||||
|
||||
return "";
|
||||
|
||||
}
|
||||
|
||||
if (Bukkit.getPluginManager().getPlugin("LuckPerms") == null) {
|
||||
|
||||
return "";
|
||||
|
||||
}
|
||||
|
||||
try {
|
||||
if (permAPI != null) {
|
||||
String group = permAPI.getPrimaryGroup(specifiedPlayer);
|
||||
if (group != null)
|
||||
msg = msg.replace("%group%", group);
|
||||
}
|
||||
if (chatAPI != null) {
|
||||
String prefix = chatAPI.getPlayerPrefix(specifiedPlayer);
|
||||
String suffix = chatAPI.getPlayerSuffix(specifiedPlayer);
|
||||
if (prefix != null) {
|
||||
msg = msg.replace("%prefix%", prefix);
|
||||
}
|
||||
if (suffix != null) {
|
||||
msg = msg.replace("%suffix%", suffix);
|
||||
}
|
||||
}
|
||||
} catch (UnsupportedOperationException ignored) {
|
||||
}
|
||||
}
|
||||
// replace general variables
|
||||
msg = msg.replace("%d%", "" + specifiedPlayer.getDisplayName())
|
||||
.replace("%p%", "" + specifiedPlayer.getName())
|
||||
.replace("%tab%",
|
||||
"" + specifiedPlayer.getPlayerListName());
|
||||
// replace other player's name if possible
|
||||
msg = msg.replace("%other%", unspecifiedOtherPlayersName != null
|
||||
? unspecifiedOtherPlayersName : "UNKNOWN");
|
||||
|
||||
break replaceVariables;
|
||||
}
|
||||
if (unspecifiedPlayer instanceof CommandSender) {
|
||||
// console
|
||||
// replace general variables
|
||||
msg = msg.replace("%d%", "Console").replace("%p%", "Console")
|
||||
.replace("%tab%", "Console");
|
||||
// replace other player's name if possible
|
||||
msg = msg.replace("%other%", unspecifiedOtherPlayersName != null
|
||||
? unspecifiedOtherPlayersName : "UNKNOWN");
|
||||
}
|
||||
}
|
||||
// convert color codes
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(16)) {
|
||||
Pattern pattern = Pattern.compile("\\{?&?#[a-fA-F0-9]{6}\\}?");
|
||||
Matcher matcher = pattern.matcher(msg);
|
||||
final LuckPerms luckPerms = LuckPermsProvider.get();
|
||||
final net.luckperms.api.model.user.User user = luckPerms.getUserManager()
|
||||
.getUser(offlinePlayer.getUniqueId());
|
||||
return user == null ? "" : user.getPrimaryGroup();
|
||||
|
||||
} catch (IllegalStateException ignored) {
|
||||
|
||||
return "";
|
||||
|
||||
while (matcher.find()) {
|
||||
String color = msg.substring(matcher.start(), matcher.end());
|
||||
msg = msg.replace(color, net.md_5.bungee.api.ChatColor.of(color.replace("&", "").replace("{", "").replace("}", "")) + "");
|
||||
matcher = pattern.matcher(msg);
|
||||
}
|
||||
|
||||
}
|
||||
msg = ChatColor.translateAlternateColorCodes('&', msg);
|
||||
return msg;
|
||||
|
||||
private String getPrimaryPrefix(Object primaryObject) {
|
||||
|
||||
final CachedMetaData metaData = getPrimaryMetaData(primaryObject);
|
||||
return metaData == null || metaData.getPrefix() == null ? "" : metaData.getPrefix();
|
||||
|
||||
}
|
||||
|
||||
private String getPrimarySuffix(Object primaryObject) {
|
||||
|
||||
final CachedMetaData metaData = getPrimaryMetaData(primaryObject);
|
||||
return metaData == null || metaData.getSuffix() == null ? "" : metaData.getSuffix();
|
||||
|
||||
}
|
||||
|
||||
private CachedMetaData getPrimaryMetaData(Object primaryObject) {
|
||||
|
||||
if (!(primaryObject instanceof OfflinePlayer offlinePlayer)
|
||||
|| Bukkit.getPluginManager().getPlugin("LuckPerms") == null)
|
||||
{
|
||||
|
||||
return null;
|
||||
|
||||
}
|
||||
|
||||
try {
|
||||
|
||||
final LuckPerms luckPerms = LuckPermsProvider.get();
|
||||
final net.luckperms.api.model.user.User user = luckPerms.getUserManager()
|
||||
.getUser(offlinePlayer.getUniqueId());
|
||||
return user == null ? null : user.getCachedData().getMetaData();
|
||||
|
||||
} catch (IllegalStateException ignored) {
|
||||
|
||||
return null;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private String replaceTag(String message, String tagName, String value) {
|
||||
|
||||
return message.replace("<" + tagName + ">", value == null ? "" : value);
|
||||
|
||||
}
|
||||
|
||||
public record MessagePlaceholder(String name, String value) {
|
||||
}
|
||||
|
||||
private static final class PlaceholderContext {
|
||||
|
||||
private Object primaryObject;
|
||||
private Player primaryPlayer;
|
||||
private String otherName;
|
||||
private final List<MessagePlaceholder> inlinePlaceholders = new ArrayList<>();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,22 +8,12 @@
|
||||
|
||||
package de.myzelyam.supervanish;
|
||||
|
||||
import com.comphenix.protocol.ProtocolLibrary;
|
||||
import de.myzelyam.api.vanish.VanishAPI;
|
||||
import de.myzelyam.supervanish.commands.VanishCommand;
|
||||
import de.myzelyam.supervanish.config.ConfigMgr;
|
||||
import de.myzelyam.supervanish.listeners.*;
|
||||
import de.myzelyam.supervanish.features.FeatureMgr;
|
||||
import de.myzelyam.supervanish.hooks.PluginHookMgr;
|
||||
import de.myzelyam.supervanish.net.UpdateNotifier;
|
||||
import de.myzelyam.supervanish.utils.ExceptionLogger;
|
||||
import de.myzelyam.supervanish.utils.VersionUtil;
|
||||
import de.myzelyam.supervanish.visibility.ActionBarMgr;
|
||||
import de.myzelyam.supervanish.visibility.FileVanishStateMgr;
|
||||
import de.myzelyam.supervanish.visibility.ServerListPacketListener;
|
||||
import de.myzelyam.supervanish.visibility.VisibilityChanger;
|
||||
import de.myzelyam.supervanish.visibility.hiders.PreventionHider;
|
||||
import lombok.Getter;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.command.Command;
|
||||
import org.bukkit.command.CommandSender;
|
||||
@@ -37,58 +27,70 @@ import org.bukkit.event.player.PlayerQuitEvent;
|
||||
import org.bukkit.plugin.PluginManager;
|
||||
import org.bukkit.plugin.java.JavaPlugin;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.logging.Level;
|
||||
import com.comphenix.protocol.ProtocolLibrary;
|
||||
|
||||
import de.myzelyam.api.vanish.VanishAPI;
|
||||
import de.myzelyam.supervanish.commands.VanishCommand;
|
||||
import de.myzelyam.supervanish.config.ConfigMgr;
|
||||
import de.myzelyam.supervanish.features.FeatureMgr;
|
||||
import de.myzelyam.supervanish.hooks.PluginHookMgr;
|
||||
import de.myzelyam.supervanish.listeners.GeneralListener;
|
||||
import de.myzelyam.supervanish.listeners.JoinListener;
|
||||
import de.myzelyam.supervanish.listeners.LoginListener;
|
||||
import de.myzelyam.supervanish.listeners.PlayerBlockModifyListener;
|
||||
import de.myzelyam.supervanish.listeners.QuitListener;
|
||||
import de.myzelyam.supervanish.listeners.TabCompleteListener;
|
||||
import de.myzelyam.supervanish.listeners.WorldChangeListener;
|
||||
import de.myzelyam.supervanish.utils.ExceptionLogger;
|
||||
import de.myzelyam.supervanish.utils.VersionUtil;
|
||||
import de.myzelyam.supervanish.visibility.ActionBarMgr;
|
||||
import de.myzelyam.supervanish.visibility.FileVanishStateMgr;
|
||||
import de.myzelyam.supervanish.visibility.ServerListPacketListener;
|
||||
import de.myzelyam.supervanish.visibility.VisibilityChanger;
|
||||
import de.myzelyam.supervanish.visibility.hiders.PreventionHider;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer;
|
||||
import net.trueog.utilitiesog.UtilitiesOG;
|
||||
|
||||
public class SuperVanish extends JavaPlugin implements SuperVanishPlugin {
|
||||
|
||||
public static final String[] NON_REQUIRED_SETTINGS_UPDATES = {"6.0.0", "6.0.1", "6.0.2", "6.0.3",
|
||||
"6.0.4", "6.0.5", "6.1.0", "6.1.1", "6.1.2", "6.1.3", "6.1.4", "6.1.5", "6.1.6", "6.1.7",
|
||||
"6.1.8", "6.2.0", "6.2.1", "6.2.2", "6.2.3", "6.2.4", "6.2.5", "6.2.6", "6.2.7", "6.2.8",
|
||||
"6.2.9", "6.2.10", "6.2.11", "6.2.12", "6.2.13", "6.2.14", "6.2.15", "6.2.16", "6.2.17",
|
||||
"6.2.18", "6.2.19", "6.2.20"},
|
||||
NON_REQUIRED_MESSAGES_UPDATES = {"6.0.0", "6.0.1", "6.0.2", "6.0.3", "6.0.4", "6.0.5", "6.1.0",
|
||||
"6.1.1", "6.1.2", "6.1.3", "6.1.4", "6.1.5", "6.1.6", "6.1.7", "6.1.8", "6.2.0", "6.2.1",
|
||||
"6.2.2", "6.2.3", "6.2.4", "6.2.5", "6.2.6", "6.2.7", "6.2.8", "6.2.9", "6.2.10", "6.2.11",
|
||||
"6.2.12", "6.2.13", "6.2.14", "6.2.15", "6.2.16", "6.2.17", "6.2.18", "6.2.19", "6.2.20"};
|
||||
public static final String[] NON_REQUIRED_SETTINGS_UPDATES = { "6.0.0", "6.0.1", "6.0.2", "6.0.3", "6.0.4", "6.0.5",
|
||||
"6.1.0", "6.1.1", "6.1.2", "6.1.3", "6.1.4", "6.1.5", "6.1.6", "6.1.7", "6.1.8", "6.2.0", "6.2.1", "6.2.2",
|
||||
"6.2.3", "6.2.4", "6.2.5", "6.2.6", "6.2.7", "6.2.8", "6.2.9", "6.2.10", "6.2.11", "6.2.12", "6.2.13",
|
||||
"6.2.14", "6.2.15", "6.2.16", "6.2.17", "6.2.18", "6.2.19", "6.2.20" };
|
||||
|
||||
public static final String[] NON_REQUIRED_MESSAGES_UPDATES = { "6.0.0", "6.0.1", "6.0.2", "6.0.3", "6.0.4", "6.0.5",
|
||||
"6.1.0", "6.1.1", "6.1.2", "6.1.3", "6.1.4", "6.1.5", "6.1.6", "6.1.7", "6.1.8", "6.2.0", "6.2.1", "6.2.2",
|
||||
"6.2.3", "6.2.4", "6.2.5", "6.2.6", "6.2.7", "6.2.8", "6.2.9", "6.2.10", "6.2.11", "6.2.12", "6.2.13",
|
||||
"6.2.14", "6.2.15", "6.2.16", "6.2.17", "6.2.18", "6.2.19", "6.2.20" };
|
||||
|
||||
@Getter
|
||||
private boolean useProtocolLib;
|
||||
@Getter
|
||||
private ActionBarMgr actionBarMgr;
|
||||
@Getter
|
||||
private FileVanishStateMgr vanishStateMgr;
|
||||
@Getter
|
||||
private VersionUtil versionUtil;
|
||||
@Getter
|
||||
private ConfigMgr configMgr;
|
||||
@Getter
|
||||
private FeatureMgr featureMgr;
|
||||
@Getter
|
||||
private PlaceholderConverter placeholderConverter;
|
||||
@Getter
|
||||
private VanishCommand command;
|
||||
@Getter
|
||||
private VisibilityChanger visibilityChanger;
|
||||
@Getter
|
||||
private UpdateNotifier updateNotifier;
|
||||
@Getter
|
||||
private LoginListener loginListener;
|
||||
@Getter
|
||||
private LayeredPermissionChecker layeredPermissionChecker;
|
||||
@Getter
|
||||
private PluginHookMgr pluginHookMgr;
|
||||
private Set<VanishPlayer> vanishPlayers = new HashSet<>();
|
||||
private final Set<VanishPlayer> vanishPlayers = new HashSet<>();
|
||||
|
||||
@Override
|
||||
public void onEnable() {
|
||||
|
||||
try {
|
||||
|
||||
useProtocolLib = getServer().getPluginManager().isPluginEnabled("ProtocolLib");
|
||||
if (!useProtocolLib) log(Level.INFO,
|
||||
"Please install ProtocolLib to be able to use all SuperVanish features: " +
|
||||
"https://www.spigotmc.org/resources/protocollib.1997/");
|
||||
if (!useProtocolLib) {
|
||||
|
||||
log(Level.INFO, "Please install ProtocolLib to be able to use all SuperVanish features: "
|
||||
+ "https://www.spigotmc.org/resources/protocollib.1997/");
|
||||
|
||||
}
|
||||
|
||||
configMgr = new ConfigMgr(this);
|
||||
configMgr.prepareFiles();
|
||||
placeholderConverter = new PlaceholderConverter(this);
|
||||
@@ -96,204 +98,418 @@ public class SuperVanish extends JavaPlugin implements SuperVanishPlugin {
|
||||
command = new VanishCommand(this);
|
||||
versionUtil = new VersionUtil(this);
|
||||
vanishStateMgr = new FileVanishStateMgr(this);
|
||||
if (getSettings().getBoolean("MiscellaneousOptions.UpdateChecker.Enable", true))
|
||||
updateNotifier = new UpdateNotifier(this);
|
||||
visibilityChanger = new VisibilityChanger(new PreventionHider(this), this);
|
||||
if (versionUtil.isOneDotXOrHigher(8) && useProtocolLib)
|
||||
if (versionUtil.isOneDotXOrHigher(8) && useProtocolLib) {
|
||||
|
||||
actionBarMgr = new ActionBarMgr(this);
|
||||
if (useProtocolLib && ServerListPacketListener.isEnabled(this))
|
||||
|
||||
}
|
||||
|
||||
if (useProtocolLib && ServerListPacketListener.isEnabled(this)) {
|
||||
|
||||
ServerListPacketListener.register(this);
|
||||
|
||||
}
|
||||
|
||||
registerEvents();
|
||||
pluginHookMgr = new PluginHookMgr(this);
|
||||
featureMgr = new FeatureMgr(this);
|
||||
featureMgr.enableFeatures();
|
||||
if (!Bukkit.getOnlinePlayers().isEmpty())
|
||||
if (!Bukkit.getOnlinePlayers().isEmpty()) {
|
||||
|
||||
onReload();
|
||||
} catch (Exception e) {
|
||||
logException(e);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
logException(e);
|
||||
|
||||
}
|
||||
|
||||
try {
|
||||
|
||||
VanishAPI.setPlugin(this);
|
||||
|
||||
} catch (NoSuchMethodError ignored) {
|
||||
|
||||
// API already loaded by other plugin
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDisable() {
|
||||
|
||||
try {
|
||||
if (featureMgr != null) featureMgr.disableFeatures();
|
||||
|
||||
if (featureMgr != null) {
|
||||
|
||||
featureMgr.disableFeatures();
|
||||
|
||||
}
|
||||
|
||||
vanishPlayers.clear();
|
||||
VanishAPI.setPlugin(null);
|
||||
|
||||
} catch (Throwable e) {
|
||||
if (e instanceof ThreadDeath || e instanceof VirtualMachineError) throw e;
|
||||
|
||||
if (e instanceof ThreadDeath || e instanceof VirtualMachineError) {
|
||||
|
||||
throw e;
|
||||
|
||||
}
|
||||
|
||||
if (!(e instanceof NoClassDefFoundError | e instanceof NoSuchMethodError)) {
|
||||
|
||||
e.printStackTrace();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void onReload() {
|
||||
for (Player player : Bukkit.getOnlinePlayers()) {
|
||||
boolean itemPickUps = getPlayerData().getBoolean(
|
||||
|
||||
Bukkit.getOnlinePlayers().forEach((Player player) -> {
|
||||
|
||||
final boolean itemPickUps = getPlayerData().getBoolean(
|
||||
"PlayerData." + player.getUniqueId() + ".itemPickUps",
|
||||
getSettings().getBoolean("InvisibilityFeatures.DefaultPickUpItemsOption"));
|
||||
boolean vanished = vanishStateMgr.isVanished(player.getUniqueId());
|
||||
final boolean vanished = vanishStateMgr.isVanished(player.getUniqueId());
|
||||
createVanishPlayer(player, itemPickUps);
|
||||
if (vanished) {
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers())
|
||||
if (!hasPermissionToSee(onlinePlayer, player))
|
||||
|
||||
Bukkit.getOnlinePlayers().forEach((Player onlinePlayer) -> {
|
||||
|
||||
if (!hasPermissionToSee(onlinePlayer, player)) {
|
||||
|
||||
visibilityChanger.getHider().setHidden(player, onlinePlayer, true);
|
||||
|
||||
}
|
||||
if (getSettings().getBoolean("MessageOptions.DisplayActionBar")
|
||||
&& vanished && actionBarMgr != null) {
|
||||
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
if (getSettings().getBoolean("MessageOptions.DisplayActionBar") && vanished && actionBarMgr != null) {
|
||||
|
||||
actionBarMgr.addActionBar(player);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
public void reload() {
|
||||
|
||||
getServer().getScheduler().cancelTasks(this);
|
||||
HandlerList.unregisterAll(this);
|
||||
if (useProtocolLib)
|
||||
if (useProtocolLib) {
|
||||
|
||||
ProtocolLibrary.getProtocolManager().removePacketListeners(this);
|
||||
|
||||
}
|
||||
|
||||
onDisable();
|
||||
onEnable();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
|
||||
|
||||
return this.command.tabComplete(command, sender, alias, args);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
|
||||
|
||||
this.command.execute(command, sender, label, args);
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
private void registerEvents() {
|
||||
PluginManager pluginManager = getServer().getPluginManager();
|
||||
|
||||
final PluginManager pluginManager = getServer().getPluginManager();
|
||||
pluginManager.registerEvents(new GeneralListener(this), this);
|
||||
pluginManager.registerEvents(new PlayerBlockModifyListener(this), this);
|
||||
pluginManager.registerEvents(new WorldChangeListener(this), this);
|
||||
if (versionUtil.isOneDotXOrHigher(10)) {
|
||||
|
||||
pluginManager.registerEvents(new TabCompleteListener(this), this);
|
||||
|
||||
}
|
||||
|
||||
pluginManager.registerEvents(loginListener = new LoginListener(this), this);
|
||||
JoinListener joinListener = new JoinListener(this);
|
||||
pluginManager.registerEvent(PlayerJoinEvent.class, joinListener,
|
||||
getEventPriority(PlayerJoinEvent.class), joinListener, this, false);
|
||||
QuitListener quitListener = new QuitListener(this);
|
||||
pluginManager.registerEvent(PlayerQuitEvent.class, quitListener,
|
||||
getEventPriority(PlayerQuitEvent.class), quitListener, this, false);
|
||||
final JoinListener joinListener = new JoinListener(this);
|
||||
pluginManager.registerEvent(PlayerJoinEvent.class, joinListener, getEventPriority(PlayerJoinEvent.class),
|
||||
joinListener, this, false);
|
||||
final QuitListener quitListener = new QuitListener(this);
|
||||
pluginManager.registerEvent(PlayerQuitEvent.class, quitListener, getEventPriority(PlayerQuitEvent.class),
|
||||
quitListener, this, false);
|
||||
|
||||
}
|
||||
|
||||
private EventPriority getEventPriority(Class<? extends Event> eventClass) {
|
||||
|
||||
try {
|
||||
String eventName = eventClass.getSimpleName();
|
||||
String configString = getSettings().getString("CompatibilityOptions." + eventName + "Priority");
|
||||
if (configString == null) return EventPriority.NORMAL;
|
||||
EventPriority priority = EventPriority.valueOf(configString);
|
||||
return priority;
|
||||
|
||||
final String eventName = eventClass.getSimpleName();
|
||||
final String configString = getSettings().getString("CompatibilityOptions." + eventName + "Priority");
|
||||
if (configString == null) {
|
||||
|
||||
return EventPriority.NORMAL;
|
||||
|
||||
}
|
||||
|
||||
return EventPriority.valueOf(configString);
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
logException(e);
|
||||
return EventPriority.NORMAL;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public String replacePlaceholders(String msg, Object... additionalPlayerInfo) {
|
||||
|
||||
return placeholderConverter.replacePlaceholders(msg, additionalPlayerInfo);
|
||||
|
||||
}
|
||||
|
||||
public Component expandPlaceholders(CommandSender recipient, String msg, Object... additionalPlayerInfo) {
|
||||
|
||||
return placeholderConverter.expandPlaceholders(recipient, msg, additionalPlayerInfo);
|
||||
|
||||
}
|
||||
|
||||
public String getMessage(String path) {
|
||||
|
||||
String message = getMessages().getString("Messages." + path);
|
||||
if (message == null) {
|
||||
|
||||
message = configMgr.getMessagesFile().getDefaultConfig().getString("Messages." + path);
|
||||
|
||||
}
|
||||
|
||||
return message;
|
||||
|
||||
}
|
||||
|
||||
public VanishPlayer getVanishPlayer(Player player) {
|
||||
|
||||
for (VanishPlayer vanishPlayer : vanishPlayers) {
|
||||
|
||||
if (vanishPlayer.getPlayerUUID().equals(player.getUniqueId())) {
|
||||
|
||||
return vanishPlayer;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// ensure that there is always a vanish player
|
||||
boolean itemPickUps = getPlayerData().getBoolean(
|
||||
"PlayerData." + player.getUniqueId() + ".itemPickUps",
|
||||
final boolean itemPickUps = getPlayerData().getBoolean("PlayerData." + player.getUniqueId() + ".itemPickUps",
|
||||
getSettings().getBoolean("InvisibilityFeatures.DefaultPickUpItemsOption"));
|
||||
final VanishPlayer vanishPlayer = new VanishPlayer(player, this, itemPickUps);
|
||||
vanishPlayers.add(vanishPlayer);
|
||||
return vanishPlayer;
|
||||
|
||||
}
|
||||
|
||||
public void createVanishPlayer(Player player, boolean itemPickUps) {
|
||||
VanishPlayer vanishPlayer = new VanishPlayer(player, this, itemPickUps);
|
||||
|
||||
final VanishPlayer vanishPlayer = new VanishPlayer(player, this, itemPickUps);
|
||||
vanishPlayers.add(vanishPlayer);
|
||||
|
||||
}
|
||||
|
||||
public void removeVanishPlayer(VanishPlayer vanishPlayer) {
|
||||
|
||||
vanishPlayers.remove(vanishPlayer);
|
||||
|
||||
}
|
||||
|
||||
public void sendMessage(CommandSender p, String messagesYmlPath, Object... additionalPlayerInfo) {
|
||||
|
||||
String message;
|
||||
if (!messagesYmlPath.contains(" ") && getMessage(messagesYmlPath) != null)
|
||||
if (!StringUtils.contains(messagesYmlPath, " ") && getMessage(messagesYmlPath) != null) {
|
||||
|
||||
message = getMessage(messagesYmlPath);
|
||||
else message = messagesYmlPath;
|
||||
if ("".equalsIgnoreCase(message) || "".equalsIgnoreCase(messagesYmlPath))
|
||||
|
||||
} else {
|
||||
|
||||
message = messagesYmlPath;
|
||||
|
||||
}
|
||||
|
||||
if (StringUtils.equalsIgnoreCase("", message) || StringUtils.equalsIgnoreCase("", messagesYmlPath)) {
|
||||
|
||||
return;
|
||||
message = replacePlaceholders(message, additionalPlayerInfo);
|
||||
p.sendMessage(message);
|
||||
|
||||
}
|
||||
|
||||
if (p instanceof Player player) {
|
||||
|
||||
UtilitiesOG.trueogMessage(player, expandPlaceholders(player, message, additionalPlayerInfo));
|
||||
|
||||
} else {
|
||||
|
||||
p.sendMessage(LegacyComponentSerializer.legacySection()
|
||||
.serialize(expandPlaceholders(p, message, additionalPlayerInfo)));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public boolean canSee(Player viewer, Player viewed) {
|
||||
|
||||
return !visibilityChanger.getHider().isHidden(viewed, viewer);
|
||||
|
||||
}
|
||||
|
||||
public boolean hasPermissionToVanish(CommandSender sender) {
|
||||
|
||||
return layeredPermissionChecker.hasPermissionToVanish(sender);
|
||||
|
||||
}
|
||||
|
||||
public boolean hasPermissionToSee(Player viewer, Player viewed) {
|
||||
|
||||
return layeredPermissionChecker.hasPermissionToSee(viewer, viewed);
|
||||
|
||||
}
|
||||
|
||||
public int getLayeredPermissionLevel(CommandSender sender, String permission) {
|
||||
|
||||
return layeredPermissionChecker.getLayeredPermissionLevel(sender, permission);
|
||||
|
||||
}
|
||||
|
||||
public FileConfiguration getSettings() {
|
||||
|
||||
return configMgr.getSettings();
|
||||
|
||||
}
|
||||
|
||||
public FileConfiguration getMessages() {
|
||||
|
||||
return configMgr.getMessages();
|
||||
|
||||
}
|
||||
|
||||
public FileConfiguration getPlayerData() {
|
||||
|
||||
return configMgr.getPlayerData();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public FileConfiguration getConfig() {
|
||||
|
||||
return getSettings();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void log(Level level, String msg) {
|
||||
|
||||
getLogger().log(level, msg);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void log(Level level, String msg, Throwable ex) {
|
||||
|
||||
getLogger().log(level, msg, ex);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void logException(Throwable e) {
|
||||
|
||||
ExceptionLogger.logException(e, this);
|
||||
|
||||
}
|
||||
|
||||
public boolean isUseProtocolLib() {
|
||||
|
||||
return useProtocolLib;
|
||||
|
||||
}
|
||||
|
||||
public ActionBarMgr getActionBarMgr() {
|
||||
|
||||
return actionBarMgr;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public FileVanishStateMgr getVanishStateMgr() {
|
||||
|
||||
return vanishStateMgr;
|
||||
|
||||
}
|
||||
|
||||
public VersionUtil getVersionUtil() {
|
||||
|
||||
return versionUtil;
|
||||
|
||||
}
|
||||
|
||||
public ConfigMgr getConfigMgr() {
|
||||
|
||||
return configMgr;
|
||||
|
||||
}
|
||||
|
||||
public FeatureMgr getFeatureMgr() {
|
||||
|
||||
return featureMgr;
|
||||
|
||||
}
|
||||
|
||||
public PlaceholderConverter getPlaceholderConverter() {
|
||||
|
||||
return placeholderConverter;
|
||||
|
||||
}
|
||||
|
||||
public VanishCommand getCommand() {
|
||||
|
||||
return command;
|
||||
|
||||
}
|
||||
|
||||
public VisibilityChanger getVisibilityChanger() {
|
||||
|
||||
return visibilityChanger;
|
||||
|
||||
}
|
||||
|
||||
public LoginListener getLoginListener() {
|
||||
|
||||
return loginListener;
|
||||
|
||||
}
|
||||
|
||||
public LayeredPermissionChecker getLayeredPermissionChecker() {
|
||||
|
||||
return layeredPermissionChecker;
|
||||
|
||||
}
|
||||
|
||||
public PluginHookMgr getPluginHookMgr() {
|
||||
|
||||
return pluginHookMgr;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -24,4 +24,5 @@ public interface SuperVanishPlugin {
|
||||
void logException(Throwable e);
|
||||
|
||||
VanishStateMgr getVanishStateMgr();
|
||||
|
||||
}
|
||||
@@ -10,54 +10,88 @@ package de.myzelyam.supervanish;
|
||||
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
|
||||
|
||||
/**
|
||||
* Holds additional information about players in the context of vanishing
|
||||
*/
|
||||
public class VanishPlayer {
|
||||
|
||||
private final SuperVanish plugin;
|
||||
@Getter
|
||||
private final UUID playerUUID;
|
||||
@Setter
|
||||
private boolean itemPickUps;
|
||||
@Getter
|
||||
private int seePermissionLevel, usePermissionLevel;
|
||||
|
||||
VanishPlayer(Player player, SuperVanish plugin, boolean itemPickUps) {
|
||||
|
||||
this.plugin = plugin;
|
||||
this.playerUUID = player.getUniqueId();
|
||||
this.itemPickUps = itemPickUps;
|
||||
if (plugin.getSettings().getBoolean("IndicationFeatures.LayeredPermissions.LayeredSeeAndUsePermissions", false)) {
|
||||
if (plugin.getSettings().getBoolean("IndicationFeatures.LayeredPermissions.LayeredSeeAndUsePermissions",
|
||||
false))
|
||||
{
|
||||
|
||||
seePermissionLevel = plugin.getLayeredPermissionLevel(player, "see");
|
||||
usePermissionLevel = plugin.getLayeredPermissionLevel(player, "use");
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public boolean isOnlineVanished() {
|
||||
|
||||
return plugin.getVanishStateMgr().isVanished(playerUUID);
|
||||
|
||||
}
|
||||
|
||||
public boolean hasItemPickUpsEnabled() {
|
||||
|
||||
return itemPickUps;
|
||||
|
||||
}
|
||||
|
||||
public UUID getPlayerUUID() {
|
||||
|
||||
return playerUUID;
|
||||
|
||||
}
|
||||
|
||||
public void setItemPickUps(boolean itemPickUps) {
|
||||
|
||||
this.itemPickUps = itemPickUps;
|
||||
|
||||
}
|
||||
|
||||
public int getSeePermissionLevel() {
|
||||
|
||||
return seePermissionLevel;
|
||||
|
||||
}
|
||||
|
||||
public int getUsePermissionLevel() {
|
||||
|
||||
return usePermissionLevel;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
|
||||
if (this == o)
|
||||
return true;
|
||||
if (o == null || getClass() != o.getClass())
|
||||
return false;
|
||||
VanishPlayer that = (VanishPlayer) o;
|
||||
return Objects.equals(playerUUID, that.playerUUID);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
|
||||
return Objects.hash(playerUUID);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -16,89 +16,68 @@ import org.bukkit.command.CommandSender;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import lombok.Getter;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
|
||||
@RequiredArgsConstructor
|
||||
public enum CommandAction {
|
||||
VANISH_SELF(
|
||||
"sv.use",
|
||||
false,
|
||||
"/sv [on|off]",
|
||||
"Toggles your visibility") {
|
||||
|
||||
VANISH_SELF("sv.use", false, "/sv [on|off]", "Toggles your visibility") {
|
||||
|
||||
@Override
|
||||
public boolean checkPermission(CommandSender sender, SuperVanish plugin) {
|
||||
|
||||
Validation.checkNotNull(plugin, "plugin cannot be null");
|
||||
return plugin.hasPermissionToVanish(sender);
|
||||
|
||||
}
|
||||
|
||||
},
|
||||
VANISH_OTHER(
|
||||
"sv.others",
|
||||
true,
|
||||
"/sv [on|off] <player>",
|
||||
"Shows or hides a player"),
|
||||
VANISHED_LIST(
|
||||
"sv.list",
|
||||
true,
|
||||
"/sv list",
|
||||
"Shows a list of vanished players"),
|
||||
BROADCAST_LOGIN(
|
||||
"sv.login",
|
||||
false,
|
||||
"/sv login",
|
||||
"Broadcasts a fake login message"),
|
||||
BROADCAST_LOGOUT(
|
||||
"sv.logout",
|
||||
false,
|
||||
"/sv logout",
|
||||
"Broadcasts a fake logout message"),
|
||||
TOGGLE_ITEM_PICKUPS(
|
||||
"sv.toggleitems",
|
||||
false,
|
||||
"/sv tipu",
|
||||
"Toggles picking up items") {
|
||||
VANISH_OTHER("sv.others", true, "/sv [on|off] <player>", "Shows or hides a player"),
|
||||
VANISHED_LIST("sv.list", true, "/sv list", "Shows a list of vanished players"),
|
||||
BROADCAST_LOGIN("sv.login", false, "/sv login", "Broadcasts a fake login message"),
|
||||
BROADCAST_LOGOUT("sv.logout", false, "/sv logout", "Broadcasts a fake logout message"),
|
||||
TOGGLE_ITEM_PICKUPS("sv.toggleitems", false, "/sv tipu", "Toggles picking up items")
|
||||
{
|
||||
|
||||
@Override
|
||||
public boolean checkPermission(CommandSender sender, SuperVanish plugin) {
|
||||
|
||||
return sender.hasPermission(getMainPermission()) || sender.hasPermission("sv.toggleitempickups");
|
||||
|
||||
}
|
||||
|
||||
},
|
||||
RECREATE_FILES(
|
||||
"sv.recreatefiles",
|
||||
true,
|
||||
"/sv recreatefiles",
|
||||
"Recreates the config") {
|
||||
RECREATE_FILES("sv.recreatefiles", true, "/sv recreatefiles", "Recreates the config")
|
||||
{
|
||||
|
||||
@Override
|
||||
public boolean checkPermission(CommandSender sender, SuperVanish plugin) {
|
||||
|
||||
return sender.hasPermission(getMainPermission()) || sender.hasPermission("sv.updatecfg");
|
||||
|
||||
}
|
||||
|
||||
},
|
||||
RELOAD(
|
||||
"sv.reload",
|
||||
true,
|
||||
"/sv reload",
|
||||
"Reloads all settings and messages"),
|
||||
PRINT_STACKTRACE(
|
||||
"sv.stacktrace",
|
||||
true,
|
||||
"/sv stacktrace",
|
||||
"Logs info for a bug report"),
|
||||
SHOW_HELP(
|
||||
"sv.help",
|
||||
true,
|
||||
"/sv help",
|
||||
"Shows this help page");
|
||||
RELOAD("sv.reload", true, "/sv reload", "Reloads all settings and messages"),
|
||||
PRINT_STACKTRACE("sv.stacktrace", true, "/sv stacktrace", "Logs info for a bug report"),
|
||||
SHOW_HELP("sv.help", true, "/sv help", "Shows this help page");
|
||||
|
||||
/**
|
||||
* Use {@link #checkPermission(CommandSender, SuperVanish)} to check whether a {@link CommandSender} has
|
||||
* permission to perform an action or not
|
||||
* Use {@link #checkPermission(CommandSender, SuperVanish)} to check whether a
|
||||
* {@link CommandSender} has permission to perform an action or not
|
||||
*/
|
||||
@Getter
|
||||
private final String mainPermission;
|
||||
private final boolean console;
|
||||
@Getter
|
||||
private final String usage, description;
|
||||
|
||||
CommandAction(String mainPermission, boolean console, String usage, String description) {
|
||||
|
||||
this.mainPermission = mainPermission;
|
||||
this.console = console;
|
||||
this.usage = usage;
|
||||
this.description = description;
|
||||
|
||||
}
|
||||
|
||||
static List<String> getAvailableFirstArguments(CommandSender sender, SuperVanish plugin) {
|
||||
|
||||
Validation.checkNotNull(plugin, "plugin cannot be null");
|
||||
List<String> list = new ArrayList<>();
|
||||
if (SHOW_HELP.checkPermission(sender, plugin))
|
||||
@@ -118,20 +97,46 @@ public enum CommandAction {
|
||||
if (PRINT_STACKTRACE.checkPermission(sender, plugin))
|
||||
list.add("stacktrace");
|
||||
return list;
|
||||
|
||||
}
|
||||
|
||||
public static boolean hasAnyCmdPermission(CommandSender sender, SuperVanish plugin) {
|
||||
|
||||
for (CommandAction action : CommandAction.values())
|
||||
if (action.checkPermission(sender, plugin))
|
||||
return true;
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
public boolean checkPermission(CommandSender sender, SuperVanish plugin) {
|
||||
|
||||
return sender.hasPermission(getMainPermission());
|
||||
|
||||
}
|
||||
|
||||
public boolean usableByConsole() {
|
||||
|
||||
return console;
|
||||
|
||||
}
|
||||
|
||||
public String getMainPermission() {
|
||||
|
||||
return mainPermission;
|
||||
|
||||
}
|
||||
|
||||
public String getUsage() {
|
||||
|
||||
return usage;
|
||||
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
|
||||
return description;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -14,4 +14,5 @@ import org.bukkit.command.CommandSender;
|
||||
public interface Executable {
|
||||
|
||||
void execute(Command cmd, CommandSender sender, String[] args, String label);
|
||||
|
||||
}
|
||||
@@ -21,42 +21,61 @@ public abstract class SubCommand implements Executable {
|
||||
protected final SuperVanish plugin;
|
||||
|
||||
public SubCommand(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
protected Collection<UUID> getAllVanishedPlayers() {
|
||||
|
||||
return plugin.getVanishStateMgr().getVanishedPlayers();
|
||||
|
||||
}
|
||||
|
||||
protected Collection<UUID> getOnlineVanishedPlayers() {
|
||||
|
||||
return plugin.getVanishStateMgr().getOnlineVanishedPlayers();
|
||||
|
||||
}
|
||||
|
||||
public void hidePlayer(Player player) {
|
||||
|
||||
plugin.getVisibilityChanger().hidePlayer(player);
|
||||
|
||||
}
|
||||
|
||||
public void showPlayer(Player player) {
|
||||
|
||||
plugin.getVisibilityChanger().showPlayer(player);
|
||||
|
||||
}
|
||||
|
||||
|
||||
public boolean isVanished(UUID uuid) {
|
||||
|
||||
return plugin.getVanishStateMgr().isVanished(uuid);
|
||||
|
||||
}
|
||||
|
||||
public boolean canDo(CommandSender sender, CommandAction action, boolean sendErrors) {
|
||||
|
||||
if (!(sender instanceof Player))
|
||||
if (!action.usableByConsole()) {
|
||||
|
||||
if (sendErrors)
|
||||
plugin.sendMessage(sender, "InvalidSender", sender);
|
||||
return false;
|
||||
|
||||
}
|
||||
if (!action.checkPermission(sender, plugin)) {
|
||||
|
||||
if (sendErrors)
|
||||
plugin.sendMessage(sender, "NoPermission", sender);
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -25,120 +25,141 @@ public class SubCommandMgr {
|
||||
private SuperVanish plugin;
|
||||
|
||||
public SubCommandMgr(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
public void execute(Command cmd, CommandSender sender, String[] args, String label) {
|
||||
|
||||
try {
|
||||
|
||||
// invalid usage by default
|
||||
Executable executable = new InvalidUsage(plugin);
|
||||
// vanish self #1
|
||||
if (args.length == 0) {
|
||||
|
||||
if (sender instanceof Player)
|
||||
executable = new VanishSelf(plugin);
|
||||
executable.execute(cmd, sender, args, label);
|
||||
return;
|
||||
}
|
||||
// vanish other
|
||||
if ((args[0].equalsIgnoreCase("on")
|
||||
|| args[0].equalsIgnoreCase("off")
|
||||
|| args[0].equalsIgnoreCase("vanish")
|
||||
|| args[0].equalsIgnoreCase("reappear")
|
||||
|| args[0].equalsIgnoreCase("enable")
|
||||
|| args[0].equalsIgnoreCase("disable"))
|
||||
&& args.length > 1
|
||||
|| Bukkit.getPlayer(args[0]) != null) {
|
||||
executable = Bukkit.getPlayer(args[0]) != null
|
||||
&& !(args[0].equalsIgnoreCase("on")
|
||||
|| args[0].equalsIgnoreCase("off")
|
||||
|| args[0].equalsIgnoreCase("vanish")
|
||||
|| args[0].equalsIgnoreCase("reappear")
|
||||
|| args[0].equalsIgnoreCase("enable")
|
||||
|| args[0].equalsIgnoreCase("disable"))
|
||||
? new VanishOther(Bukkit.getPlayer(args[0]), plugin)
|
||||
: new VanishOther(plugin);
|
||||
}
|
||||
// vanish self #2
|
||||
if ((args[0].equalsIgnoreCase("on")
|
||||
|| args[0].equalsIgnoreCase("off")
|
||||
|| args[0].equalsIgnoreCase("vanish")
|
||||
|| args[0].equalsIgnoreCase("reappear")
|
||||
|| args[0].equalsIgnoreCase("enable")
|
||||
|| args[0].equalsIgnoreCase("disable")
|
||||
|| args[0].equalsIgnoreCase("-s"))
|
||||
&& args.length == 1) {
|
||||
executable = new VanishSelf(plugin);
|
||||
}
|
||||
//
|
||||
if (args[0].equalsIgnoreCase("help")
|
||||
|| args[0].equalsIgnoreCase("commands")
|
||||
|| args[0].equalsIgnoreCase("?")) {
|
||||
executable = new ShowHelp(plugin);
|
||||
}
|
||||
if (args[0].equalsIgnoreCase("printstacktrace")
|
||||
|| args[0].equalsIgnoreCase("logstacktrace")
|
||||
|| args[0].equalsIgnoreCase("dumpstacktrace")
|
||||
|| args[0].equalsIgnoreCase("stacktrace")) {
|
||||
executable = new PrintStacktrace(plugin);
|
||||
}
|
||||
if (args[0].equalsIgnoreCase("toggleitempickups")
|
||||
|| args[0].equalsIgnoreCase("toggleitempickup")
|
||||
|| args[0].equalsIgnoreCase("toggleitem")
|
||||
|| args[0].equalsIgnoreCase("toggleitems")
|
||||
|| args[0].equalsIgnoreCase("togglepickup")
|
||||
|| args[0].equalsIgnoreCase("togglepickups")
|
||||
|| args[0].equalsIgnoreCase("pickup")
|
||||
|| args[0].equalsIgnoreCase("pickups")
|
||||
|| args[0].equalsIgnoreCase("tipu")
|
||||
|| args[0].equalsIgnoreCase("tip")) {
|
||||
executable = new ToggleItemPickups(plugin);
|
||||
}
|
||||
if (args[0].equalsIgnoreCase("recreatecfg")
|
||||
|| args[0].equalsIgnoreCase("rccfg")
|
||||
|| args[0].equalsIgnoreCase("recreateconfig")
|
||||
|| args[0].equalsIgnoreCase("rcconfig")
|
||||
|| args[0].equalsIgnoreCase("updatecfg")
|
||||
|| args[0].equalsIgnoreCase("recreate")
|
||||
|| args[0].equalsIgnoreCase("recreatefiles")
|
||||
|| args[0].equalsIgnoreCase("rf")
|
||||
|| args[0].equalsIgnoreCase("rcf")
|
||||
|| args[0].equalsIgnoreCase("refi")) {
|
||||
executable = new RecreateFiles(plugin);
|
||||
}
|
||||
if (args[0].equalsIgnoreCase("reload")
|
||||
|| args[0].equalsIgnoreCase("rl")
|
||||
|| args[0].equalsIgnoreCase("re")
|
||||
|| args[0].equalsIgnoreCase("rlc")
|
||||
|| args[0].equalsIgnoreCase("rlcfg")
|
||||
|| args[0].equalsIgnoreCase("reloadconfig")
|
||||
|| args[0].equalsIgnoreCase("rlp")
|
||||
|| args[0].equalsIgnoreCase("rlpl")
|
||||
|| args[0].equalsIgnoreCase("reloadplugin")) {
|
||||
executable = new Reload(plugin);
|
||||
}
|
||||
if (args[0].equalsIgnoreCase("list")) {
|
||||
executable = new VanishedList(plugin);
|
||||
}
|
||||
if (args[0].equalsIgnoreCase("login")) {
|
||||
executable = new BroadcastLogin(plugin);
|
||||
}
|
||||
if (args[0].equalsIgnoreCase("logout")) {
|
||||
executable = new BroadcastLogout(plugin);
|
||||
}
|
||||
executable.execute(cmd, sender, args, label);
|
||||
} catch (Exception e) {
|
||||
plugin.logException(e);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public List<String> onTabComplete(Command command, CommandSender sender,
|
||||
String alias, String[] args) {
|
||||
// vanish other
|
||||
if ((args[0].equalsIgnoreCase("on") || args[0].equalsIgnoreCase("off") || args[0].equalsIgnoreCase("vanish")
|
||||
|| args[0].equalsIgnoreCase("reappear") || args[0].equalsIgnoreCase("enable")
|
||||
|| args[0].equalsIgnoreCase("disable")) && args.length > 1 || Bukkit.getPlayer(args[0]) != null)
|
||||
{
|
||||
|
||||
executable = Bukkit.getPlayer(args[0]) != null
|
||||
&& !(args[0].equalsIgnoreCase("on") || args[0].equalsIgnoreCase("off")
|
||||
|| args[0].equalsIgnoreCase("vanish") || args[0].equalsIgnoreCase("reappear")
|
||||
|| args[0].equalsIgnoreCase("enable") || args[0].equalsIgnoreCase("disable"))
|
||||
? new VanishOther(Bukkit.getPlayer(args[0]), plugin)
|
||||
: new VanishOther(plugin);
|
||||
|
||||
}
|
||||
|
||||
// vanish self #2
|
||||
if ((args[0].equalsIgnoreCase("on") || args[0].equalsIgnoreCase("off") || args[0].equalsIgnoreCase("vanish")
|
||||
|| args[0].equalsIgnoreCase("reappear") || args[0].equalsIgnoreCase("enable")
|
||||
|| args[0].equalsIgnoreCase("disable") || args[0].equalsIgnoreCase("-s")) && args.length == 1)
|
||||
{
|
||||
|
||||
executable = new VanishSelf(plugin);
|
||||
|
||||
}
|
||||
|
||||
//
|
||||
if (args[0].equalsIgnoreCase("help") || args[0].equalsIgnoreCase("commands")
|
||||
|| args[0].equalsIgnoreCase("?"))
|
||||
{
|
||||
|
||||
executable = new ShowHelp(plugin);
|
||||
|
||||
}
|
||||
|
||||
if (args[0].equalsIgnoreCase("printstacktrace") || args[0].equalsIgnoreCase("logstacktrace")
|
||||
|| args[0].equalsIgnoreCase("dumpstacktrace") || args[0].equalsIgnoreCase("stacktrace"))
|
||||
{
|
||||
|
||||
executable = new PrintStacktrace(plugin);
|
||||
|
||||
}
|
||||
|
||||
if (args[0].equalsIgnoreCase("toggleitempickups") || args[0].equalsIgnoreCase("toggleitempickup")
|
||||
|| args[0].equalsIgnoreCase("toggleitem") || args[0].equalsIgnoreCase("toggleitems")
|
||||
|| args[0].equalsIgnoreCase("togglepickup") || args[0].equalsIgnoreCase("togglepickups")
|
||||
|| args[0].equalsIgnoreCase("pickup") || args[0].equalsIgnoreCase("pickups")
|
||||
|| args[0].equalsIgnoreCase("tipu") || args[0].equalsIgnoreCase("tip"))
|
||||
{
|
||||
|
||||
executable = new ToggleItemPickups(plugin);
|
||||
|
||||
}
|
||||
|
||||
if (args[0].equalsIgnoreCase("recreatecfg") || args[0].equalsIgnoreCase("rccfg")
|
||||
|| args[0].equalsIgnoreCase("recreateconfig") || args[0].equalsIgnoreCase("rcconfig")
|
||||
|| args[0].equalsIgnoreCase("updatecfg") || args[0].equalsIgnoreCase("recreate")
|
||||
|| args[0].equalsIgnoreCase("recreatefiles") || args[0].equalsIgnoreCase("rf")
|
||||
|| args[0].equalsIgnoreCase("rcf") || args[0].equalsIgnoreCase("refi"))
|
||||
{
|
||||
|
||||
executable = new RecreateFiles(plugin);
|
||||
|
||||
}
|
||||
|
||||
if (args[0].equalsIgnoreCase("reload") || args[0].equalsIgnoreCase("rl") || args[0].equalsIgnoreCase("re")
|
||||
|| args[0].equalsIgnoreCase("rlc") || args[0].equalsIgnoreCase("rlcfg")
|
||||
|| args[0].equalsIgnoreCase("reloadconfig") || args[0].equalsIgnoreCase("rlp")
|
||||
|| args[0].equalsIgnoreCase("rlpl") || args[0].equalsIgnoreCase("reloadplugin"))
|
||||
{
|
||||
|
||||
executable = new Reload(plugin);
|
||||
|
||||
}
|
||||
|
||||
if (args[0].equalsIgnoreCase("list")) {
|
||||
|
||||
executable = new VanishedList(plugin);
|
||||
|
||||
}
|
||||
|
||||
if (args[0].equalsIgnoreCase("login")) {
|
||||
|
||||
executable = new BroadcastLogin(plugin);
|
||||
|
||||
}
|
||||
|
||||
if (args[0].equalsIgnoreCase("logout")) {
|
||||
|
||||
executable = new BroadcastLogout(plugin);
|
||||
|
||||
}
|
||||
|
||||
executable.execute(cmd, sender, args, label);
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
plugin.logException(e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public List<String> onTabComplete(Command command, CommandSender sender, String alias, String[] args) {
|
||||
|
||||
// don't provide any help at all if user doesn't have permission to
|
||||
// execute '/sv help'
|
||||
if (!CommandAction.hasAnyCmdPermission(sender, plugin)) {
|
||||
|
||||
return Collections.emptyList();
|
||||
|
||||
}
|
||||
|
||||
if (args.length == 1) {
|
||||
|
||||
String toComplete = args[0];
|
||||
// didn't start to type first argument
|
||||
if (toComplete.equalsIgnoreCase(""))
|
||||
@@ -146,34 +167,48 @@ public class SubCommandMgr {
|
||||
// started to type it, only show args that start with given argument
|
||||
List<String> matchingFirstArguments = new ArrayList<>();
|
||||
for (String arg : CommandAction.getAvailableFirstArguments(sender, plugin)) {
|
||||
|
||||
if (arg.toLowerCase(Locale.ENGLISH).startsWith(toComplete.toLowerCase(Locale.ENGLISH)))
|
||||
matchingFirstArguments.add(arg);
|
||||
|
||||
}
|
||||
|
||||
if (matchingFirstArguments.isEmpty())
|
||||
return getOnlinePlayerNameTabCompletions(toComplete);
|
||||
return matchingFirstArguments;
|
||||
|
||||
// extra commands
|
||||
} else if (args.length == 2) {
|
||||
|
||||
// vanish other player tab completion
|
||||
if ((args[0].equalsIgnoreCase("on")
|
||||
|| args[0].equalsIgnoreCase("off")
|
||||
|| args[0].equalsIgnoreCase("vanish")
|
||||
|| args[0].equalsIgnoreCase("reappear")
|
||||
|| args[0].equalsIgnoreCase("enable")
|
||||
if ((args[0].equalsIgnoreCase("on") || args[0].equalsIgnoreCase("off") || args[0].equalsIgnoreCase("vanish")
|
||||
|| args[0].equalsIgnoreCase("reappear") || args[0].equalsIgnoreCase("enable")
|
||||
|| args[0].equalsIgnoreCase("disable"))
|
||||
&& CommandAction.VANISH_OTHER.checkPermission(sender, plugin)) {
|
||||
&& CommandAction.VANISH_OTHER.checkPermission(sender, plugin))
|
||||
{
|
||||
|
||||
return getOnlinePlayerNameTabCompletions(args[1]);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return Collections.emptyList();
|
||||
|
||||
}
|
||||
|
||||
private List<String> getOnlinePlayerNameTabCompletions(String arg) {
|
||||
|
||||
List<String> playerNames = new ArrayList<>();
|
||||
for (Player p : plugin.getServer().getOnlinePlayers()) {
|
||||
|
||||
if (p.getName().toLowerCase(Locale.ENGLISH).startsWith(arg.toLowerCase(Locale.ENGLISH)))
|
||||
playerNames.add(p.getName());
|
||||
|
||||
}
|
||||
|
||||
return playerNames;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,29 +8,33 @@
|
||||
|
||||
package de.myzelyam.supervanish.commands;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import java.util.List;
|
||||
|
||||
import org.bukkit.command.Command;
|
||||
import org.bukkit.command.CommandSender;
|
||||
|
||||
import java.util.List;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
public class VanishCommand {
|
||||
|
||||
private final SuperVanish plugin;
|
||||
private final SubCommandMgr subCommandMgr;
|
||||
|
||||
public VanishCommand(SuperVanish plugin) {
|
||||
this.plugin = plugin;
|
||||
|
||||
subCommandMgr = new SubCommandMgr(plugin);
|
||||
|
||||
}
|
||||
|
||||
public void execute(Command command, CommandSender sender, String commandLabel, String[] args) {
|
||||
|
||||
subCommandMgr.execute(command, sender, args, commandLabel);
|
||||
|
||||
}
|
||||
|
||||
public List<String> tabComplete(Command command, CommandSender sender, String alias, String[] args)
|
||||
throws IllegalArgumentException {
|
||||
public List<String> tabComplete(Command command, CommandSender sender, String alias, String[] args) {
|
||||
|
||||
return subCommandMgr.onTabComplete(command, sender, alias, args);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -20,14 +20,21 @@ import org.bukkit.entity.Player;
|
||||
public class BroadcastLogin extends SubCommand {
|
||||
|
||||
public BroadcastLogin(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender p, String[] args, String label) {
|
||||
|
||||
if (canDo(p, CommandAction.BROADCAST_LOGIN, true)) {
|
||||
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers())
|
||||
plugin.sendMessage(onlinePlayer, "ReappearMessage", p, onlinePlayer);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -20,14 +20,21 @@ import org.bukkit.entity.Player;
|
||||
public class BroadcastLogout extends SubCommand {
|
||||
|
||||
public BroadcastLogout(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender p, String[] args, String label) {
|
||||
|
||||
if (canDo(p, CommandAction.BROADCAST_LOGOUT, true)) {
|
||||
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers())
|
||||
plugin.sendMessage(onlinePlayer, "VanishMessage", p, onlinePlayer);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,15 +18,23 @@ import org.bukkit.command.CommandSender;
|
||||
public class InvalidUsage extends SubCommand {
|
||||
|
||||
public InvalidUsage(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender sender, String[] args, String label) {
|
||||
|
||||
if (!CommandAction.hasAnyCmdPermission(sender, plugin)) {
|
||||
|
||||
plugin.sendMessage(sender, "NoPermission", sender);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
plugin.sendMessage(sender, "InvalidUsage", sender);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,14 +18,21 @@ import org.bukkit.command.CommandSender;
|
||||
public class PrintStacktrace extends SubCommand {
|
||||
|
||||
public PrintStacktrace(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender sender, String[] args, String label) {
|
||||
|
||||
if (canDo(sender, CommandAction.PRINT_STACKTRACE, true)) {
|
||||
|
||||
plugin.sendMessage(sender, "PrintedStacktrace", sender);
|
||||
plugin.logException(null);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,103 +8,161 @@
|
||||
|
||||
package de.myzelyam.supervanish.commands.subcommands;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.commands.CommandAction;
|
||||
import de.myzelyam.supervanish.commands.SubCommand;
|
||||
import java.io.File;
|
||||
|
||||
import org.bukkit.ChatColor;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.bukkit.command.Command;
|
||||
import org.bukkit.command.CommandSender;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import java.io.File;
|
||||
import de.myzelyam.supervanish.PlaceholderConverter;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.commands.CommandAction;
|
||||
import de.myzelyam.supervanish.commands.SubCommand;
|
||||
import net.trueog.utilitiesog.UtilitiesOG;
|
||||
|
||||
public class RecreateFiles extends SubCommand {
|
||||
|
||||
public RecreateFiles(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender p, String[] args, String label) {
|
||||
if (canDo(p, CommandAction.RECREATE_FILES, true)) {
|
||||
String updates;
|
||||
|
||||
if (!canDo(p, CommandAction.RECREATE_FILES, true)) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
String files;
|
||||
String changes;
|
||||
if (plugin.getConfigMgr().isSettingsUpdateRequired()
|
||||
&& plugin.getConfigMgr().isMessagesUpdateRequired()) {
|
||||
updates = "the config and the messages file";
|
||||
if (plugin.getConfigMgr().isSettingsUpdateRequired() && plugin.getConfigMgr().isMessagesUpdateRequired()) {
|
||||
|
||||
files = "the config and the messages file";
|
||||
changes = "all settings and messages";
|
||||
|
||||
} else if (plugin.getConfigMgr().isSettingsUpdateRequired()) {
|
||||
updates = "the config";
|
||||
|
||||
files = "the config";
|
||||
changes = "all settings";
|
||||
|
||||
} else {
|
||||
updates = "the messages file";
|
||||
|
||||
files = "the messages file";
|
||||
changes = "all messages";
|
||||
|
||||
}
|
||||
|
||||
if (args.length != 2) {
|
||||
|
||||
if (!plugin.getConfigMgr().isSettingsUpdateRequired()
|
||||
&& !plugin.getConfigMgr().isMessagesUpdateRequired()) {
|
||||
&& !plugin.getConfigMgr().isMessagesUpdateRequired())
|
||||
{
|
||||
|
||||
plugin.sendMessage(p, "NoConfigUpdateAvailable", p);
|
||||
return;
|
||||
|
||||
}
|
||||
plugin.sendMessage(p, plugin.getMessage("UpdateWarning").replace("%changes%", changes)
|
||||
.replace("%updates%", updates), p);
|
||||
|
||||
plugin.sendMessage(p, plugin.getMessage("UpdateWarning"), p,
|
||||
PlaceholderConverter.placeholder("changes", changes),
|
||||
PlaceholderConverter.placeholder("files", files));
|
||||
return;
|
||||
|
||||
}
|
||||
if (args[1].equalsIgnoreCase("confirm") || args[1].equalsIgnoreCase("force")) {
|
||||
if (!plugin.getConfigMgr().isSettingsUpdateRequired()
|
||||
&& !plugin.getConfigMgr().isMessagesUpdateRequired()
|
||||
&& !args[1].equalsIgnoreCase("force")) {
|
||||
|
||||
if (StringUtils.equalsIgnoreCase("confirm", args[1]) || StringUtils.equalsIgnoreCase(args[1], "force")) {
|
||||
|
||||
if (!plugin.getConfigMgr().isSettingsUpdateRequired() && !plugin.getConfigMgr().isMessagesUpdateRequired()
|
||||
&& !StringUtils.equalsIgnoreCase(args[1], "force"))
|
||||
{
|
||||
|
||||
plugin.sendMessage(p, "NoConfigUpdateAvailable", p);
|
||||
return;
|
||||
|
||||
}
|
||||
if (args[1].equalsIgnoreCase("force")) {
|
||||
updates = "the config and the messages file";
|
||||
|
||||
if (StringUtils.equalsIgnoreCase(args[1], "force")) {
|
||||
|
||||
files = "the config and the messages file";
|
||||
changes = "all settings and messages";
|
||||
|
||||
}
|
||||
// delete necessary files
|
||||
|
||||
// Delete necessary files.
|
||||
boolean success = false;
|
||||
if (plugin.getConfigMgr().isSettingsUpdateRequired()
|
||||
|| args[1].equalsIgnoreCase("force")) {
|
||||
File file = new File(plugin.getDataFolder().getPath() + File.separator + "config.yml");
|
||||
if (plugin.getConfigMgr().isSettingsUpdateRequired() || StringUtils.equalsIgnoreCase(args[1], "force")) {
|
||||
|
||||
final File file = new File(plugin.getDataFolder().getPath() + File.separator + "config.yml");
|
||||
success = file.delete();
|
||||
plugin.getConfigMgr().getSettingsFile().save();
|
||||
plugin.getConfigMgr().getSettingsFile().reload();
|
||||
plugin.getConfigMgr().setSettings(plugin.getConfigMgr().getSettingsFile().getConfig());
|
||||
|
||||
}
|
||||
if (plugin.getConfigMgr().isMessagesUpdateRequired()
|
||||
|| args[1].equalsIgnoreCase("force")) {
|
||||
File file2 = new File(plugin.getDataFolder().getPath() + File.separator + "messages.yml");
|
||||
|
||||
if (plugin.getConfigMgr().isMessagesUpdateRequired() || StringUtils.equalsIgnoreCase(args[1], "force")) {
|
||||
|
||||
final File file2 = new File(plugin.getDataFolder().getPath() + File.separator + "messages.yml");
|
||||
success &= file2.delete();
|
||||
|
||||
plugin.getConfigMgr().getMessagesFile().save();
|
||||
plugin.getConfigMgr().getMessagesFile().reload();
|
||||
plugin.getConfigMgr().setMessages(plugin.getConfigMgr().getMessagesFile().getConfig());
|
||||
|
||||
}
|
||||
|
||||
if (!success) {
|
||||
p.sendMessage(ChatColor.RED +
|
||||
"Cannot update config, failed to delete file. Are the file permissions valid?");
|
||||
|
||||
final String failMsg = "&cERROR: Cannot recreate files because one of them could not be deleted. Are the file permissions valid?";
|
||||
if (p instanceof Player player) {
|
||||
|
||||
UtilitiesOG.trueogMessage(player, failMsg);
|
||||
|
||||
} else {
|
||||
|
||||
p.sendMessage(failMsg);
|
||||
|
||||
}
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
plugin.sendMessage(p, plugin.getMessage("RecreatedConfig")
|
||||
.replace("%changes%", changes)
|
||||
.replace("%updates%", updates), p);
|
||||
// update update-information
|
||||
|
||||
plugin.sendMessage(p, plugin.getMessage("RecreatedConfig"), p,
|
||||
PlaceholderConverter.placeholder("changes", changes),
|
||||
PlaceholderConverter.placeholder("files", files));
|
||||
|
||||
// Refresh recreation status after regenerating the files.
|
||||
plugin.getConfigMgr().checkFilesForLeftOvers();
|
||||
} else if (args[1].equalsIgnoreCase("dismiss")) {
|
||||
String currentVersion = plugin.getDescription().getVersion();
|
||||
boolean isDismissed =
|
||||
plugin.getPlayerData().getBoolean("PlayerData." + (p instanceof Player ? ((Player) p)
|
||||
.getUniqueId()
|
||||
.toString() : "CONSOLE") + ".dismissed." + currentVersion.replace(".", "_"), false);
|
||||
plugin.getPlayerData().set("PlayerData." + (p instanceof Player ? ((Player) p).getUniqueId().toString()
|
||||
: "CONSOLE") + ".dismissed." + currentVersion.replace(".", "_"), !isDismissed);
|
||||
|
||||
} else if (StringUtils.equalsIgnoreCase("dismiss", args[1])) {
|
||||
|
||||
final String currentVersion = plugin.getPluginMeta().getVersion();
|
||||
final boolean isDismissed = plugin.getPlayerData().getBoolean(
|
||||
"PlayerData." + (p instanceof Player ? ((Player) p).getUniqueId().toString() : "CONSOLE")
|
||||
+ ".dismissed." + currentVersion.replace(".", "_"),
|
||||
false);
|
||||
plugin.getPlayerData()
|
||||
.set("PlayerData." + (p instanceof Player ? ((Player) p).getUniqueId().toString() : "CONSOLE")
|
||||
+ ".dismissed." + currentVersion.replace(".", "_"), !isDismissed);
|
||||
plugin.getConfigMgr().getPlayerDataFile().save();
|
||||
if (!isDismissed)
|
||||
if (!isDismissed) {
|
||||
|
||||
plugin.sendMessage(p, "DismissedRecreationWarning", p);
|
||||
else
|
||||
|
||||
} else {
|
||||
|
||||
plugin.sendMessage(p, "UndismissedRecreationWarning", p);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,35 +8,57 @@
|
||||
|
||||
package de.myzelyam.supervanish.commands.subcommands;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.command.Command;
|
||||
import org.bukkit.command.CommandSender;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import de.myzelyam.supervanish.PlaceholderConverter;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.commands.CommandAction;
|
||||
import de.myzelyam.supervanish.commands.SubCommand;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.command.Command;
|
||||
import org.bukkit.command.CommandSender;
|
||||
import net.trueog.utilitiesog.UtilitiesOG;
|
||||
|
||||
public class Reload extends SubCommand {
|
||||
|
||||
public Reload(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender p, String[] args, String label) {
|
||||
if (canDo(p, CommandAction.RELOAD, true)) {
|
||||
long before = System.currentTimeMillis();
|
||||
|
||||
if (!canDo(p, CommandAction.RELOAD, true)) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
final long before = System.currentTimeMillis();
|
||||
plugin.reload();
|
||||
if (!Bukkit.getPluginManager().isPluginEnabled(plugin)) {
|
||||
p.sendMessage(ChatColor.RED +
|
||||
"Failed to reload SuperVanish since it failed to restart itself. " +
|
||||
"More information is in the console. ("
|
||||
+ (System.currentTimeMillis() - before) + "ms)");
|
||||
|
||||
final String failMsg = "&cERROR: Failed to reload SuperVanish since it failed to restart itself. "
|
||||
+ "More information is in the console. (" + (System.currentTimeMillis() - before) + "ms)";
|
||||
if (p instanceof Player player) {
|
||||
|
||||
UtilitiesOG.trueogMessage(player, failMsg);
|
||||
|
||||
} else {
|
||||
|
||||
p.sendMessage(failMsg);
|
||||
|
||||
}
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
plugin.sendMessage(p, plugin.getMessage("PluginReloaded").replace("%time%",
|
||||
(System.currentTimeMillis() - before) + ""), p);
|
||||
}
|
||||
|
||||
plugin.sendMessage(p, plugin.getMessage("PluginReloaded"), p,
|
||||
PlaceholderConverter.placeholder("time", System.currentTimeMillis() - before));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,7 +8,7 @@
|
||||
|
||||
package de.myzelyam.supervanish.commands.subcommands;
|
||||
|
||||
|
||||
import de.myzelyam.supervanish.PlaceholderConverter;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.commands.CommandAction;
|
||||
import de.myzelyam.supervanish.commands.SubCommand;
|
||||
@@ -19,21 +19,32 @@ import org.bukkit.command.CommandSender;
|
||||
public class ShowHelp extends SubCommand {
|
||||
|
||||
public ShowHelp(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender sender, String[] args, String label) {
|
||||
|
||||
if (canDo(sender, CommandAction.SHOW_HELP, true)) {
|
||||
|
||||
plugin.sendMessage(sender, "HelpHeader", sender);
|
||||
for (CommandAction action : CommandAction.values()) {
|
||||
|
||||
if (canDo(sender, action, false)) {
|
||||
plugin.sendMessage(sender, plugin.getMessage("HelpFormat")
|
||||
.replace("%usage%", action.getUsage())
|
||||
.replace("%description%", action.getDescription())
|
||||
.replace("%permission%", action.getMainPermission()), sender);
|
||||
|
||||
plugin.sendMessage(sender, plugin.getMessage("HelpFormat"), sender,
|
||||
PlaceholderConverter.placeholder("usage", action.getUsage()),
|
||||
PlaceholderConverter.placeholder("description", action.getDescription()),
|
||||
PlaceholderConverter.placeholder("permission", action.getMainPermission()));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -20,24 +20,32 @@ import org.bukkit.entity.Player;
|
||||
public class ToggleItemPickups extends SubCommand {
|
||||
|
||||
public ToggleItemPickups(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender sender, String[] args, String label) {
|
||||
|
||||
if (canDo(sender, CommandAction.TOGGLE_ITEM_PICKUPS, true)) {
|
||||
|
||||
Player p = (Player) sender;
|
||||
plugin.sendMessage(p, plugin.getMessage("ToggledPickingUpItems"
|
||||
+ (toggleState(plugin.getVanishPlayer(p)) ? "On" : "Off")), p);
|
||||
plugin.sendMessage(p, plugin
|
||||
.getMessage("ToggledPickingUpItems" + (toggleState(plugin.getVanishPlayer(p)) ? "On" : "Off")), p);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean toggleState(VanishPlayer vp) {
|
||||
boolean hasEnabled = plugin.getPlayerData().getBoolean("PlayerData."
|
||||
+ vp.getPlayerUUID() + ".itemPickUps");
|
||||
|
||||
boolean hasEnabled = plugin.getPlayerData().getBoolean("PlayerData." + vp.getPlayerUUID() + ".itemPickUps");
|
||||
plugin.getPlayerData().set("PlayerData." + vp.getPlayerUUID() + ".itemPickUps", !hasEnabled);
|
||||
vp.setItemPickUps(!hasEnabled);
|
||||
plugin.getConfigMgr().getPlayerDataFile().save();
|
||||
return !hasEnabled;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -24,82 +24,126 @@ public class VanishOther extends SubCommand {
|
||||
private Player specifiedPlayer;
|
||||
|
||||
public VanishOther(SuperVanish plugin) {
|
||||
|
||||
this(null, plugin);
|
||||
|
||||
}
|
||||
|
||||
public VanishOther(Player specifiedPlayer, SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
this.specifiedPlayer = specifiedPlayer;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender sender, String[] args, String label) {
|
||||
|
||||
if (canDo(sender, CommandAction.VANISH_OTHER, true)) {
|
||||
|
||||
boolean hide = false, offline = false, silent = false;
|
||||
Player target;
|
||||
String name;
|
||||
UUID uuid;
|
||||
if (specifiedPlayer == null) {
|
||||
|
||||
if (args[0].equalsIgnoreCase("on") || args[0].equalsIgnoreCase("enable")
|
||||
|| args[0].equalsIgnoreCase("vanish"))
|
||||
hide = true;
|
||||
target = Bukkit.getPlayer(args[1]);
|
||||
name = target == null ? args[1] : target.getName();
|
||||
|
||||
} else {
|
||||
|
||||
target = specifiedPlayer;
|
||||
name = specifiedPlayer.getName();
|
||||
hide = !isVanished(target.getUniqueId());
|
||||
|
||||
}
|
||||
|
||||
if (target == null) {
|
||||
|
||||
offline = true;
|
||||
uuid = plugin.getVanishStateMgr().getVanishedUUIDFromNameOnFile(name);
|
||||
if (uuid == null) {
|
||||
|
||||
plugin.sendMessage(sender, "PlayerNonExistent", sender, name);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
name = target.getName();
|
||||
uuid = target.getUniqueId();
|
||||
|
||||
}
|
||||
if (!offline && sender instanceof Player && sender != target
|
||||
&& target.hasPermission("sv.notoggle")) {
|
||||
|
||||
if (!offline && sender instanceof Player && sender != target && target.hasPermission("sv.notoggle")) {
|
||||
|
||||
plugin.sendMessage(sender, "CannotHideOtherPlayer", sender, name);
|
||||
return;
|
||||
|
||||
}
|
||||
if (plugin.getSettings().getBoolean(
|
||||
"IndicationFeatures.LayeredPermissions.HideInvisibleInCommands", false) && target != null
|
||||
&& sender instanceof Player && !plugin.hasPermissionToSee((Player) sender, target)) {
|
||||
|
||||
if (plugin.getSettings().getBoolean("IndicationFeatures.LayeredPermissions.HideInvisibleInCommands", false)
|
||||
&& target != null && sender instanceof Player
|
||||
&& !plugin.hasPermissionToSee((Player) sender, target))
|
||||
{
|
||||
|
||||
plugin.sendMessage(sender, "PlayerNonExistent", sender, name);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (hide && (offline ? isVanished(uuid) : isVanished(uuid))) {
|
||||
|
||||
plugin.sendMessage(sender, "AlreadyInvisibleMessage", sender, name);
|
||||
return;
|
||||
|
||||
} else if (!hide && !(offline ? isVanished(uuid) : isVanished(uuid))) {
|
||||
|
||||
plugin.sendMessage(sender, "AlreadyVisibleMessage", sender, name);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (args.length == 3)
|
||||
silent = args[2].equalsIgnoreCase("-s");
|
||||
else if (args.length == 2)
|
||||
silent = args[1].equalsIgnoreCase("-s");
|
||||
if (!offline) {
|
||||
|
||||
if (hide) {
|
||||
|
||||
plugin.getVisibilityChanger().hidePlayer(target, sender.getName(), silent);
|
||||
plugin.sendMessage(sender, "HideOtherMessage", sender, name);
|
||||
|
||||
} else {
|
||||
|
||||
plugin.getVisibilityChanger().showPlayer(target, sender.getName());
|
||||
plugin.sendMessage(sender, "ShowOtherMessage", sender, name, silent);
|
||||
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
if (hide) {
|
||||
|
||||
plugin.getVanishStateMgr().setVanishedState(uuid, name, true, sender.getName());
|
||||
plugin.sendMessage(sender, "HideOtherMessage", sender, name);
|
||||
|
||||
} else {
|
||||
|
||||
plugin.getVanishStateMgr().setVanishedState(uuid, name, false, sender.getName());
|
||||
plugin.sendMessage(sender, "ShowOtherMessage", sender, name);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -19,40 +19,63 @@ import org.bukkit.entity.Player;
|
||||
public class VanishSelf extends SubCommand {
|
||||
|
||||
public VanishSelf(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, CommandSender s, String[] args, String label) {
|
||||
|
||||
if (canDo(s, CommandAction.VANISH_SELF, true)) {
|
||||
|
||||
Player p = (Player) s;
|
||||
if (args.length == 0) {
|
||||
|
||||
if (isVanished(p.getUniqueId()))
|
||||
showPlayer(p);
|
||||
else
|
||||
hidePlayer(p);
|
||||
|
||||
} else if (args.length == 1) {
|
||||
if (args[0].equalsIgnoreCase("off")
|
||||
|| args[0].equalsIgnoreCase("reappear")
|
||||
|| args[0].equalsIgnoreCase("disable")) {
|
||||
|
||||
if (args[0].equalsIgnoreCase("off") || args[0].equalsIgnoreCase("reappear")
|
||||
|| args[0].equalsIgnoreCase("disable"))
|
||||
{
|
||||
|
||||
if (!isVanished(p.getUniqueId())) {
|
||||
|
||||
plugin.sendMessage(p, "NotVanishedError", p);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
showPlayer(p);
|
||||
|
||||
} else if (args[0].equalsIgnoreCase("-s")) {
|
||||
|
||||
if (isVanished(p.getUniqueId()))
|
||||
plugin.getVisibilityChanger().showPlayer(p, null, true);
|
||||
else
|
||||
plugin.getVisibilityChanger().hidePlayer(p, null, true);
|
||||
|
||||
} else {
|
||||
|
||||
if (isVanished(p.getUniqueId())) {
|
||||
|
||||
plugin.sendMessage(p, "AlreadyVanishedError", p);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
hidePlayer(p);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -10,12 +10,14 @@ package de.myzelyam.supervanish.commands.subcommands;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
|
||||
import de.myzelyam.supervanish.PlaceholderConverter;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.commands.CommandAction;
|
||||
import de.myzelyam.supervanish.commands.SubCommand;
|
||||
import net.kyori.adventure.text.minimessage.MiniMessage;
|
||||
import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.command.Command;
|
||||
import org.bukkit.command.CommandSender;
|
||||
|
||||
@@ -25,31 +27,53 @@ import java.util.UUID;
|
||||
public class VanishedList extends SubCommand {
|
||||
|
||||
public VanishedList(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Command cmd, final CommandSender sender, final String[] args, String label) {
|
||||
if (canDo(sender, CommandAction.VANISHED_LIST, true)) {
|
||||
String listMessage = plugin.getMessage("ListMessagePrefix");
|
||||
StringBuilder stringBuilder = new StringBuilder();
|
||||
List<UUID> allInvisiblePlayerUUIDs = ImmutableList.copyOf(getAllVanishedPlayers());
|
||||
if (allInvisiblePlayerUUIDs.isEmpty()) {
|
||||
stringBuilder.append("none");
|
||||
|
||||
if (!canDo(sender, CommandAction.VANISHED_LIST, true)) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
String listMessage = plugin.getMessage("ListMessagePrefix");
|
||||
final StringBuilder stringBuilder = new StringBuilder();
|
||||
final List<UUID> allInvisiblePlayerUUIDs = ImmutableList.copyOf(getAllVanishedPlayers());
|
||||
if (allInvisiblePlayerUUIDs.isEmpty()) {
|
||||
|
||||
stringBuilder.append("none");
|
||||
|
||||
}
|
||||
|
||||
for (int i = 0; i < allInvisiblePlayerUUIDs.size(); i++) {
|
||||
UUID playerUUID = allInvisiblePlayerUUIDs.get(i);
|
||||
|
||||
final UUID playerUUID = allInvisiblePlayerUUIDs.get(i);
|
||||
String name = Bukkit.getOfflinePlayer(playerUUID).getName();
|
||||
if (Bukkit.getPlayer(playerUUID) == null) {
|
||||
name = name + ChatColor.RED + "[offline]" + ChatColor.WHITE;
|
||||
|
||||
name = LegacyComponentSerializer.legacySection()
|
||||
.serialize(MiniMessage.miniMessage().deserialize(name + "<red>[offline]<white>"));
|
||||
|
||||
}
|
||||
|
||||
stringBuilder.append(name);
|
||||
if (i != allInvisiblePlayerUUIDs.size() - 1) {
|
||||
stringBuilder.append(ChatColor.GREEN).append(", ").append(ChatColor.WHITE);
|
||||
|
||||
stringBuilder.append(LegacyComponentSerializer.legacySection()
|
||||
.serialize(MiniMessage.miniMessage().deserialize("<green>, <white>")));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
listMessage = listMessage.replace("%l", stringBuilder.toString());
|
||||
plugin.sendMessage(sender, listMessage, sender);
|
||||
}
|
||||
|
||||
plugin.sendMessage(sender, listMessage, sender,
|
||||
PlaceholderConverter.placeholder("vanished_list", stringBuilder.toString()));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -9,34 +9,38 @@
|
||||
package de.myzelyam.supervanish.config;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import net.trueog.utilitiesog.UtilitiesOG;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.configuration.file.FileConfiguration;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Collections;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
import static de.myzelyam.supervanish.SuperVanish.*;
|
||||
|
||||
@Data
|
||||
public class ConfigMgr {
|
||||
|
||||
private final SuperVanish plugin;
|
||||
private final FileMgr fileMgr;
|
||||
private boolean settingsUpdateRequired, messagesUpdateRequired;
|
||||
private FileConfiguration settings, messages, playerData;
|
||||
private ConfigurableFile messagesFile, settingsFile;
|
||||
private boolean settingsUpdateRequired;
|
||||
private boolean messagesUpdateRequired;
|
||||
private FileConfiguration settings;
|
||||
private FileConfiguration messages;
|
||||
private FileConfiguration playerData;
|
||||
private ConfigurableFile messagesFile;
|
||||
private ConfigurableFile settingsFile;
|
||||
private StorageFile playerDataFile;
|
||||
|
||||
public ConfigMgr(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
fileMgr = new FileMgr(plugin);
|
||||
|
||||
}
|
||||
|
||||
public void prepareFiles() {
|
||||
|
||||
// messages
|
||||
messagesFile = (ConfigurableFile) fileMgr.addFile("messages", FileMgr.FileType.CONFIG);
|
||||
messages = messagesFile.getConfig();
|
||||
@@ -48,16 +52,19 @@ public class ConfigMgr {
|
||||
playerData = playerDataFile.getConfig();
|
||||
playerData.addDefault("InvisiblePlayers", Collections.emptyList());
|
||||
playerData.options().copyDefaults(true);
|
||||
playerData.options().header("SuperVanish v" + plugin.getDescription().getVersion() + " - Data file");
|
||||
playerData.options().setHeader(List.of("SuperVanish v" + plugin.getPluginMeta().getVersion() + " - Data file"));
|
||||
playerDataFile.save();
|
||||
|
||||
checkFilesForLeftOvers();
|
||||
|
||||
}
|
||||
|
||||
public void checkFilesForLeftOvers() {
|
||||
|
||||
try {
|
||||
|
||||
String currentSettingsVersion = settings.getString("ConfigVersion");
|
||||
String newestVersion = plugin.getDescription().getVersion();
|
||||
String newestVersion = plugin.getPluginMeta().getVersion();
|
||||
String currentMessagesVersion = messages.getString("MessagesVersion");
|
||||
messagesUpdateRequired = fileRequiresRecreation(currentMessagesVersion, false);
|
||||
settingsUpdateRequired = fileRequiresRecreation(currentSettingsVersion, true);
|
||||
@@ -66,32 +73,111 @@ public class ConfigMgr {
|
||||
if (newestVersion.equals(currentMessagesVersion))
|
||||
messagesUpdateRequired = false;
|
||||
if (settingsUpdateRequired || messagesUpdateRequired) {
|
||||
String currentVersion = plugin.getDescription().getVersion();
|
||||
boolean isDismissed = playerData.getBoolean("PlayerData.CONSOLE.dismissed."
|
||||
+ currentVersion.replace(".", "_"), false);
|
||||
if (!isDismissed) plugin.log(Level.WARNING, "At least one config file is outdated, " +
|
||||
"it's recommended to regenerate it using '/sv recreatefiles'");
|
||||
|
||||
String currentVersion = plugin.getPluginMeta().getVersion();
|
||||
boolean isDismissed = playerData
|
||||
.getBoolean("PlayerData.CONSOLE.dismissed." + currentVersion.replace(".", "_"), false);
|
||||
if (!isDismissed)
|
||||
plugin.log(Level.WARNING, "At least one config file needs to be recreated. "
|
||||
+ "Use '/sv recreatefiles' to regenerate it.");
|
||||
|
||||
}
|
||||
|
||||
if (currentSettingsVersion.startsWith("1.5.") || currentSettingsVersion.startsWith("1.4.")) {
|
||||
Bukkit.getConsoleSender().sendMessage(ChatColor.YELLOW + "You have a very outdated " +
|
||||
"config file, your settings will not work until you regenerate your SV-files " +
|
||||
"using /sv recreatefiles");
|
||||
|
||||
UtilitiesOG.logToConsole("[SuperVanish]",
|
||||
"<yellow>You have a very old config file. Your settings will not work until you "
|
||||
+ "regenerate your SV files using /sv recreatefiles.");
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
plugin.logException(e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean fileRequiresRecreation(String currentVersion, boolean isSettingsFile) {
|
||||
if (currentVersion == null) return true;
|
||||
for (String ignoredVersion : isSettingsFile ? NON_REQUIRED_SETTINGS_UPDATES
|
||||
: NON_REQUIRED_MESSAGES_UPDATES) {
|
||||
if (currentVersion.equalsIgnoreCase(ignoredVersion)) return false;
|
||||
}
|
||||
|
||||
if (currentVersion == null)
|
||||
return true;
|
||||
for (String ignoredVersion : isSettingsFile ? NON_REQUIRED_SETTINGS_UPDATES : NON_REQUIRED_MESSAGES_UPDATES) {
|
||||
|
||||
if (currentVersion.equalsIgnoreCase(ignoredVersion))
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
public FileMgr getFileMgr() {
|
||||
|
||||
return fileMgr;
|
||||
|
||||
}
|
||||
|
||||
public boolean isSettingsUpdateRequired() {
|
||||
|
||||
return settingsUpdateRequired;
|
||||
|
||||
}
|
||||
|
||||
public boolean isMessagesUpdateRequired() {
|
||||
|
||||
return messagesUpdateRequired;
|
||||
|
||||
}
|
||||
|
||||
public FileConfiguration getSettings() {
|
||||
|
||||
return settings;
|
||||
|
||||
}
|
||||
|
||||
public FileConfiguration getMessages() {
|
||||
|
||||
return messages;
|
||||
|
||||
}
|
||||
|
||||
public FileConfiguration getPlayerData() {
|
||||
|
||||
return playerData;
|
||||
|
||||
}
|
||||
|
||||
public void setSettings(FileConfiguration settings) {
|
||||
|
||||
this.settings = settings;
|
||||
|
||||
}
|
||||
|
||||
public void setMessages(FileConfiguration messages) {
|
||||
|
||||
this.messages = messages;
|
||||
|
||||
}
|
||||
|
||||
public ConfigurableFile getMessagesFile() {
|
||||
|
||||
return messagesFile;
|
||||
|
||||
}
|
||||
|
||||
public ConfigurableFile getSettingsFile() {
|
||||
|
||||
return settingsFile;
|
||||
|
||||
}
|
||||
|
||||
public StorageFile getPlayerDataFile() {
|
||||
|
||||
return playerDataFile;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -27,47 +27,72 @@ public class ConfigurableFile implements PluginFile<FileConfiguration> {
|
||||
private FileConfiguration defaultFileConfiguration;
|
||||
|
||||
public ConfigurableFile(String name, SuperVanish plugin) {
|
||||
|
||||
this.name = name + ".yml";
|
||||
this.plugin = plugin;
|
||||
setup();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
|
||||
return name;
|
||||
|
||||
}
|
||||
|
||||
private void setup() {
|
||||
|
||||
file = new File(plugin.getDataFolder(), name);
|
||||
try (Reader reader = new InputStreamReader(plugin.getResource(name))) {
|
||||
|
||||
defaultFileConfiguration = YamlConfiguration.loadConfiguration(reader);
|
||||
|
||||
} catch (IOException e) {
|
||||
|
||||
e.printStackTrace();
|
||||
|
||||
}
|
||||
|
||||
save();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reload() {
|
||||
|
||||
fileConfiguration = YamlConfiguration.loadConfiguration(file);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public FileConfiguration getConfig() {
|
||||
|
||||
if (fileConfiguration == null) {
|
||||
|
||||
reload();
|
||||
|
||||
}
|
||||
|
||||
return fileConfiguration;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void save() {
|
||||
|
||||
if (!file.exists()) {
|
||||
|
||||
plugin.saveResource(name, false);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public FileConfiguration getDefaultConfig() {
|
||||
|
||||
return defaultFileConfiguration;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -20,40 +20,55 @@ public class FileMgr {
|
||||
private Map<String, PluginFile<?>> files;
|
||||
|
||||
public FileMgr(SuperVanishPlugin plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
files = new HashMap<>();
|
||||
|
||||
}
|
||||
|
||||
public PluginFile<?> addFile(String name, FileType type) {
|
||||
|
||||
if (name == null)
|
||||
throw new IllegalArgumentException("The file name cannot be null!");
|
||||
if (type == FileType.STORAGE) {
|
||||
|
||||
StorageFile file = new StorageFile(name, (SuperVanish) plugin);
|
||||
files.put(name, file);
|
||||
return file;
|
||||
|
||||
} else if (type == FileType.CONFIG) {
|
||||
|
||||
ConfigurableFile file = new ConfigurableFile(name, (SuperVanish) plugin);
|
||||
files.put(name, file);
|
||||
return file;
|
||||
|
||||
} else {
|
||||
|
||||
throw new IllegalArgumentException("The FileType cannot be null!");
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void reloadFile(String fileName) {
|
||||
|
||||
PluginFile<?> file = files.get(fileName);
|
||||
if (file != null)
|
||||
file.reload();
|
||||
else
|
||||
throw new IllegalArgumentException("Specified file doesn't exist!");
|
||||
|
||||
}
|
||||
|
||||
public void reloadAll() {
|
||||
|
||||
for (String fileName : files.keySet())
|
||||
reloadFile(fileName);
|
||||
|
||||
}
|
||||
|
||||
public enum FileType {
|
||||
STORAGE, CONFIG
|
||||
}
|
||||
|
||||
}
|
||||
@@ -17,4 +17,5 @@ public interface PluginFile<CT> {
|
||||
CT getConfig();
|
||||
|
||||
void save();
|
||||
|
||||
}
|
||||
@@ -24,39 +24,55 @@ public class StorageFile implements PluginFile<FileConfiguration> {
|
||||
private FileConfiguration config;
|
||||
|
||||
public StorageFile(String name, SuperVanish plugin) {
|
||||
|
||||
this.name = name;
|
||||
this.plugin = plugin;
|
||||
setup();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
|
||||
return name;
|
||||
|
||||
}
|
||||
|
||||
private void setup() {
|
||||
file = new File(plugin.getDataFolder().getPath() + File.separator
|
||||
+ name + ".yml");
|
||||
|
||||
file = new File(plugin.getDataFolder().getPath() + File.separator + name + ".yml");
|
||||
config = YamlConfiguration.loadConfiguration(file);
|
||||
save();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reload() {
|
||||
|
||||
setup();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public FileConfiguration getConfig() {
|
||||
|
||||
return config;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void save() {
|
||||
|
||||
try {
|
||||
|
||||
config.save(file);
|
||||
|
||||
} catch (IOException e) {
|
||||
|
||||
e.printStackTrace();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,117 +0,0 @@
|
||||
/*
|
||||
* Copyright © 2015, Leon Mangler and the SuperVanish contributors
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
package de.myzelyam.supervanish.features;
|
||||
|
||||
import de.myzelyam.api.vanish.PlayerShowEvent;
|
||||
import de.myzelyam.api.vanish.PostPlayerHideEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
|
||||
public class Broadcast extends Feature {
|
||||
|
||||
public Broadcast(SuperVanish plugin) {
|
||||
super(plugin);
|
||||
}
|
||||
|
||||
public static void announceSilentJoin(Player vanished, SuperVanish plugin) {
|
||||
if (plugin.getSettings().getBoolean("MessageOptions.AnnounceRealJoinQuitToAdmins", true)) {
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
if (vanished == onlinePlayer)
|
||||
continue;
|
||||
if (plugin.canSee(onlinePlayer, vanished)) {
|
||||
plugin.sendMessage(onlinePlayer, "SilentJoinMessageForAdmins", vanished, onlinePlayer);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void announceSilentDeath(Player p, SuperVanish plugin, String deathMessage) {
|
||||
if (plugin.getSettings().getBoolean("MessageOptions.AnnounceDeathToAdmins", true)) {
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
if (p == onlinePlayer)
|
||||
continue;
|
||||
if (plugin.canSee(onlinePlayer, p)) {
|
||||
String message = plugin.getMessage("SilentDeathMessage")
|
||||
.replace("%deathmsg%", deathMessage);
|
||||
plugin.sendMessage(onlinePlayer, message, p, onlinePlayer);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void announceSilentQuit(Player p, SuperVanish plugin) {
|
||||
if (plugin.getSettings().getBoolean("MessageOptions.AnnounceRealJoinQuitToAdmins", true)) {
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
if (p == onlinePlayer)
|
||||
continue;
|
||||
if (plugin.canSee(onlinePlayer, p)) {
|
||||
plugin.sendMessage(onlinePlayer, "SilentQuitMessageForAdmins", p, onlinePlayer);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
return plugin.getSettings().getBoolean("MessageOptions.FakeJoinQuitMessages.BroadcastFakeQuitOnVanish")
|
||||
|| plugin.getSettings().getBoolean("MessageOptions.FakeJoinQuitMessages" +
|
||||
".BroadcastFakeQuitOnReappear");
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onVanish(PostPlayerHideEvent e) {
|
||||
final Player p = e.getPlayer();
|
||||
if (plugin.getSettings().getBoolean("MessageOptions.FakeJoinQuitMessages.BroadcastFakeQuitOnVanish")
|
||||
&& !e.isSilent()) {
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
if (!plugin.canSee(onlinePlayer, p)) {
|
||||
if (!plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.SendMessageOnlyToAdmins"))
|
||||
plugin.sendMessage(onlinePlayer, "VanishMessage", p, onlinePlayer);
|
||||
} else if (!plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.SendMessageOnlyToUsers"))
|
||||
if (!plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.AnnounceVanishReappearToAdmins"))
|
||||
plugin.sendMessage(onlinePlayer, "VanishMessage", p, onlinePlayer);
|
||||
else if (onlinePlayer == p && !plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.SendMessageOnlyToAdmins"))
|
||||
plugin.sendMessage(onlinePlayer, "VanishMessage", p, onlinePlayer);
|
||||
else if (onlinePlayer != p)
|
||||
plugin.sendMessage(onlinePlayer, "VanishMessageWithPermission", p, onlinePlayer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onReappear(PlayerShowEvent e) {
|
||||
Player p = e.getPlayer();
|
||||
if (plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.BroadcastFakeJoinOnReappear") && !e.isSilent()) {
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
if (!plugin.canSee(onlinePlayer, p)) {
|
||||
if (!plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.SendMessageOnlyToAdmins"))
|
||||
plugin.sendMessage(onlinePlayer, "ReappearMessage", p, onlinePlayer);
|
||||
} else if (!plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.SendMessageOnlyToUsers"))
|
||||
if (!plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.AnnounceVanishReappearToAdmins"))
|
||||
plugin.sendMessage(onlinePlayer, "ReappearMessageWithPermission", p, onlinePlayer);
|
||||
else if (onlinePlayer == p && !plugin.getSettings().getBoolean(
|
||||
"MessageOptions.FakeJoinQuitMessages.SendMessageOnlyToAdmins"))
|
||||
plugin.sendMessage(onlinePlayer, "ReappearMessage", p, onlinePlayer);
|
||||
else if (onlinePlayer != p)
|
||||
plugin.sendMessage(onlinePlayer, "ReappearMessageWithPermission", p, onlinePlayer);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -20,18 +20,25 @@ public abstract class Feature implements Listener {
|
||||
protected final SuperVanish plugin;
|
||||
|
||||
public Feature(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
public void onEnable() {
|
||||
|
||||
}
|
||||
|
||||
public void onDisable() {
|
||||
|
||||
}
|
||||
|
||||
public abstract boolean isActive();
|
||||
|
||||
protected void delay(Runnable runnable) {
|
||||
|
||||
plugin.getServer().getScheduler().runTaskLater(plugin, runnable, 1);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,12 +8,6 @@
|
||||
|
||||
package de.myzelyam.supervanish.features;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.utils.Requirement;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.event.HandlerList;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
@@ -23,100 +17,149 @@ import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import lombok.Data;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.event.HandlerList;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.utils.Requirement;
|
||||
|
||||
public class FeatureMgr {
|
||||
|
||||
private static final Requirement<FeatureInfo> protocolLibInstalled = featureInfo -> Bukkit.getPluginManager().isPluginEnabled("ProtocolLib"),
|
||||
oneDotEightOrHigher = featureInfo -> featureInfo.getPlugin().getVersionUtil().isOneDotXOrHigher(8),
|
||||
oneDotSeventeenOrHigher = featureInfo -> featureInfo.getPlugin().getVersionUtil().isOneDotXOrHigher(17),
|
||||
supportedServer = featureInfo -> Bukkit.getServer().getName().equals("Paper") || Bukkit.getServer().getName().equals("Purpur");
|
||||
private static final Requirement<FeatureInfo> protocolLibInstalled = featureInfo -> Bukkit.getPluginManager()
|
||||
.isPluginEnabled("ProtocolLib");
|
||||
private static final Requirement<FeatureInfo> oneDotEightOrHigher = featureInfo -> featureInfo.getPlugin()
|
||||
.getVersionUtil().isOneDotXOrHigher(8);
|
||||
private static final Requirement<FeatureInfo> oneDotSeventeenOrHigher = featureInfo -> featureInfo.getPlugin()
|
||||
.getVersionUtil().isOneDotXOrHigher(17);
|
||||
private static final Requirement<FeatureInfo> supportedServer = featureInfo -> "Paper"
|
||||
.equals(Bukkit.getServer().getName()) || "Purpur".equals(Bukkit.getServer().getName());
|
||||
private final Map<String, FeatureInfo> registeredFeatures = new HashMap<>();
|
||||
private final Set<Feature> activeFeatures = new HashSet<>();
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public FeatureMgr(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
registeredFeatures.put("SilentOpenChest", new FeatureInfo(SilentOpenChest.class, plugin,
|
||||
Arrays.asList(protocolLibInstalled, oneDotEightOrHigher)));
|
||||
registeredFeatures.put("NightVision", new FeatureInfo(NightVision.class, plugin,
|
||||
Arrays.asList(protocolLibInstalled, oneDotEightOrHigher)));
|
||||
registeredFeatures.put("NightVision",
|
||||
new FeatureInfo(NightVision.class, plugin, Arrays.asList(protocolLibInstalled, oneDotEightOrHigher)));
|
||||
registeredFeatures.put("VanishIndication", new FeatureInfo(VanishIndication.class, plugin,
|
||||
Arrays.asList(protocolLibInstalled, oneDotEightOrHigher)));
|
||||
registeredFeatures.put("Broadcast", new FeatureInfo(Broadcast.class, plugin));
|
||||
registeredFeatures.put("NoSculkSensorDetection", new FeatureInfo(NoSculkSensorDetection.class, plugin,
|
||||
Collections.singletonList(oneDotSeventeenOrHigher)));
|
||||
registeredFeatures.put("NoTurtleEggBreaking", new FeatureInfo(NoTurtleEggBreaking.class, plugin,
|
||||
Collections.singletonList(oneDotSeventeenOrHigher)));
|
||||
registeredFeatures.put("NoDripLeafTilt", new FeatureInfo(NoDripLeafTilt.class, plugin,
|
||||
Collections.singletonList(oneDotSeventeenOrHigher)));
|
||||
registeredFeatures.put("NoRaidTrigger", new FeatureInfo(NoRaidTrigger.class, plugin,
|
||||
Collections.singletonList(oneDotSeventeenOrHigher)));
|
||||
registeredFeatures.put("NoMobSpawn", new FeatureInfo(NoMobSpawn.class, plugin,
|
||||
Collections.singletonList(supportedServer)));
|
||||
registeredFeatures.put("HideAdvancementMessages", new FeatureInfo(HideAdvancementMessages.class, plugin,
|
||||
Collections.singletonList(supportedServer)));
|
||||
registeredFeatures.put("NoTurtleEggBreaking",
|
||||
new FeatureInfo(NoTurtleEggBreaking.class, plugin, Collections.singletonList(oneDotSeventeenOrHigher)));
|
||||
registeredFeatures.put("NoDripLeafTilt",
|
||||
new FeatureInfo(NoDripLeafTilt.class, plugin, Collections.singletonList(oneDotSeventeenOrHigher)));
|
||||
registeredFeatures.put("NoRaidTrigger",
|
||||
new FeatureInfo(NoRaidTrigger.class, plugin, Collections.singletonList(oneDotSeventeenOrHigher)));
|
||||
registeredFeatures.put("NoMobSpawn",
|
||||
new FeatureInfo(NoMobSpawn.class, plugin, Collections.singletonList(supportedServer)));
|
||||
|
||||
}
|
||||
|
||||
public void enableFeatures() {
|
||||
featureLoop:
|
||||
for (String id : registeredFeatures.keySet()) {
|
||||
FeatureInfo featureInfo = registeredFeatures.get(id);
|
||||
|
||||
featureLoop: for (String id : registeredFeatures.keySet()) {
|
||||
|
||||
final FeatureInfo featureInfo = registeredFeatures.get(id);
|
||||
for (Requirement<FeatureInfo> requirement : featureInfo.getRequirements()) {
|
||||
if (!requirement.fulfilledBy(featureInfo)) continue featureLoop;
|
||||
|
||||
if (!requirement.fulfilledBy(featureInfo)) {
|
||||
|
||||
continue featureLoop;
|
||||
|
||||
}
|
||||
Feature feature;
|
||||
|
||||
}
|
||||
|
||||
final Feature feature;
|
||||
try {
|
||||
|
||||
feature = featureInfo.getFeatureClass().getConstructor(SuperVanish.class).newInstance(plugin);
|
||||
} catch (NoSuchMethodException | InvocationTargetException
|
||||
| InstantiationException | IllegalAccessException e) {
|
||||
|
||||
} catch (NoSuchMethodException | InvocationTargetException | InstantiationException
|
||||
| IllegalAccessException e)
|
||||
{
|
||||
|
||||
plugin.logException(e);
|
||||
continue;
|
||||
|
||||
}
|
||||
if (!feature.isActive()) continue;
|
||||
|
||||
if (!feature.isActive()) {
|
||||
|
||||
continue;
|
||||
|
||||
}
|
||||
|
||||
activeFeatures.add(feature);
|
||||
|
||||
Bukkit.getPluginManager().registerEvents(feature, plugin);
|
||||
|
||||
feature.onEnable();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void disableFeatures() {
|
||||
for (Feature feature : activeFeatures) {
|
||||
|
||||
activeFeatures.forEach(feature -> {
|
||||
|
||||
feature.onDisable();
|
||||
HandlerList.unregisterAll(feature);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
activeFeatures.clear();
|
||||
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public <T extends Feature> T getFeature(Class<T> featureClass) {
|
||||
for (Feature feature : activeFeatures) {
|
||||
if (feature.getClass().equals(featureClass)) {
|
||||
//noinspection unchecked
|
||||
return (T) feature;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
|
||||
// noinspection unchecked on purpose
|
||||
return activeFeatures.stream().filter(feature -> feature.getClass().equals(featureClass)).findFirst()
|
||||
.map(feature -> (T) feature).orElse(null);
|
||||
|
||||
}
|
||||
|
||||
public Set<Feature> getActiveFeatures() {
|
||||
|
||||
return activeFeatures;
|
||||
|
||||
}
|
||||
|
||||
@Data
|
||||
private static class FeatureInfo {
|
||||
private final Class<? extends Feature> featureClass;
|
||||
private final Collection<Requirement<FeatureInfo>> requirements;
|
||||
private final SuperVanish plugin;
|
||||
|
||||
FeatureInfo(Class<? extends Feature> featureClass, SuperVanish plugin,
|
||||
Collection<Requirement<FeatureInfo>> requirements) {
|
||||
this.featureClass = featureClass;
|
||||
this.requirements = requirements;
|
||||
this.plugin = plugin;
|
||||
}
|
||||
private record FeatureInfo(Class<? extends Feature> featureClass, SuperVanish plugin,
|
||||
Collection<Requirement<FeatureInfo>> requirements)
|
||||
{
|
||||
|
||||
FeatureInfo(Class<? extends Feature> featureClass, SuperVanish plugin) {
|
||||
|
||||
this(featureClass, plugin, Collections.emptySet());
|
||||
|
||||
}
|
||||
|
||||
public Class<? extends Feature> getFeatureClass() {
|
||||
|
||||
return featureClass;
|
||||
|
||||
}
|
||||
|
||||
public Collection<Requirement<FeatureInfo>> getRequirements() {
|
||||
|
||||
return requirements;
|
||||
|
||||
}
|
||||
|
||||
public SuperVanish getPlugin() {
|
||||
|
||||
return plugin;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,40 +0,0 @@
|
||||
package de.myzelyam.supervanish.features;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.player.PlayerAdvancementDoneEvent;
|
||||
|
||||
// This feature is paper-only because the PlayerAdvancementDoneEvent#message() method doesn't exist in Spigot
|
||||
public class HideAdvancementMessages extends Feature {
|
||||
|
||||
private boolean suppressErrors = false;
|
||||
|
||||
public HideAdvancementMessages(SuperVanish plugin) {
|
||||
super(plugin);
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onAdvancementDone(PlayerAdvancementDoneEvent e) {
|
||||
try {
|
||||
Player p = e.getPlayer();
|
||||
Component message = e.message();
|
||||
if (message == null) return;
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) return;
|
||||
if (e.message() == null) return;
|
||||
e.message(null);
|
||||
p.sendMessage(message);
|
||||
} catch (Exception er) {
|
||||
if (!suppressErrors) {
|
||||
plugin.logException(er);
|
||||
suppressErrors = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
return plugin.getSettings().getBoolean("MessageOptions.HideAdvancementMessages", true);
|
||||
}
|
||||
}
|
||||
@@ -33,95 +33,137 @@ public class NightVision extends Feature implements Runnable {
|
||||
private final Map<UUID, PotionEffect> playerPreviousPotionEffectMap = new HashMap<>();
|
||||
|
||||
public NightVision(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onEnable() {
|
||||
|
||||
plugin.getServer().getScheduler().scheduleSyncRepeatingTask(plugin, this, 20 * 60 * 2, 20 * 60 * 2);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.NightVisionEffect");
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onVanish(PlayerHideEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
// getPotionEffect(..) is 1.10+ API
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(10)) {
|
||||
|
||||
if (p.getPotionEffect(PotionEffectType.NIGHT_VISION) != null) {
|
||||
|
||||
playerPreviousPotionEffectMap.put(p.getUniqueId(), p.getPotionEffect(PotionEffectType.NIGHT_VISION));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
sendAddPotionEffect(p);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onReappear(PlayerShowEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
sendRemovePotionEffect(p);
|
||||
if (playerPreviousPotionEffectMap.containsKey(p.getUniqueId())) {
|
||||
|
||||
p.addPotionEffect(playerPreviousPotionEffectMap.remove(p.getUniqueId()));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onJoin(PlayerJoinEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
if (playerPreviousPotionEffectMap.containsKey(p.getUniqueId())) {
|
||||
|
||||
p.addPotionEffect(playerPreviousPotionEffectMap.remove(p.getUniqueId()));
|
||||
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
sendAddPotionEffect(p);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onQuit(PlayerQuitEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
sendRemovePotionEffect(p);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onTeleport(PlayerTeleportEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
if (e.getFrom().getWorld() == null || e.getTo() == null || e.getTo().getWorld() == null
|
||||
|| e.getFrom().getWorld().getName().equals(e.getTo().getWorld().getName())) return;
|
||||
|| e.getFrom().getWorld().getName().equals(e.getTo().getWorld().getName()))
|
||||
return;
|
||||
sendRemovePotionEffect(p);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onWorldChange(PlayerChangedWorldEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
sendAddPotionEffect(p);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
// renew every now and then to prevent blinking bug
|
||||
for (UUID uuid : plugin.getVanishStateMgr().getOnlineVanishedPlayers()) {
|
||||
|
||||
Player p = Bukkit.getPlayer(uuid);
|
||||
if (p == null) continue;
|
||||
if (p == null)
|
||||
continue;
|
||||
sendRemovePotionEffect(p);
|
||||
sendAddPotionEffect(p);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void sendAddPotionEffect(Player p) {
|
||||
p.addPotionEffect(new PotionEffect(PotionEffectType.NIGHT_VISION,
|
||||
INFINITE_POTION_EFFECT_LENGTH, 0, true, false));
|
||||
|
||||
p.addPotionEffect(
|
||||
new PotionEffect(PotionEffectType.NIGHT_VISION, INFINITE_POTION_EFFECT_LENGTH, 0, true, false));
|
||||
|
||||
}
|
||||
|
||||
private void sendRemovePotionEffect(Player p) {
|
||||
|
||||
p.removePotionEffect(PotionEffectType.NIGHT_VISION);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -10,22 +10,29 @@ import org.bukkit.event.player.PlayerInteractEvent;
|
||||
public class NoDripLeafTilt extends Feature {
|
||||
|
||||
public NoDripLeafTilt(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onInteract(PlayerInteractEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) return;
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
if (!e.getAction().equals(Action.PHYSICAL) || e.getClickedBlock() == null
|
||||
|| !e.getClickedBlock().getType().toString().equals("BIG_DRIPLEAF"))
|
||||
return;
|
||||
e.setCancelled(true);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.DisableDripLeaf", true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,79 +18,123 @@ public class NoMobSpawn extends Feature {
|
||||
private boolean suppressErrors = false;
|
||||
|
||||
public NoMobSpawn(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onSkeletonHorseTrap(SkeletonHorseTrapEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
List<HumanEntity> humans = e.getEligibleHumans();
|
||||
int humansCount = humans.size();
|
||||
for (HumanEntity human : humans) {
|
||||
|
||||
if (human instanceof Player) {
|
||||
|
||||
Player p = (Player) human;
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
humansCount--;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (humansCount == 0)
|
||||
e.setCancelled(true);
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
if (!suppressErrors) {
|
||||
|
||||
plugin.logException(er);
|
||||
suppressErrors = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onEntitySpawn(PlayerNaturallySpawnCreaturesEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
if (plugin.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId()))
|
||||
e.setCancelled(true);
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
if (!suppressErrors) {
|
||||
|
||||
plugin.logException(er);
|
||||
suppressErrors = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onEntitySpawnerSpawn(PreSpawnerSpawnEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
// First check if a non-spectator vanished player is in range
|
||||
boolean vanishedPlayerInRange = false;
|
||||
for (UUID vanishedUUID : plugin.getVanishStateMgr().getOnlineVanishedPlayers()) {
|
||||
|
||||
Player p = Bukkit.getPlayer(vanishedUUID);
|
||||
if (p == null) continue;
|
||||
if (p.getWorld().equals(e.getSpawnerLocation().getWorld()) &&
|
||||
p.getLocation().distanceSquared(e.getSpawnerLocation()) <= 256 &&
|
||||
p.getGameMode() != GameMode.SPECTATOR)
|
||||
if (p == null)
|
||||
continue;
|
||||
if (p.getWorld().equals(e.getSpawnerLocation().getWorld())
|
||||
&& p.getLocation().distanceSquared(e.getSpawnerLocation()) <= 256
|
||||
&& p.getGameMode() != GameMode.SPECTATOR)
|
||||
vanishedPlayerInRange = true;
|
||||
|
||||
}
|
||||
if (!vanishedPlayerInRange) return;
|
||||
|
||||
if (!vanishedPlayerInRange)
|
||||
return;
|
||||
|
||||
// If so, only cancel if no non-vanished player is in range
|
||||
for (Player p : Bukkit.getOnlinePlayers()) {
|
||||
if (p.getWorld().equals(e.getSpawnerLocation().getWorld()) &&
|
||||
p.getLocation().distanceSquared(e.getSpawnerLocation()) <= 256 &&
|
||||
p.getGameMode() != GameMode.SPECTATOR &&
|
||||
!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
|
||||
if (p.getWorld().equals(e.getSpawnerLocation().getWorld())
|
||||
&& p.getLocation().distanceSquared(e.getSpawnerLocation()) <= 256
|
||||
&& p.getGameMode() != GameMode.SPECTATOR
|
||||
&& !plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
e.setCancelled(true);
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
if (!suppressErrors) {
|
||||
|
||||
plugin.logException(er);
|
||||
suppressErrors = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.PreventMobSpawning", true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -23,56 +23,82 @@ import org.bukkit.scoreboard.Team;
|
||||
public class NoPush extends Feature {
|
||||
|
||||
public NoPush(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.DisablePush");
|
||||
|
||||
}
|
||||
|
||||
public void setCantPush(Player p) {
|
||||
|
||||
Team team = p.getScoreboard().getTeam("Vanished");
|
||||
if (team == null) {
|
||||
|
||||
team = p.getScoreboard().registerNewTeam("Vanished");
|
||||
|
||||
}
|
||||
|
||||
try {
|
||||
|
||||
team.setOption(Team.Option.COLLISION_RULE, Team.OptionStatus.NEVER);
|
||||
team.addEntry(p.getName());
|
||||
|
||||
} catch (NoSuchMethodError | NoClassDefFoundError ignored) {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void setCanPush(Player p) {
|
||||
|
||||
Team team = p.getScoreboard().getTeam("Vanished");
|
||||
if (team != null)
|
||||
team.removeEntry(p.getName());
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onVanish(PlayerHideEvent e) {
|
||||
|
||||
setCantPush(e.getPlayer());
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onReappear(PlayerShowEvent e) {
|
||||
|
||||
setCanPush(e.getPlayer());
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onJoin(final PlayerJoinEvent e) {
|
||||
|
||||
if (plugin.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId()))
|
||||
new BukkitRunnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
setCantPush(e.getPlayer());
|
||||
|
||||
}
|
||||
|
||||
}.runTaskLater(plugin, 5);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onQuit(PlayerQuitEvent e) {
|
||||
|
||||
setCanPush(e.getPlayer());
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -4,26 +4,31 @@ import de.myzelyam.supervanish.SuperVanish;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.block.Action;
|
||||
import org.bukkit.event.player.PlayerInteractEvent;
|
||||
import org.bukkit.event.raid.RaidEvent;
|
||||
import org.bukkit.event.raid.RaidTriggerEvent;
|
||||
|
||||
public class NoRaidTrigger extends Feature {
|
||||
|
||||
public NoRaidTrigger(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onInteract(RaidTriggerEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) return;
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.PreventRaidTriggering", true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -11,28 +11,42 @@ import org.bukkit.event.player.PlayerInteractEvent;
|
||||
public class NoSculkSensorDetection extends Feature {
|
||||
|
||||
public NoSculkSensorDetection(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onSculkSensorTrigger(BlockReceiveGameEvent e) {
|
||||
if (!(e.getEntity() instanceof Player)) return;
|
||||
|
||||
if (!(e.getEntity() instanceof Player))
|
||||
return;
|
||||
Player p = (Player) e.getEntity();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) return;
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onInteract(PlayerInteractEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) return;
|
||||
if (!e.getAction().equals(Action.PHYSICAL) || e.getClickedBlock() == null) return;
|
||||
if (!e.getClickedBlock().getType().toString().matches("SCULK_SENSOR|CALIBRATED_SCULK_SENSOR|SCULK_SHRIEKER")) return;
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
if (!e.getAction().equals(Action.PHYSICAL) || e.getClickedBlock() == null)
|
||||
return;
|
||||
if (!e.getClickedBlock().getType().toString().matches("SCULK_SENSOR|CALIBRATED_SCULK_SENSOR|SCULK_SHRIEKER"))
|
||||
return;
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.PreventSculkSensorActivation", true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -10,21 +10,29 @@ import org.bukkit.event.player.PlayerInteractEvent;
|
||||
public class NoTurtleEggBreaking extends Feature {
|
||||
|
||||
public NoTurtleEggBreaking(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onInteract(PlayerInteractEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) return;
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
if (!e.getAction().equals(Action.PHYSICAL) || e.getClickedBlock() == null
|
||||
|| !e.getClickedBlock().getType().toString().equals("TURTLE_EGG"))
|
||||
return;
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.PreventTurtleEggBreaking", true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,10 +8,34 @@
|
||||
|
||||
package de.myzelyam.supervanish.features;
|
||||
|
||||
import com.comphenix.protocol.ProtocolLibrary;
|
||||
import de.myzelyam.api.vanish.PlayerShowEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.hooks.OpenInvHook;
|
||||
import static org.bukkit.Material.BLACK_SHULKER_BOX;
|
||||
import static org.bukkit.Material.BLUE_SHULKER_BOX;
|
||||
import static org.bukkit.Material.BROWN_SHULKER_BOX;
|
||||
import static org.bukkit.Material.CHEST;
|
||||
import static org.bukkit.Material.CYAN_SHULKER_BOX;
|
||||
import static org.bukkit.Material.ENDER_CHEST;
|
||||
import static org.bukkit.Material.GRAY_SHULKER_BOX;
|
||||
import static org.bukkit.Material.GREEN_SHULKER_BOX;
|
||||
import static org.bukkit.Material.ITEM_FRAME;
|
||||
import static org.bukkit.Material.LIGHT_BLUE_SHULKER_BOX;
|
||||
import static org.bukkit.Material.LIGHT_GRAY_SHULKER_BOX;
|
||||
import static org.bukkit.Material.LIME_SHULKER_BOX;
|
||||
import static org.bukkit.Material.MAGENTA_SHULKER_BOX;
|
||||
import static org.bukkit.Material.ORANGE_SHULKER_BOX;
|
||||
import static org.bukkit.Material.PINK_SHULKER_BOX;
|
||||
import static org.bukkit.Material.PURPLE_SHULKER_BOX;
|
||||
import static org.bukkit.Material.RED_SHULKER_BOX;
|
||||
import static org.bukkit.Material.SHULKER_BOX;
|
||||
import static org.bukkit.Material.TRAPPED_CHEST;
|
||||
import static org.bukkit.Material.WHITE_SHULKER_BOX;
|
||||
import static org.bukkit.Material.YELLOW_SHULKER_BOX;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.bukkit.GameMode;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
@@ -23,15 +47,22 @@ import org.bukkit.event.block.Action;
|
||||
import org.bukkit.event.inventory.InventoryClickEvent;
|
||||
import org.bukkit.event.inventory.InventoryCloseEvent;
|
||||
import org.bukkit.event.inventory.InventoryType;
|
||||
import org.bukkit.event.player.*;
|
||||
import org.bukkit.event.player.PlayerGameModeChangeEvent;
|
||||
import org.bukkit.event.player.PlayerInteractEvent;
|
||||
import org.bukkit.event.player.PlayerMoveEvent;
|
||||
import org.bukkit.event.player.PlayerQuitEvent;
|
||||
import org.bukkit.event.player.PlayerTeleportEvent;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.bukkit.inventory.InventoryView;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.scheduler.BukkitRunnable;
|
||||
import org.bukkit.util.Vector;
|
||||
|
||||
import java.util.*;
|
||||
import com.comphenix.protocol.ProtocolLibrary;
|
||||
|
||||
import static org.bukkit.Material.*;
|
||||
import de.myzelyam.api.vanish.PlayerShowEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.hooks.OpenInvHook;
|
||||
|
||||
public class SilentOpenChest extends Feature {
|
||||
|
||||
@@ -40,220 +71,386 @@ public class SilentOpenChest extends Feature {
|
||||
private final Collection<Material> additionalChestMaterials;
|
||||
|
||||
public SilentOpenChest(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
additionalChestMaterials = new ArrayList<>();
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(11)) {
|
||||
|
||||
try {
|
||||
//noinspection unused
|
||||
InventoryType testInvType = InventoryType.SHULKER_BOX;
|
||||
|
||||
additionalChestMaterials.addAll(Arrays.asList(BLACK_SHULKER_BOX, BLUE_SHULKER_BOX, BROWN_SHULKER_BOX,
|
||||
CYAN_SHULKER_BOX, GRAY_SHULKER_BOX, GREEN_SHULKER_BOX, LIGHT_BLUE_SHULKER_BOX,
|
||||
LIME_SHULKER_BOX, MAGENTA_SHULKER_BOX, ORANGE_SHULKER_BOX, PINK_SHULKER_BOX,
|
||||
PURPLE_SHULKER_BOX, RED_SHULKER_BOX, WHITE_SHULKER_BOX,
|
||||
YELLOW_SHULKER_BOX));
|
||||
CYAN_SHULKER_BOX, GRAY_SHULKER_BOX, GREEN_SHULKER_BOX, LIGHT_BLUE_SHULKER_BOX, LIME_SHULKER_BOX,
|
||||
MAGENTA_SHULKER_BOX, ORANGE_SHULKER_BOX, PINK_SHULKER_BOX, PURPLE_SHULKER_BOX, RED_SHULKER_BOX,
|
||||
WHITE_SHULKER_BOX, YELLOW_SHULKER_BOX));
|
||||
try {
|
||||
|
||||
additionalChestMaterials.add(LIGHT_GRAY_SHULKER_BOX);
|
||||
|
||||
} catch (NoSuchFieldError e) {
|
||||
// old name
|
||||
|
||||
// Old name.
|
||||
additionalChestMaterials.add(Material.valueOf("SILVER_SHULKER_BOX"));
|
||||
|
||||
}
|
||||
|
||||
try {
|
||||
|
||||
additionalChestMaterials.add(SHULKER_BOX);
|
||||
|
||||
} catch (NoSuchFieldError ignored) {
|
||||
|
||||
// no standard shulker box in old versions
|
||||
}
|
||||
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(14)) {
|
||||
|
||||
additionalChestMaterials.add(Material.valueOf("BARREL"));
|
||||
|
||||
}
|
||||
|
||||
} catch (NoSuchFieldError | IllegalArgumentException ignored) {
|
||||
|
||||
// no shulker box support in very old versions
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDisable() {
|
||||
|
||||
for (Player p : playerStateInfoMap.keySet()) {
|
||||
StateInfo stateInfo = playerStateInfoMap.remove(p);
|
||||
if (stateInfo == null) continue;
|
||||
restoreState(stateInfo, p);
|
||||
|
||||
final StateInfo stateInfo = playerStateInfoMap.remove(p);
|
||||
if (stateInfo == null) {
|
||||
|
||||
continue;
|
||||
|
||||
}
|
||||
|
||||
restoreState(stateInfo, p);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.LOWEST)
|
||||
public void onSpectatorClick(InventoryClickEvent e) {
|
||||
if (!(e.getWhoClicked() instanceof Player))
|
||||
|
||||
if (!(e.getWhoClicked() instanceof Player)) {
|
||||
|
||||
return;
|
||||
Player p = (Player) e.getWhoClicked();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) return;
|
||||
if (!playerStateInfoMap.containsKey(p)) return;
|
||||
if (p.getGameMode() == GameMode.SPECTATOR) {
|
||||
e.setCancelled(false);
|
||||
|
||||
}
|
||||
|
||||
final Player p = (Player) e.getWhoClicked();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (!playerStateInfoMap.containsKey(p)) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (p.getGameMode() == GameMode.SPECTATOR) {
|
||||
|
||||
e.setCancelled(false);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR)
|
||||
public void onQuit(PlayerQuitEvent e) {
|
||||
Player p = e.getPlayer();
|
||||
StateInfo stateInfo = playerStateInfoMap.remove(p);
|
||||
if (stateInfo == null) return;
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
final StateInfo stateInfo = playerStateInfoMap.remove(p);
|
||||
if (stateInfo == null) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
restoreState(stateInfo, p);
|
||||
|
||||
playerStateInfoMap.remove(p);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onTeleport(PlayerTeleportEvent e) {
|
||||
Player p = e.getPlayer();
|
||||
if (playerStateInfoMap.containsKey(p)
|
||||
&& e.getCause() == PlayerTeleportEvent.TeleportCause.SPECTATE) {
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
if (playerStateInfoMap.containsKey(p) && e.getCause() == PlayerTeleportEvent.TeleportCause.SPECTATE) {
|
||||
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onReappear(PlayerShowEvent e) {
|
||||
Player p = e.getPlayer();
|
||||
StateInfo stateInfo = playerStateInfoMap.remove(p);
|
||||
if (stateInfo == null) return;
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
final StateInfo stateInfo = playerStateInfoMap.remove(p);
|
||||
if (stateInfo == null) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
p.closeInventory();
|
||||
|
||||
restoreState(stateInfo, p);
|
||||
|
||||
playerStateInfoMap.remove(p);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onMove(PlayerMoveEvent e) {
|
||||
Player p = e.getPlayer();
|
||||
if (playerStateInfoMap.containsKey(p)) {
|
||||
Location loc = e.getTo() != null ? e.getTo() : e.getFrom();
|
||||
if (playerStateInfoMap.get(p).openLoc.distance(loc) > .5) {
|
||||
p.closeInventory();
|
||||
restoreState(playerStateInfoMap.get(p), p);
|
||||
playerStateInfoMap.remove(p);
|
||||
}
|
||||
}
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
if (!playerStateInfoMap.containsKey(p)) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onGameModeChange(PlayerGameModeChangeEvent e) {
|
||||
Player p = e.getPlayer();
|
||||
if (playerStateInfoMap.containsKey(p) && e.getNewGameMode() != GameMode.SPECTATOR) {
|
||||
// Don't let low-priority event listeners cancel the gamemode change
|
||||
if (e.isCancelled()) e.setCancelled(false);
|
||||
final Location loc = e.getTo() != null ? e.getTo() : e.getFrom();
|
||||
if (playerStateInfoMap.get(p).openLoc.distance(loc) <= .5) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
p.closeInventory();
|
||||
|
||||
restoreState(playerStateInfoMap.get(p), p);
|
||||
|
||||
playerStateInfoMap.remove(p);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.NORMAL)
|
||||
public void onGameModeChange(PlayerGameModeChangeEvent e) {
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
final boolean condition = playerStateInfoMap.containsKey(p) && e.getNewGameMode() != GameMode.SPECTATOR
|
||||
&& e.isCancelled();
|
||||
// Don't let low-priority event listeners cancel the gamemode change.
|
||||
if (condition) {
|
||||
|
||||
e.setCancelled(false);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onChestInteract(PlayerInteractEvent e) {
|
||||
Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId())
|
||||
|| !p.hasPermission("sv.silentchest")) return;
|
||||
if (e.getAction() != Action.RIGHT_CLICK_BLOCK) return;
|
||||
if (p.getGameMode() == GameMode.SPECTATOR) return;
|
||||
// Remember to keep "p.getItemInHand() != null" as we can't ensure that older Spigot versions will always return a non-null value
|
||||
//noinspection deprecation,ConstantConditions
|
||||
if (p.isSneaking() && p.getItemInHand() != null
|
||||
&& (p.getItemInHand().getType().isBlock() || p.getItemInHand().getType() == ITEM_FRAME)
|
||||
&& p.getItemInHand().getType() != Material.AIR)
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()) || !p.hasPermission("sv.silentchest")) {
|
||||
|
||||
return;
|
||||
Block block = e.getClickedBlock();
|
||||
if (block == null) return;
|
||||
|
||||
}
|
||||
|
||||
if (e.getAction() != Action.RIGHT_CLICK_BLOCK) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (p.getGameMode() == GameMode.SPECTATOR) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
final ItemStack heldItem = p.getInventory().getItemInMainHand();
|
||||
if (p.isSneaking() && heldItem != null && (heldItem.getType().isBlock() || heldItem.getType() == ITEM_FRAME)
|
||||
&& heldItem.getType() != Material.AIR)
|
||||
{
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
final Block block = e.getClickedBlock();
|
||||
if (block == null) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (block.getType() == ENDER_CHEST) {
|
||||
|
||||
e.setCancelled(true);
|
||||
p.openInventory(p.getEnderChest());
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (!(block.getType() == CHEST || block.getType() == TRAPPED_CHEST
|
||||
|| plugin.getVersionUtil().isOneDotXOrHigher(11) && additionalChestMaterials.contains(block.getType())))
|
||||
{
|
||||
|
||||
return;
|
||||
StateInfo stateInfo = StateInfo.extract(p);
|
||||
|
||||
}
|
||||
|
||||
final StateInfo stateInfo = StateInfo.extract(p);
|
||||
|
||||
p.setVelocity(new Vector(0, 0, 0));
|
||||
|
||||
playerStateInfoMap.put(p, stateInfo);
|
||||
|
||||
p.setGameMode(GameMode.SPECTATOR);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onChestClose(InventoryCloseEvent e) {
|
||||
if (!(e.getPlayer() instanceof Player))
|
||||
|
||||
if (!(e.getPlayer() instanceof Player)) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
final Player p = (Player) e.getPlayer();
|
||||
if (!playerStateInfoMap.containsKey(p)) return;
|
||||
if (!playerStateInfoMap.containsKey(p)) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
if (!isSilentOpenInventory(e.getView())) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
new BukkitRunnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
StateInfo stateInfo = playerStateInfoMap.get(p);
|
||||
if (stateInfo == null) return;
|
||||
restoreState(stateInfo, p);
|
||||
playerStateInfoMap.remove(p);
|
||||
|
||||
final StateInfo stateInfo = playerStateInfoMap.get(p);
|
||||
if (stateInfo == null) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
restoreState(stateInfo, p);
|
||||
|
||||
playerStateInfoMap.remove(p);
|
||||
|
||||
}
|
||||
|
||||
}.runTaskLater(plugin, 1);
|
||||
|
||||
}
|
||||
|
||||
private void restoreState(StateInfo stateInfo, Player p) {
|
||||
|
||||
p.setGameMode(stateInfo.gameMode);
|
||||
p.teleport(p.getLocation().add(0, 0.2, 0));
|
||||
new BukkitRunnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
p.setAllowFlight(stateInfo.canFly);
|
||||
p.setFlying(stateInfo.isFlying);
|
||||
|
||||
}
|
||||
|
||||
}.runTaskLater(plugin, 1);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
|
||||
return plugin.getSettings().getBoolean("InvisibilityFeatures.OpenChestsSilently")
|
||||
&& !(plugin.getPluginHookMgr() != null && plugin.getPluginHookMgr().isHookActive(OpenInvHook.class));
|
||||
|
||||
}
|
||||
|
||||
private boolean isShulkerBox(Inventory inv) {
|
||||
|
||||
try {
|
||||
|
||||
return inv.getType() == InventoryType.SHULKER_BOX;
|
||||
|
||||
} catch (NoSuchFieldError e) {
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean isShulkerBox(InventoryView inv) {
|
||||
try {
|
||||
return inv.getType() == InventoryType.SHULKER_BOX;
|
||||
} catch (NoSuchFieldError e) {
|
||||
return false;
|
||||
|
||||
return isShulkerBox(inv.getTopInventory());
|
||||
|
||||
}
|
||||
|
||||
private boolean isBarrel(InventoryView inv) {
|
||||
|
||||
try {
|
||||
|
||||
return inv.getType() == InventoryType.BARREL;
|
||||
|
||||
} catch (NoSuchFieldError e) {
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean isSilentOpenInventory(InventoryView inv) {
|
||||
|
||||
return inv.getType() == InventoryType.CHEST || inv.getType() == InventoryType.ENDER_CHEST || isShulkerBox(inv)
|
||||
|| isBarrel(inv);
|
||||
|
||||
}
|
||||
|
||||
public boolean hasSilentlyOpenedChest(Player p) {
|
||||
|
||||
return playerStateInfoMap.containsKey(p);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onEnable() {
|
||||
if (!plugin.getVersionUtil().isOneDotXOrHigher(19)) {
|
||||
SilentOpenChestPacketAdapter packetAdapter = new SilentOpenChestPacketAdapter(this);
|
||||
|
||||
// ProtocolLib 5.0 maps PLAYER_INFO to ClientboundPlayerInfoUpdatePacket
|
||||
final SilentOpenChestPacketAdapter packetAdapter = new SilentOpenChestPacketAdapter(this);
|
||||
ProtocolLibrary.getProtocolManager().addPacketListener(packetAdapter);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private static class StateInfo {
|
||||
|
||||
private final boolean canFly, isFlying;
|
||||
private final GameMode gameMode;
|
||||
private final Location openLoc;
|
||||
|
||||
StateInfo(boolean canFly, boolean isFlying, GameMode gameMode, Location openLoc) {
|
||||
this.canFly = canFly;
|
||||
this.isFlying = isFlying;
|
||||
this.gameMode = gameMode;
|
||||
this.openLoc = openLoc;
|
||||
}
|
||||
private record StateInfo(boolean canFly, boolean isFlying, GameMode gameMode, Location openLoc) {
|
||||
|
||||
static StateInfo extract(Player p) {
|
||||
return new StateInfo(
|
||||
p.getAllowFlight(),
|
||||
p.isFlying(),
|
||||
p.getGameMode(),
|
||||
p.getLocation()
|
||||
);
|
||||
|
||||
return new StateInfo(p.getAllowFlight(), p.isFlying(), p.getGameMode(), p.getLocation());
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -2,7 +2,7 @@
|
||||
* Copyright © 2015, Leon Mangler and the SuperVanish contributors
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* license, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
@@ -20,11 +20,17 @@ import org.bukkit.entity.Player;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
|
||||
import static com.comphenix.protocol.PacketType.Play.Server.*;
|
||||
|
||||
/**
|
||||
* This is currently unused on Minecraft 1.19 or higher
|
||||
* Adapter that masks a vanished player's silent-chest spectator state from
|
||||
* other clients. On Purpur 1.19.4 ProtocolLib's PLAYER_INFO type maps to
|
||||
* ClientboundPlayerInfoUpdatePacket which carries a Set<Action> instead of the
|
||||
* legacy single action; ViaSuite handles client-side re-encoding for connected
|
||||
* versions 1.8-1.21.x.
|
||||
*/
|
||||
public class SilentOpenChestPacketAdapter extends PacketAdapter {
|
||||
|
||||
@@ -33,90 +39,167 @@ public class SilentOpenChestPacketAdapter extends PacketAdapter {
|
||||
private boolean suppressErrors = false;
|
||||
|
||||
public SilentOpenChestPacketAdapter(SilentOpenChest silentOpenChest) {
|
||||
super(silentOpenChest.plugin, ListenerPriority.LOW, PLAYER_INFO, ABILITIES,
|
||||
ENTITY_METADATA);
|
||||
|
||||
super(silentOpenChest.plugin, ListenerPriority.LOW, PLAYER_INFO, ABILITIES, ENTITY_METADATA);
|
||||
this.silentOpenChest = silentOpenChest;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPacketSending(PacketEvent event) {
|
||||
|
||||
try {
|
||||
|
||||
Player receiver = event.getPlayer();
|
||||
if (receiver == null) return;
|
||||
if (receiver == null)
|
||||
return;
|
||||
if (event.getPacketType() == PLAYER_INFO) {
|
||||
|
||||
// multiple events share same packet object
|
||||
event.setPacket(event.getPacket().shallowClone());
|
||||
|
||||
List<PlayerInfoData> infoDataList = new ArrayList<>(
|
||||
event.getPacket().getPlayerInfoDataLists().read(0));
|
||||
if (!isGameModeUpdate(event))
|
||||
return;
|
||||
|
||||
List<PlayerInfoData> infoDataList = new ArrayList<>(event.getPacket().getPlayerInfoDataLists().read(0));
|
||||
boolean modified = false;
|
||||
for (PlayerInfoData infoData : ImmutableList.copyOf(infoDataList)) {
|
||||
if (!silentOpenChest.plugin.getVisibilityChanger().getHider()
|
||||
.isHidden(infoData.getProfile().getUUID(), receiver)
|
||||
&& silentOpenChest.plugin.getVanishStateMgr()
|
||||
.isVanished(infoData.getProfile().getUUID())) {
|
||||
Player vanishedTabPlayer = Bukkit.getPlayer(infoData.getProfile().getUUID());
|
||||
if (infoData.getGameMode() == EnumWrappers.NativeGameMode.SPECTATOR
|
||||
&& silentOpenChest.hasSilentlyOpenedChest(vanishedTabPlayer)
|
||||
&& event.getPacket().getPlayerInfoAction().read(0)
|
||||
== EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE) {
|
||||
int latency;
|
||||
try {
|
||||
latency = infoData.getLatency();
|
||||
} catch (NoSuchMethodError e) {
|
||||
latency = 21;
|
||||
}
|
||||
PlayerInfoData newData = new PlayerInfoData(infoData.getProfile(),
|
||||
latency, EnumWrappers.NativeGameMode.SURVIVAL,
|
||||
infoData.getDisplayName());
|
||||
infoDataList.remove(infoData);
|
||||
infoDataList.add(newData);
|
||||
}
|
||||
}
|
||||
|
||||
UUID uuid = extractUUID(infoData);
|
||||
if (uuid == null)
|
||||
continue;
|
||||
if (silentOpenChest.plugin.getVisibilityChanger().getHider().isHidden(uuid, receiver))
|
||||
continue;
|
||||
if (!silentOpenChest.plugin.getVanishStateMgr().isVanished(uuid))
|
||||
continue;
|
||||
if (infoData.getGameMode() != EnumWrappers.NativeGameMode.SPECTATOR)
|
||||
continue;
|
||||
|
||||
Player vanishedTabPlayer = Bukkit.getPlayer(uuid);
|
||||
if (vanishedTabPlayer == null || !silentOpenChest.hasSilentlyOpenedChest(vanishedTabPlayer))
|
||||
continue;
|
||||
|
||||
PlayerInfoData newData = new PlayerInfoData(uuid, infoData.getLatency(), infoData.isListed(),
|
||||
EnumWrappers.NativeGameMode.SURVIVAL, infoData.getProfile(), infoData.getDisplayName(),
|
||||
infoData.getRemoteChatSessionData());
|
||||
int index = infoDataList.indexOf(infoData);
|
||||
infoDataList.set(index, newData);
|
||||
modified = true;
|
||||
|
||||
}
|
||||
|
||||
if (modified)
|
||||
event.getPacket().getPlayerInfoDataLists().write(0, infoDataList);
|
||||
|
||||
} else if (event.getPacketType() == GAME_STATE_CHANGE) {
|
||||
|
||||
// Currently unused due to ProtocolLib class loading bug
|
||||
if (silentOpenChest.plugin.getVanishStateMgr().isVanished(
|
||||
receiver.getUniqueId())) {
|
||||
if (silentOpenChest.plugin.getVanishStateMgr().isVanished(receiver.getUniqueId())) {
|
||||
|
||||
try {
|
||||
if (event.getPacket().getIntegers().read(0) != 3) return;
|
||||
|
||||
if (event.getPacket().getIntegers().read(0) != 3)
|
||||
return;
|
||||
|
||||
} catch (FieldAccessException e) {
|
||||
|
||||
// TODO
|
||||
}
|
||||
if (!silentOpenChest.hasSilentlyOpenedChest(receiver)) return;
|
||||
|
||||
if (!silentOpenChest.hasSilentlyOpenedChest(receiver))
|
||||
return;
|
||||
event.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
} else if (event.getPacketType() == ABILITIES) {
|
||||
if (silentOpenChest.plugin.getVanishStateMgr().isVanished(
|
||||
receiver.getUniqueId())) {
|
||||
if (!silentOpenChest.hasSilentlyOpenedChest(receiver)) return;
|
||||
|
||||
if (silentOpenChest.plugin.getVanishStateMgr().isVanished(receiver.getUniqueId())) {
|
||||
|
||||
if (!silentOpenChest.hasSilentlyOpenedChest(receiver))
|
||||
return;
|
||||
event.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
} else if (event.getPacketType() == ENTITY_METADATA) {
|
||||
|
||||
int entityID = event.getPacket().getIntegers().read(0);
|
||||
if (entityID == receiver.getEntityId()) {
|
||||
if (silentOpenChest.plugin.getVanishStateMgr().isVanished(
|
||||
receiver.getUniqueId())) {
|
||||
if (!silentOpenChest.hasSilentlyOpenedChest(receiver)) return;
|
||||
|
||||
if (silentOpenChest.plugin.getVanishStateMgr().isVanished(receiver.getUniqueId())) {
|
||||
|
||||
if (!silentOpenChest.hasSilentlyOpenedChest(receiver))
|
||||
return;
|
||||
event.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception | NoClassDefFoundError e) {
|
||||
|
||||
if (!suppressErrors) {
|
||||
if (e.getMessage() == null
|
||||
|| !e.getMessage().endsWith("is not supported for temporary players.")) {
|
||||
|
||||
if (e.getMessage() == null || !e.getMessage().endsWith("is not supported for temporary players.")) {
|
||||
|
||||
silentOpenChest.plugin.logException(e);
|
||||
silentOpenChest.plugin.getLogger().warning("IMPORTANT: Please make sure that you are using the latest " +
|
||||
"dev-build of ProtocolLib and that your server is up-to-date! This error likely " +
|
||||
"happened inside of ProtocolLib code which is out of SuperVanish's control. It's part " +
|
||||
"of an optional feature module and can be removed safely by disabling " +
|
||||
"OpenChestsSilently in the config file. Please report this " +
|
||||
"error if you can reproduce it on an up-to-date server with only latest " +
|
||||
"ProtocolLib and latest SV installed.");
|
||||
silentOpenChest.plugin.getLogger()
|
||||
.warning("IMPORTANT: Please make sure that you are using the latest "
|
||||
+ "dev-build of ProtocolLib and that your server is up-to-date! This error likely "
|
||||
+ "happened inside of ProtocolLib code which is out of SuperVanish's control. It's part "
|
||||
+ "of an optional feature module and can be removed safely by disabling "
|
||||
+ "OpenChestsSilently in the config file. Please report this "
|
||||
+ "error if you can reproduce it on an up-to-date server with only latest "
|
||||
+ "ProtocolLib and latest SV installed.");
|
||||
suppressErrors = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean isGameModeUpdate(PacketEvent event) {
|
||||
|
||||
// 1.19.3+: ClientboundPlayerInfoUpdatePacket exposes Set<Action>
|
||||
try {
|
||||
|
||||
Set<EnumWrappers.PlayerInfoAction> actions = event.getPacket().getPlayerInfoActions().read(0);
|
||||
if (actions != null)
|
||||
return actions.contains(EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE);
|
||||
|
||||
} catch (FieldAccessException | IllegalArgumentException ignored) {
|
||||
|
||||
// legacy single-action packet on pre-1.19.3
|
||||
}
|
||||
|
||||
try {
|
||||
|
||||
EnumWrappers.PlayerInfoAction action = event.getPacket().getPlayerInfoAction().read(0);
|
||||
return action == EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE;
|
||||
|
||||
} catch (FieldAccessException | IllegalArgumentException ignored) {
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private UUID extractUUID(PlayerInfoData infoData) {
|
||||
|
||||
UUID uuid = infoData.getProfileId();
|
||||
if (uuid != null)
|
||||
return uuid;
|
||||
if (infoData.getProfile() != null)
|
||||
return infoData.getProfile().getUUID();
|
||||
return null;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -14,158 +14,290 @@ import com.comphenix.protocol.events.ListenerPriority;
|
||||
import com.comphenix.protocol.events.PacketAdapter;
|
||||
import com.comphenix.protocol.events.PacketContainer;
|
||||
import com.comphenix.protocol.events.PacketEvent;
|
||||
import com.comphenix.protocol.reflect.FieldAccessException;
|
||||
import com.comphenix.protocol.wrappers.EnumWrappers;
|
||||
import com.comphenix.protocol.wrappers.PlayerInfoData;
|
||||
import com.comphenix.protocol.wrappers.WrappedChatComponent;
|
||||
import com.comphenix.protocol.wrappers.WrappedGameProfile;
|
||||
import com.comphenix.protocol.wrappers.WrappedRemoteChatSessionData;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import de.myzelyam.api.vanish.PlayerShowEvent;
|
||||
import de.myzelyam.api.vanish.PostPlayerHideEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.player.PlayerJoinEvent;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.EnumSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
import java.util.concurrent.ThreadLocalRandom;
|
||||
|
||||
import static com.comphenix.protocol.PacketType.Play.Server.PLAYER_INFO;
|
||||
|
||||
/**
|
||||
* This is currently unused on Minecraft 1.19 or higher
|
||||
* Marks visible vanished players as spectators in player info updates. On
|
||||
* Purpur 1.19.4 this operates on the server-native
|
||||
* ClientboundPlayerInfoUpdatePacket format and ViaSuite handles translation for
|
||||
* connected 1.8-1.21.x clients.
|
||||
*/
|
||||
public class VanishIndication extends Feature {
|
||||
|
||||
private boolean suppressErrors = false;
|
||||
|
||||
public VanishIndication(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isActive() {
|
||||
return !plugin.getVersionUtil().isOneDotXOrHigher(19)
|
||||
&& plugin.getSettings().getBoolean("IndicationFeatures.MarkVanishedPlayersAsSpectators");
|
||||
|
||||
return plugin.getSettings().getBoolean("IndicationFeatures.MarkVanishedPlayersAsSpectators");
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onVanish(PostPlayerHideEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
|
||||
if (!plugin.getVisibilityChanger().getHider().isHidden(p, onlinePlayer) && p != onlinePlayer) {
|
||||
|
||||
sendPlayerInfoChangeGameModePacket(onlinePlayer, p, true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onReappear(PlayerShowEvent e) {
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
for (final Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
|
||||
if (!plugin.getVisibilityChanger().getHider().isHidden(p, onlinePlayer) && p != onlinePlayer) {
|
||||
|
||||
delay(() -> sendPlayerInfoChangeGameModePacket(onlinePlayer, p, false));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onJoin(PlayerJoinEvent e) {
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
delay(() -> {
|
||||
|
||||
// tell others that p is a spectator
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
if (!plugin.getVisibilityChanger().getHider().isHidden(p, onlinePlayer)
|
||||
&& p != onlinePlayer) {
|
||||
|
||||
if (!plugin.getVisibilityChanger().getHider().isHidden(p, onlinePlayer) && p != onlinePlayer) {
|
||||
|
||||
sendPlayerInfoChangeGameModePacket(onlinePlayer, p, true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
// tell p that others are spectators
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers()) {
|
||||
if (!plugin.getVanishStateMgr().isVanished(onlinePlayer.getUniqueId())) continue;
|
||||
if (!plugin.getVisibilityChanger().getHider().isHidden(onlinePlayer, p)
|
||||
&& p != onlinePlayer) {
|
||||
|
||||
if (!plugin.getVanishStateMgr().isVanished(onlinePlayer.getUniqueId()))
|
||||
continue;
|
||||
if (!plugin.getVisibilityChanger().getHider().isHidden(onlinePlayer, p) && p != onlinePlayer) {
|
||||
|
||||
sendPlayerInfoChangeGameModePacket(p, onlinePlayer, true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onEnable() {
|
||||
|
||||
ProtocolLibrary.getProtocolManager().addPacketListener(
|
||||
new PacketAdapter(plugin, ListenerPriority.NORMAL, PacketType.Play.Server.PLAYER_INFO) {
|
||||
new PacketAdapter(plugin, ListenerPriority.NORMAL, PacketType.Play.Server.PLAYER_INFO)
|
||||
{
|
||||
|
||||
@Override
|
||||
public void onPacketSending(PacketEvent event) {
|
||||
|
||||
try {
|
||||
|
||||
// multiple events share same packet object
|
||||
event.setPacket(event.getPacket().shallowClone());
|
||||
List<PlayerInfoData> infoDataList = new ArrayList<>(
|
||||
event.getPacket().getPlayerInfoDataLists().read(0));
|
||||
Player receiver = event.getPlayer();
|
||||
for (PlayerInfoData infoData : ImmutableList.copyOf(infoDataList)) {
|
||||
|
||||
try {
|
||||
if (!VanishIndication.this.plugin.getVisibilityChanger().getHider()
|
||||
.isHidden(infoData.getProfile().getUUID(), receiver)
|
||||
&& VanishIndication.this.plugin.getVanishStateMgr()
|
||||
.isVanished(infoData.getProfile().getUUID())) {
|
||||
if (!receiver.getUniqueId().equals(infoData.getProfile().getUUID()))
|
||||
if (infoData.getGameMode() != EnumWrappers.NativeGameMode.SPECTATOR) {
|
||||
int latency;
|
||||
try {
|
||||
latency = infoData.getLatency();
|
||||
} catch (NoSuchMethodError e) {
|
||||
latency = 21;
|
||||
}
|
||||
if (event.getPacket().getPlayerInfoAction().read(0)
|
||||
!= EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE) {
|
||||
|
||||
if (!isGameModeUpdate(event))
|
||||
break;
|
||||
|
||||
if (extractUUID(infoData) == null)
|
||||
continue;
|
||||
if (!VanishIndication.this.plugin.getVisibilityChanger().getHider()
|
||||
.isHidden(extractUUID(infoData), receiver)
|
||||
&& VanishIndication.this.plugin.getVanishStateMgr()
|
||||
.isVanished(extractUUID(infoData)))
|
||||
{
|
||||
|
||||
if (!receiver.getUniqueId().equals(extractUUID(infoData)))
|
||||
if (infoData.getGameMode() != EnumWrappers.NativeGameMode.SPECTATOR) {
|
||||
|
||||
PlayerInfoData newData = createGameModeUpdate(infoData,
|
||||
EnumWrappers.NativeGameMode.SPECTATOR);
|
||||
int index = infoDataList.indexOf(infoData);
|
||||
infoDataList.set(index, newData);
|
||||
|
||||
}
|
||||
PlayerInfoData newData = new PlayerInfoData(infoData.getProfile(),
|
||||
latency, EnumWrappers.NativeGameMode.SPECTATOR,
|
||||
infoData.getDisplayName());
|
||||
infoDataList.remove(infoData);
|
||||
infoDataList.add(newData);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (UnsupportedOperationException ignored) {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
event.getPacket().getPlayerInfoDataLists().write(0, infoDataList);
|
||||
|
||||
} catch (Exception | NoClassDefFoundError e) {
|
||||
|
||||
if (!suppressErrors) {
|
||||
|
||||
VanishIndication.this.plugin.logException(e);
|
||||
plugin.getLogger().warning("IMPORTANT: Please make sure that you are using the latest " +
|
||||
"dev-build of ProtocolLib and that your server is up-to-date! This error likely " +
|
||||
"happened inside of ProtocolLib code which is out of SuperVanish's control. It's part " +
|
||||
"of an optional feature module and can be removed safely by disabling " +
|
||||
"MarkVanishedPlayersAsSpectators in the config file. Please report this " +
|
||||
"error if you can reproduce it on an up-to-date server with only latest " +
|
||||
"ProtocolLib and latest SV installed.");
|
||||
plugin.getLogger().warning("IMPORTANT: Please make sure that you are using the latest "
|
||||
+ "dev-build of ProtocolLib and that your server is up-to-date! This error likely "
|
||||
+ "happened inside of ProtocolLib code which is out of SuperVanish's control. It's part "
|
||||
+ "of an optional feature module and can be removed safely by disabling "
|
||||
+ "MarkVanishedPlayersAsSpectators in the config file. Please report this "
|
||||
+ "error if you can reproduce it on an up-to-date server with only latest "
|
||||
+ "ProtocolLib and latest SV installed.");
|
||||
suppressErrors = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
private void sendPlayerInfoChangeGameModePacket(Player p, Player change, boolean spectator) {
|
||||
|
||||
PacketContainer packet = new PacketContainer(PLAYER_INFO);
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(19)) {
|
||||
|
||||
packet.getPlayerInfoActions().write(0, EnumSet.of(EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE));
|
||||
|
||||
} else {
|
||||
|
||||
packet.getPlayerInfoAction().write(0, EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE);
|
||||
|
||||
}
|
||||
|
||||
List<PlayerInfoData> data = new ArrayList<>();
|
||||
int ping = ThreadLocalRandom.current().nextInt(20) + 15;
|
||||
data.add(new PlayerInfoData(WrappedGameProfile.fromPlayer(change), ping,
|
||||
spectator ? EnumWrappers.NativeGameMode.SPECTATOR
|
||||
: EnumWrappers.NativeGameMode.fromBukkit(change.getGameMode()),
|
||||
WrappedChatComponent.fromText(change.getPlayerListName())));
|
||||
EnumWrappers.NativeGameMode gameMode = spectator ? EnumWrappers.NativeGameMode.SPECTATOR
|
||||
: EnumWrappers.NativeGameMode.fromBukkit(change.getGameMode());
|
||||
WrappedChatComponent displayName = WrappedChatComponent
|
||||
.fromText(LegacyComponentSerializer.legacySection().serialize(change.playerListName()));
|
||||
WrappedGameProfile profile = WrappedGameProfile.fromPlayer(change);
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(19)) {
|
||||
|
||||
data.add(new PlayerInfoData(change.getUniqueId(), ping, true, gameMode, profile, displayName,
|
||||
(WrappedRemoteChatSessionData) null));
|
||||
|
||||
} else {
|
||||
|
||||
data.add(new PlayerInfoData(profile, ping, gameMode, displayName));
|
||||
|
||||
}
|
||||
|
||||
packet.getPlayerInfoDataLists().write(0, data);
|
||||
try {
|
||||
|
||||
ProtocolLibrary.getProtocolManager().sendServerPacket(p, packet);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
throw new RuntimeException("Cannot send packet", e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean isGameModeUpdate(PacketEvent event) {
|
||||
|
||||
try {
|
||||
|
||||
Set<EnumWrappers.PlayerInfoAction> actions = event.getPacket().getPlayerInfoActions().read(0);
|
||||
if (actions != null)
|
||||
return actions.contains(EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE);
|
||||
|
||||
} catch (FieldAccessException | IllegalArgumentException ignored) {
|
||||
|
||||
// legacy single-action packet on pre-1.19.3
|
||||
}
|
||||
|
||||
try {
|
||||
|
||||
EnumWrappers.PlayerInfoAction action = event.getPacket().getPlayerInfoAction().read(0);
|
||||
return action == EnumWrappers.PlayerInfoAction.UPDATE_GAME_MODE;
|
||||
|
||||
} catch (FieldAccessException | IllegalArgumentException ignored) {
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private UUID extractUUID(PlayerInfoData infoData) {
|
||||
|
||||
UUID uuid = infoData.getProfileId();
|
||||
if (uuid != null)
|
||||
return uuid;
|
||||
if (infoData.getProfile() != null)
|
||||
return infoData.getProfile().getUUID();
|
||||
return null;
|
||||
|
||||
}
|
||||
|
||||
private PlayerInfoData createGameModeUpdate(PlayerInfoData infoData, EnumWrappers.NativeGameMode gameMode) {
|
||||
|
||||
UUID uuid = extractUUID(infoData);
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(19)) {
|
||||
|
||||
return new PlayerInfoData(uuid, infoData.getLatency(), infoData.isListed(), gameMode, infoData.getProfile(),
|
||||
infoData.getDisplayName(), infoData.getRemoteChatSessionData());
|
||||
|
||||
}
|
||||
|
||||
return new PlayerInfoData(infoData.getProfile(), infoData.getLatency(), gameMode, infoData.getDisplayName());
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -26,44 +26,62 @@ import java.util.UUID;
|
||||
|
||||
public class CitizensHook extends PluginHook {
|
||||
|
||||
|
||||
public CitizensHook(SuperVanish superVanish) {
|
||||
|
||||
super(superVanish);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH, ignoreCancelled = true)
|
||||
public void onNPCTarget(NPCSpeechEvent e) {
|
||||
|
||||
e.setCancelled(!checkContext(e.getContext()));
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH, ignoreCancelled = true)
|
||||
public void onSpeechTargeted(SpeechEvent e) {
|
||||
|
||||
e.setCancelled(!checkContext(e.getContext()));
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return FALSE if the event should be cancelled, TRUE otherwise
|
||||
*/
|
||||
private boolean checkContext(SpeechContext context) {
|
||||
|
||||
// don't let it talk about hidden players
|
||||
for (UUID uuid : superVanish.getVanishStateMgr().getOnlineVanishedPlayers()) {
|
||||
|
||||
if (context.getMessage().contains(Bukkit.getPlayer(uuid).getName())) {
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// don't let hidden players receive it
|
||||
Iterator<Talkable> iterator = context.iterator();
|
||||
while (iterator.hasNext()) {
|
||||
|
||||
Talkable recipient = iterator.next();
|
||||
Entity entity = recipient.getEntity();
|
||||
if (!(entity instanceof Player))
|
||||
continue;
|
||||
Player player = (Player) entity;
|
||||
if (superVanish.getVanishStateMgr().isVanished(player.getUniqueId())) {
|
||||
|
||||
iterator.remove();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// cancel contexts with only hidden recipients
|
||||
return context.hasRecipients();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -24,52 +24,64 @@ public class DynmapHook extends PluginHook {
|
||||
private final SuperVanish superVanish;
|
||||
|
||||
public DynmapHook(SuperVanish superVanish) {
|
||||
|
||||
super(superVanish);
|
||||
this.superVanish = superVanish;
|
||||
sendJoinLeave
|
||||
= superVanish.getSettings().getBoolean("HookOptions.DynmapSendJoinLeaveMessages")
|
||||
sendJoinLeave = superVanish.getSettings().getBoolean("HookOptions.DynmapSendJoinLeaveMessages")
|
||||
&& !superVanish.getMessage("DynmapFakeJoin").equals("");
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onVanish(PlayerHideEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
DynmapAPI dynmap = (DynmapAPI) plugin;
|
||||
|
||||
dynmap.setPlayerVisiblity(p, false);
|
||||
if (sendJoinLeave)
|
||||
dynmap.sendBroadcastToWeb("",
|
||||
superVanish.replacePlaceholders(superVanish.getMessage("DynmapFakeQuit"), p));
|
||||
dynmap.sendBroadcastToWeb("", superVanish.replacePlaceholders(superVanish.getMessage("DynmapFakeQuit"), p));
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onReappear(PlayerShowEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
DynmapAPI dynmap = (DynmapAPI) plugin;
|
||||
|
||||
dynmap.setPlayerVisiblity(p, true);
|
||||
if (sendJoinLeave)
|
||||
dynmap.sendBroadcastToWeb("",
|
||||
superVanish.replacePlaceholders(superVanish.getMessage("DynmapFakeJoin"), p));
|
||||
dynmap.sendBroadcastToWeb("", superVanish.replacePlaceholders(superVanish.getMessage("DynmapFakeJoin"), p));
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.LOWEST)
|
||||
public void onJoin(PlayerJoinEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
DynmapAPI dynmap = (DynmapAPI) plugin;
|
||||
|
||||
if (superVanish.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
dynmap.setPlayerVisiblity(p, false);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR)
|
||||
public void onQuit(PlayerQuitEvent e) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
DynmapAPI dynmap = (DynmapAPI) plugin;
|
||||
|
||||
if (superVanish.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
dynmap.setPlayerVisiblity(p, true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -37,87 +37,129 @@ public class EssentialsHook extends PluginHook {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
try {
|
||||
if (!Bukkit.getPluginManager().isPluginEnabled("Essentials")) return;
|
||||
|
||||
if (!Bukkit.getPluginManager().isPluginEnabled("Essentials"))
|
||||
return;
|
||||
for (UUID uuid : superVanish.getVanishStateMgr().getOnlineVanishedPlayers()) {
|
||||
|
||||
Player p = Bukkit.getPlayer(uuid);
|
||||
User user = essentials.getUser(p);
|
||||
if (user == null) continue;
|
||||
if (user == null)
|
||||
continue;
|
||||
if (!user.isHidden())
|
||||
user.setHidden(true);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
cancel();
|
||||
superVanish.logException(e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
private BukkitTask forcedInvisibilityTask;
|
||||
|
||||
public EssentialsHook(SuperVanish superVanish) {
|
||||
|
||||
super(superVanish);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPluginEnable(Plugin plugin) {
|
||||
|
||||
essentials = (Essentials) plugin;
|
||||
forcedInvisibilityTask = forcedInvisibilityRunnable.runTaskTimer(superVanish, 0, 100);
|
||||
forcedInvisibilityRunnable.run();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPluginDisable(Plugin plugin) {
|
||||
|
||||
essentials = null;
|
||||
forcedInvisibilityTask.cancel();
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.LOW)
|
||||
public void onJoin(PlayerJoinEvent e) {
|
||||
|
||||
User user = essentials.getUser(e.getPlayer());
|
||||
if (user == null) return;
|
||||
if (user == null)
|
||||
return;
|
||||
if (superVanish.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId()) && !user.isHidden())
|
||||
user.setHidden(true);
|
||||
else user.setHidden(false);
|
||||
else
|
||||
user.setHidden(false);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onVanish(PlayerHideEvent e) {
|
||||
|
||||
User user = essentials.getUser(e.getPlayer());
|
||||
if (user == null) return;
|
||||
if (user.isVanished()) user.setVanished(false);
|
||||
if (user == null)
|
||||
return;
|
||||
if (user.isVanished())
|
||||
user.setVanished(false);
|
||||
preVanishHiddenPlayers.remove(e.getPlayer().getUniqueId());
|
||||
user.setHidden(true);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onReappear(PostPlayerShowEvent e) {
|
||||
|
||||
User user = essentials.getUser(e.getPlayer());
|
||||
if (user == null) return;
|
||||
if (user == null)
|
||||
return;
|
||||
user.setHidden(false);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
|
||||
public void onCommand(final PlayerCommandPreprocessEvent e) {
|
||||
if (!CommandAction.VANISH_SELF.checkPermission(e.getPlayer(), superVanish)) return;
|
||||
if (superVanish.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId())) return;
|
||||
|
||||
if (!CommandAction.VANISH_SELF.checkPermission(e.getPlayer(), superVanish))
|
||||
return;
|
||||
if (superVanish.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId()))
|
||||
return;
|
||||
String command = e.getMessage().toLowerCase(Locale.ENGLISH).split(" ")[0].replace("/", "")
|
||||
.toLowerCase(Locale.ENGLISH);
|
||||
if (command.split(":").length > 1) command = command.split(":")[1];
|
||||
if (command.equals("supervanish") || command.equals("sv")
|
||||
|| command.equals("v") || command.equals("vanish")) {
|
||||
if (command.split(":").length > 1)
|
||||
command = command.split(":")[1];
|
||||
if (command.equals("supervanish") || command.equals("sv") || command.equals("v") || command.equals("vanish")) {
|
||||
|
||||
final User user = essentials.getUser(e.getPlayer());
|
||||
if (user == null || !user.isAfk()) return;
|
||||
if (user == null || !user.isAfk())
|
||||
return;
|
||||
user.setHidden(true);
|
||||
preVanishHiddenPlayers.add(e.getPlayer().getUniqueId());
|
||||
superVanish.getServer().getScheduler().runTaskLater(superVanish, new Runnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
if (preVanishHiddenPlayers.remove(e.getPlayer().getUniqueId())) {
|
||||
|
||||
user.setHidden(false);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}, 1);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -10,14 +10,22 @@ package de.myzelyam.supervanish.hooks;
|
||||
|
||||
public class InvalidPluginHookException extends RuntimeException {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
public InvalidPluginHookException() {
|
||||
|
||||
}
|
||||
|
||||
public InvalidPluginHookException(String message) {
|
||||
|
||||
super(message);
|
||||
|
||||
}
|
||||
|
||||
public InvalidPluginHookException(Throwable cause) {
|
||||
|
||||
super(cause);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,143 +0,0 @@
|
||||
/*
|
||||
* Copyright © 2015, Leon Mangler and the SuperVanish contributors
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
package de.myzelyam.supervanish.hooks;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.plugin.Plugin;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.ConcurrentModificationException;
|
||||
import java.util.UUID;
|
||||
|
||||
import be.maximvdw.placeholderapi.PlaceholderAPI;
|
||||
import be.maximvdw.placeholderapi.PlaceholderReplaceEvent;
|
||||
import be.maximvdw.placeholderapi.PlaceholderReplacer;
|
||||
|
||||
|
||||
public class MVdWPlaceholderAPIHook extends PluginHook {
|
||||
|
||||
private final String yes, no, prefix, suffix;
|
||||
|
||||
public MVdWPlaceholderAPIHook(SuperVanish superVanish) {
|
||||
super(superVanish);
|
||||
yes = superVanish.getMessage("PlaceholderIsVanishedYes");
|
||||
no = superVanish.getMessage("PlaceholderIsVanishedNo");
|
||||
prefix = superVanish.getMessage("PlaceholderVanishPrefix");
|
||||
suffix = superVanish.getMessage("PlaceholderVanishSuffix");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPluginEnable(Plugin plugin) {
|
||||
PlaceholderAPI.registerPlaceholder(superVanish, "supervanish_isvanished",
|
||||
e -> {
|
||||
try {
|
||||
Player p = e.getPlayer();
|
||||
if (p == null) return no;
|
||||
try {
|
||||
return superVanish.getVanishStateMgr().isVanished(p.getUniqueId()) ? yes
|
||||
: no;
|
||||
} catch (Exception er) {
|
||||
superVanish.logException(er);
|
||||
}
|
||||
return null;
|
||||
} catch (Throwable t) {
|
||||
if (!(t instanceof NoClassDefFoundError || t instanceof
|
||||
ConcurrentModificationException))
|
||||
superVanish.logException(t);
|
||||
return no;
|
||||
}
|
||||
});
|
||||
PlaceholderAPI.registerPlaceholder(superVanish, "supervanish_vanishprefix",
|
||||
e -> {
|
||||
try {
|
||||
Player p = e.getPlayer();
|
||||
if (p == null) return "";
|
||||
try {
|
||||
return superVanish.getVanishStateMgr().isVanished(p.getUniqueId()) ? prefix : "";
|
||||
} catch (Exception er) {
|
||||
superVanish.logException(er);
|
||||
}
|
||||
return null;
|
||||
} catch (Throwable t) {
|
||||
if (!(t instanceof NoClassDefFoundError || t instanceof
|
||||
ConcurrentModificationException))
|
||||
superVanish.logException(t);
|
||||
return "";
|
||||
}
|
||||
});
|
||||
PlaceholderAPI.registerPlaceholder(superVanish, "supervanish_vanishsuffix",
|
||||
e -> {
|
||||
try {
|
||||
Player p = e.getPlayer();
|
||||
if (p == null) return "";
|
||||
try {
|
||||
return superVanish.getVanishStateMgr().isVanished(p.getUniqueId()) ? suffix : "";
|
||||
} catch (Exception er) {
|
||||
superVanish.logException(er);
|
||||
}
|
||||
return null;
|
||||
} catch (Throwable t) {
|
||||
if (!(t instanceof NoClassDefFoundError || t instanceof
|
||||
ConcurrentModificationException))
|
||||
superVanish.logException(t);
|
||||
return "";
|
||||
}
|
||||
});
|
||||
PlaceholderAPI.registerPlaceholder(superVanish, "supervanish_vanishedplayers",
|
||||
e -> {
|
||||
try {
|
||||
Player p = e.getPlayer();
|
||||
Collection<UUID> onlineVanishedPlayers = superVanish.getVanishStateMgr()
|
||||
.getOnlineVanishedPlayers();
|
||||
String playerListMessage = "";
|
||||
for (UUID uuid : onlineVanishedPlayers) {
|
||||
Player onlineVanished = Bukkit.getPlayer(uuid);
|
||||
if (onlineVanished == null) continue;
|
||||
if (p != null && superVanish.getSettings().getBoolean(
|
||||
"IndicationFeatures.LayeredPermissions.HideInvisibleInCommands", false)
|
||||
&& !superVanish.hasPermissionToSee(p, onlineVanished)) {
|
||||
continue;
|
||||
}
|
||||
playerListMessage = playerListMessage + onlineVanished.getName() + ", ";
|
||||
}
|
||||
return playerListMessage.length() > 3
|
||||
? playerListMessage.substring(0, playerListMessage.length() - 2)
|
||||
: playerListMessage;
|
||||
} catch (Throwable t) {
|
||||
if (!(t instanceof NoClassDefFoundError || t instanceof
|
||||
ConcurrentModificationException))
|
||||
superVanish.logException(t);
|
||||
return "";
|
||||
}
|
||||
});
|
||||
PlaceholderAPI.registerPlaceholder(superVanish, "supervanish_playercount",
|
||||
e -> {
|
||||
try {
|
||||
Player p = e.getPlayer();
|
||||
int playercount = Bukkit.getOnlinePlayers().size();
|
||||
for (UUID uuid : superVanish.getVanishStateMgr()
|
||||
.getOnlineVanishedPlayers()) {
|
||||
Player onlineVanished = Bukkit.getPlayer(uuid);
|
||||
if (onlineVanished == null) continue;
|
||||
if (p == null || !superVanish.canSee(p, onlineVanished))
|
||||
playercount--;
|
||||
}
|
||||
return playercount + "";
|
||||
} catch (Throwable t) {
|
||||
if (!(t instanceof NoClassDefFoundError || t instanceof
|
||||
ConcurrentModificationException))
|
||||
superVanish.logException(t);
|
||||
return Bukkit.getOnlinePlayers().size() + "";
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,152 @@
|
||||
/*
|
||||
* Copyright © 2015, Leon Mangler and the SuperVanish contributors
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
package de.myzelyam.supervanish.hooks;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
import io.github.miniplaceholders.api.Expansion;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.minimessage.tag.Tag;
|
||||
import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.plugin.Plugin;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.UUID;
|
||||
|
||||
public class MiniPlaceholdersHook extends PluginHook {
|
||||
|
||||
private static final LegacyComponentSerializer LEGACY_SERIALIZER = LegacyComponentSerializer.legacyAmpersand();
|
||||
|
||||
private final String yes, no, prefix, suffix;
|
||||
private Expansion expansion;
|
||||
|
||||
public MiniPlaceholdersHook(SuperVanish superVanish) {
|
||||
|
||||
super(superVanish);
|
||||
yes = superVanish.getMessage("PlaceholderIsVanishedYes");
|
||||
no = superVanish.getMessage("PlaceholderIsVanishedNo");
|
||||
prefix = superVanish.getMessage("PlaceholderVanishPrefix");
|
||||
suffix = superVanish.getMessage("PlaceholderVanishSuffix");
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPluginEnable(Plugin plugin) {
|
||||
|
||||
expansion = Expansion.builder("supervanish")
|
||||
.audiencePlaceholder("isvanished", (audience, queue, ctx) -> textTag(isVanishedText(audience)))
|
||||
.audiencePlaceholder("vanishprefix",
|
||||
(audience, queue, ctx) -> componentTag(isVanished(audience) ? prefix : ""))
|
||||
.audiencePlaceholder("vanishsuffix",
|
||||
(audience, queue, ctx) -> componentTag(isVanished(audience) ? suffix : ""))
|
||||
.audiencePlaceholder("vanishedplayers", (audience, queue, ctx) -> textTag(getVanishedPlayers(audience)))
|
||||
.audiencePlaceholder("playercount",
|
||||
(audience, queue, ctx) -> textTag(String.valueOf(getPlayerCount(audience))))
|
||||
.build();
|
||||
expansion.register();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPluginDisable(Plugin plugin) {
|
||||
|
||||
if (expansion != null && expansion.registered()) {
|
||||
|
||||
expansion.unregister();
|
||||
|
||||
}
|
||||
|
||||
expansion = null;
|
||||
|
||||
}
|
||||
|
||||
private String isVanishedText(Object audience) {
|
||||
|
||||
return isVanished(audience) ? yes : no;
|
||||
|
||||
}
|
||||
|
||||
private boolean isVanished(Object audience) {
|
||||
|
||||
if (!(audience instanceof Player))
|
||||
return false;
|
||||
return superVanish.getVanishStateMgr().isVanished(((Player) audience).getUniqueId());
|
||||
|
||||
}
|
||||
|
||||
private String getVanishedPlayers(Object audience) {
|
||||
|
||||
Player viewer = audience instanceof Player ? (Player) audience : null;
|
||||
Collection<UUID> onlineVanishedPlayers = superVanish.getVanishStateMgr().getOnlineVanishedPlayers();
|
||||
StringBuilder playerListMessage = new StringBuilder();
|
||||
for (UUID uuid : onlineVanishedPlayers) {
|
||||
|
||||
Player onlineVanished = Bukkit.getPlayer(uuid);
|
||||
if (onlineVanished == null)
|
||||
continue;
|
||||
if (viewer != null
|
||||
&& superVanish.getSettings()
|
||||
.getBoolean("IndicationFeatures.LayeredPermissions.HideInvisibleInCommands", false)
|
||||
&& !superVanish.hasPermissionToSee(viewer, onlineVanished))
|
||||
{
|
||||
|
||||
continue;
|
||||
|
||||
}
|
||||
|
||||
if (playerListMessage.length() > 0) {
|
||||
|
||||
playerListMessage.append(", ");
|
||||
|
||||
}
|
||||
|
||||
playerListMessage.append(onlineVanished.getName());
|
||||
|
||||
}
|
||||
|
||||
return playerListMessage.toString();
|
||||
|
||||
}
|
||||
|
||||
private int getPlayerCount(Object audience) {
|
||||
|
||||
Player viewer = audience instanceof Player ? (Player) audience : null;
|
||||
int playerCount = Bukkit.getOnlinePlayers().size();
|
||||
for (UUID uuid : superVanish.getVanishStateMgr().getOnlineVanishedPlayers()) {
|
||||
|
||||
Player onlineVanished = Bukkit.getPlayer(uuid);
|
||||
if (onlineVanished == null)
|
||||
continue;
|
||||
if (viewer == null || !superVanish.canSee(viewer, onlineVanished)) {
|
||||
|
||||
playerCount--;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return playerCount;
|
||||
|
||||
}
|
||||
|
||||
private Tag textTag(String value) {
|
||||
|
||||
return Tag.selfClosingInserting(Component.text(value));
|
||||
|
||||
}
|
||||
|
||||
private Tag componentTag(String value) {
|
||||
|
||||
return Tag.selfClosingInserting(LEGACY_SERIALIZER.deserialize(value));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,6 +1,5 @@
|
||||
package de.myzelyam.supervanish.hooks;
|
||||
|
||||
import com.lishid.openinv.IOpenInv;
|
||||
import de.myzelyam.api.vanish.PlayerShowEvent;
|
||||
import de.myzelyam.api.vanish.PostPlayerHideEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
@@ -9,7 +8,9 @@ import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.player.PlayerJoinEvent;
|
||||
import org.bukkit.event.player.PlayerQuitEvent;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
@@ -21,98 +22,174 @@ public class OpenInvHook extends PluginHook {
|
||||
private final Set<UUID> alreadyHiddenBeforeVanishing = new HashSet<>();
|
||||
|
||||
public OpenInvHook(SuperVanish superVanish) {
|
||||
|
||||
super(superVanish);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onVanish(PostPlayerHideEvent e) {
|
||||
try {
|
||||
Player p = e.getPlayer();
|
||||
IOpenInv openInv = (IOpenInv) plugin;
|
||||
|
||||
if (openInv.getSilentContainerStatus(p)) {
|
||||
try {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
|
||||
if (getSilentContainerStatus(p)) {
|
||||
|
||||
alreadyHiddenBeforeVanishing.add(p.getUniqueId());
|
||||
|
||||
} else {
|
||||
if (!p.hasPermission("sv.silentchest")) return;
|
||||
openInv.setSilentContainerStatus(p, true);
|
||||
|
||||
if (!p.hasPermission("sv.silentchest"))
|
||||
return;
|
||||
setSilentContainerStatus(p, true);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception | NoSuchMethodError | NoClassDefFoundError er) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
superVanish.logException(er);
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
||||
public void onReappear(PlayerShowEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
IOpenInv openInv = (IOpenInv) plugin;
|
||||
|
||||
if (!alreadyHiddenBeforeVanishing.remove(p.getUniqueId())) {
|
||||
openInv.setSilentContainerStatus(p, false);
|
||||
|
||||
setSilentContainerStatus(p, false);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception | NoSuchMethodError | NoClassDefFoundError er) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
superVanish.logException(er);
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.LOW)
|
||||
public void onJoin(PlayerJoinEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
IOpenInv openInv = (IOpenInv) plugin;
|
||||
|
||||
if (superVanish.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
if (openInv.getSilentContainerStatus(p)) {
|
||||
|
||||
if (getSilentContainerStatus(p)) {
|
||||
|
||||
alreadyHiddenBeforeVanishing.add(p.getUniqueId());
|
||||
|
||||
} else {
|
||||
if (!p.hasPermission("sv.silentchest")) return;
|
||||
openInv.setSilentContainerStatus(p, true);
|
||||
|
||||
if (!p.hasPermission("sv.silentchest"))
|
||||
return;
|
||||
setSilentContainerStatus(p, true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception | NoSuchMethodError | NoClassDefFoundError er) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
superVanish.logException(er);
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR)
|
||||
public void onQuit(PlayerQuitEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
IOpenInv openInv = (IOpenInv) plugin;
|
||||
|
||||
if (superVanish.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
if (!alreadyHiddenBeforeVanishing.remove(p.getUniqueId())) {
|
||||
openInv.setSilentContainerStatus(p, false);
|
||||
|
||||
setSilentContainerStatus(p, false);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception | NoSuchMethodError | NoClassDefFoundError er) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
superVanish.logException(er);
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public boolean openPlayerInventory(Player vanished, Player target) {
|
||||
IOpenInv openInv = (IOpenInv) plugin;
|
||||
|
||||
try {
|
||||
openInv.openInventory(vanished, openInv.getSpecialInventory(target, true));
|
||||
|
||||
Method getSpecialInventoryMethod = plugin.getClass().getMethod("getSpecialInventory", Player.class,
|
||||
boolean.class);
|
||||
Inventory specialInventory = (Inventory) getSpecialInventoryMethod.invoke(plugin, target, true);
|
||||
Method openInventoryMethod = plugin.getClass().getMethod("openInventory", Player.class, Inventory.class);
|
||||
openInventoryMethod.invoke(plugin, vanished, specialInventory);
|
||||
|
||||
} catch (Exception | NoSuchMethodError | NoClassDefFoundError e) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
superVanish.logException(e);
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
private boolean getSilentContainerStatus(Player player) throws ReflectiveOperationException {
|
||||
|
||||
Method method = plugin.getClass().getMethod("getSilentContainerStatus", Player.class);
|
||||
return (Boolean) method.invoke(plugin, player);
|
||||
|
||||
}
|
||||
|
||||
private void setSilentContainerStatus(Player player, boolean status) throws ReflectiveOperationException {
|
||||
|
||||
Method method = plugin.getClass().getMethod("setSilentContainerStatus", Player.class, boolean.class);
|
||||
method.invoke(plugin, player, status);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,124 +0,0 @@
|
||||
/*
|
||||
* Copyright © 2015, Leon Mangler and the SuperVanish contributors
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
package de.myzelyam.supervanish.hooks;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import me.clip.placeholderapi.PlaceholderAPI;
|
||||
import me.clip.placeholderapi.expansion.PlaceholderExpansion;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.OfflinePlayer;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.UUID;
|
||||
|
||||
public class PlaceholderAPIHook extends PluginHook {
|
||||
|
||||
private final String yes, no, prefix, suffix;
|
||||
|
||||
public PlaceholderAPIHook(SuperVanish superVanish) {
|
||||
super(superVanish);
|
||||
yes = superVanish.getMessage("PlaceholderIsVanishedYes");
|
||||
no = superVanish.getMessage("PlaceholderIsVanishedNo");
|
||||
prefix = superVanish.getMessage("PlaceholderVanishPrefix");
|
||||
suffix = superVanish.getMessage("PlaceholderVanishSuffix");
|
||||
new SVPlaceholderExpansion().register();
|
||||
}
|
||||
|
||||
public static String translatePlaceholders(String msg, Player p) {
|
||||
return PlaceholderAPI.setPlaceholders((OfflinePlayer) p, msg);
|
||||
}
|
||||
|
||||
public class SVPlaceholderExpansion extends PlaceholderExpansion {
|
||||
|
||||
@Override
|
||||
public boolean persist() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canRegister() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getAuthor() {
|
||||
return superVanish.getDescription().getAuthors().toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getIdentifier() {
|
||||
return "supervanish";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getVersion() {
|
||||
return superVanish.getDescription().getVersion();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String onRequest(OfflinePlayer op, String id) {
|
||||
try {
|
||||
Player p;
|
||||
if (op instanceof Player)
|
||||
p = (Player) op;
|
||||
else
|
||||
p = null;
|
||||
if (id.equalsIgnoreCase("isvanished")
|
||||
|| id.equalsIgnoreCase("isinvisible")
|
||||
|| id.equalsIgnoreCase("vanished")
|
||||
|| id.equalsIgnoreCase("invisible"))
|
||||
return p != null && superVanish.getVanishStateMgr().isVanished(p.getUniqueId())
|
||||
? yes : no;
|
||||
if (id.equalsIgnoreCase("vanishprefix"))
|
||||
return p != null && superVanish.getVanishStateMgr().isVanished(p.getUniqueId())
|
||||
? prefix : "";
|
||||
if (id.equalsIgnoreCase("vanishsuffix"))
|
||||
return p != null && superVanish.getVanishStateMgr().isVanished(p.getUniqueId())
|
||||
? suffix : "";
|
||||
if (id.equalsIgnoreCase("onlinevanishedplayers")
|
||||
|| id.equalsIgnoreCase("onlinevanished")
|
||||
|| id.equalsIgnoreCase("invisibleplayers")
|
||||
|| id.equalsIgnoreCase("vanishedplayers")
|
||||
|| id.equalsIgnoreCase("hiddenplayers")) {
|
||||
Collection<UUID> onlineVanishedPlayers = superVanish.getVanishStateMgr()
|
||||
.getOnlineVanishedPlayers();
|
||||
String playerListMessage = "";
|
||||
for (UUID uuid : onlineVanishedPlayers) {
|
||||
Player onlineVanished = Bukkit.getPlayer(uuid);
|
||||
if (onlineVanished == null) continue;
|
||||
if (superVanish.getSettings().getBoolean(
|
||||
"IndicationFeatures.LayeredPermissions.HideInvisibleInCommands", false)
|
||||
&& !superVanish.hasPermissionToSee(p, onlineVanished)) {
|
||||
continue;
|
||||
}
|
||||
playerListMessage = playerListMessage + onlineVanished.getName() + ", ";
|
||||
}
|
||||
return playerListMessage.length() > 3
|
||||
? playerListMessage.substring(0, playerListMessage.length() - 2)
|
||||
: playerListMessage;
|
||||
}
|
||||
if (id.equalsIgnoreCase("playercount")
|
||||
|| id.equalsIgnoreCase("onlineplayers")) {
|
||||
int playercount = Bukkit.getOnlinePlayers().size();
|
||||
for (UUID uuid : superVanish.getVanishStateMgr()
|
||||
.getOnlineVanishedPlayers()) {
|
||||
Player onlineVanished = Bukkit.getPlayer(uuid);
|
||||
if (onlineVanished == null) continue;
|
||||
if (p == null || !superVanish.canSee(p, onlineVanished)) playercount--;
|
||||
}
|
||||
return playercount + "";
|
||||
}
|
||||
} catch (Exception e) {
|
||||
superVanish.logException(e);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -14,8 +14,8 @@ import org.bukkit.event.Listener;
|
||||
import org.bukkit.plugin.Plugin;
|
||||
|
||||
/**
|
||||
* Represents a hook into a plugin to support its functionality or make it support SuperVanish's
|
||||
* functionality
|
||||
* Represents a hook into a plugin to support its functionality or make it
|
||||
* support SuperVanish's functionality
|
||||
*/
|
||||
public abstract class PluginHook implements Listener {
|
||||
|
||||
@@ -23,20 +23,29 @@ public abstract class PluginHook implements Listener {
|
||||
protected Plugin plugin;
|
||||
|
||||
public PluginHook(SuperVanish superVanish) {
|
||||
|
||||
this.superVanish = superVanish;
|
||||
|
||||
}
|
||||
|
||||
public void onPluginEnable(Plugin plugin) {
|
||||
|
||||
}
|
||||
|
||||
public void onPluginDisable(Plugin plugin) {
|
||||
|
||||
}
|
||||
|
||||
public Plugin getPlugin() {
|
||||
|
||||
return plugin;
|
||||
|
||||
}
|
||||
|
||||
void setPlugin(Plugin plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -25,98 +25,140 @@ import java.util.logging.Level;
|
||||
|
||||
public class PluginHookMgr implements Listener {
|
||||
|
||||
private static final Map<String, Class<? extends PluginHook>> REGISTERED_HOOKS
|
||||
= new HashMap<String, Class<? extends PluginHook>>() {{
|
||||
private static final Map<String, Class<? extends PluginHook>> REGISTERED_HOOKS = new HashMap<String, Class<? extends PluginHook>>() {
|
||||
|
||||
{
|
||||
|
||||
put("Essentials", EssentialsHook.class);
|
||||
put("Citizens", CitizensHook.class);
|
||||
put("PlaceholderAPI", PlaceholderAPIHook.class);
|
||||
put("Utilities-OG", MiniPlaceholdersHook.class);
|
||||
put("dynmap", DynmapHook.class);
|
||||
put("TrailGUI", TrailGUIHook.class);
|
||||
put("MVdWPlaceholderAPI", MVdWPlaceholderAPIHook.class);
|
||||
put("OpenInv", OpenInvHook.class);
|
||||
}};
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
private final SuperVanish plugin;
|
||||
private Set<PluginHook> activeHooks = new HashSet<>();
|
||||
|
||||
public PluginHookMgr(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
plugin.getServer().getPluginManager().registerEvents(this, plugin);
|
||||
for (Plugin alreadyEnabledPlugin : Bukkit.getPluginManager().getPlugins())
|
||||
if (alreadyEnabledPlugin.isEnabled())
|
||||
onPluginEnable(new PluginEnableEvent(alreadyEnabledPlugin));
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onPluginEnable(PluginEnableEvent e) {
|
||||
|
||||
Plugin plugin = e.getPlugin();
|
||||
if (REGISTERED_HOOKS.get(plugin.getName()) == null) return;
|
||||
if (isHookDisabled(plugin.getName())) return;
|
||||
if (REGISTERED_HOOKS.get(plugin.getName()) == null)
|
||||
return;
|
||||
if (isHookDisabled(plugin.getName()))
|
||||
return;
|
||||
PluginHook hook = null;
|
||||
try {
|
||||
hook = REGISTERED_HOOKS.get(plugin.getName()).getConstructor(SuperVanish.class).
|
||||
newInstance(PluginHookMgr.this.plugin);
|
||||
|
||||
hook = REGISTERED_HOOKS.get(plugin.getName()).getConstructor(SuperVanish.class)
|
||||
.newInstance(PluginHookMgr.this.plugin);
|
||||
hook.setPlugin(plugin);
|
||||
hook.onPluginEnable(plugin);
|
||||
Bukkit.getPluginManager().registerEvents(hook, plugin);
|
||||
activeHooks.add(hook);
|
||||
PluginHookMgr.this.plugin.log(
|
||||
Level.INFO, "Hooked into " + plugin.getName());
|
||||
PluginHookMgr.this.plugin.log(Level.INFO, "Hooked into " + plugin.getName());
|
||||
|
||||
} catch (NoClassDefFoundError er) {
|
||||
Bukkit.getLogger().warning("NoClassDefFoundError for SV-Hook(v"
|
||||
+ this.plugin.getDescription().getVersion() + ") "
|
||||
+ (hook != null ? hook.getClass().getSimpleName() : "?") + " of plugin "
|
||||
+ plugin.getName() + " v" + plugin.getDescription().getVersion()
|
||||
+ ", please report this if you are using the latest version of that" +
|
||||
" plugin!");
|
||||
|
||||
Bukkit.getLogger()
|
||||
.warning("NoClassDefFoundError for SV-Hook(v" + this.plugin.getPluginMeta().getVersion() + ") "
|
||||
+ (hook != null ? hook.getClass().getSimpleName() : "?") + " of plugin " + plugin.getName()
|
||||
+ " v" + plugin.getPluginMeta().getVersion()
|
||||
+ ", please report this if you are using the latest version of that" + " plugin!");
|
||||
|
||||
} catch (Exception er) {
|
||||
if (er.getMessage() != null
|
||||
&& er.getMessage().contains("Unable to find handler list for event")) {
|
||||
this.plugin.log(Level.WARNING, "" + er.getMessage()
|
||||
+ "; This is not an issue with SuperVanish");
|
||||
|
||||
if (er.getMessage() != null && er.getMessage().contains("Unable to find handler list for event")) {
|
||||
|
||||
this.plugin.log(Level.WARNING, "" + er.getMessage() + "; This is not an issue with SuperVanish");
|
||||
return;
|
||||
} else if (er.getCause() != null && er.getCause().getMessage() != null && er.getCause()
|
||||
.getMessage().contains("Unable to find handler list for event ")) {
|
||||
this.plugin.log(Level.WARNING, "" + er.getCause()
|
||||
.getMessage() + "; This is not an issue with SuperVanish");
|
||||
|
||||
} else if (er.getCause() != null && er.getCause().getMessage() != null
|
||||
&& er.getCause().getMessage().contains("Unable to find handler list for event "))
|
||||
{
|
||||
|
||||
this.plugin.log(Level.WARNING,
|
||||
"" + er.getCause().getMessage() + "; This is not an issue with SuperVanish");
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
this.plugin.logException(new InvalidPluginHookException(er));
|
||||
this.plugin.log(Level.WARNING, "Affected by this error is only the "
|
||||
+ plugin.getName() + "-Hook, all other hooks and features aren't affected.");
|
||||
this.plugin.log(Level.WARNING, "Affected by this error is only the " + plugin.getName()
|
||||
+ "-Hook, all other hooks and features aren't affected.");
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean isHookDisabled(String pluginName) {
|
||||
|
||||
if (pluginName.equalsIgnoreCase("dynmap"))
|
||||
return !plugin.getSettings().getBoolean("HookOptions.EnableDynmapHook");
|
||||
if (pluginName.equalsIgnoreCase("Utilities-OG"))
|
||||
return !plugin.getSettings().getBoolean("HookOptions.EnableUtilitiesOGHook", true);
|
||||
return !plugin.getSettings().getBoolean("HookOptions.Enable" + pluginName + "Hook", true);
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onPluginDisable(PluginDisableEvent e) {
|
||||
|
||||
Plugin plugin = e.getPlugin();
|
||||
PluginHook hook = getActiveHook(plugin);
|
||||
if (hook == null) return;
|
||||
if (hook == null)
|
||||
return;
|
||||
try {
|
||||
|
||||
hook.onPluginDisable(plugin);
|
||||
|
||||
} catch (Exception e1) {
|
||||
|
||||
this.plugin.logException(new InvalidPluginHookException(e1));
|
||||
|
||||
}
|
||||
|
||||
hook.setPlugin(null);
|
||||
activeHooks.remove(hook);
|
||||
|
||||
}
|
||||
|
||||
private PluginHook getActiveHook(Plugin plugin) {
|
||||
for (PluginHook hook : activeHooks) if (hook.getPlugin() == plugin) return hook;
|
||||
|
||||
for (PluginHook hook : activeHooks)
|
||||
if (hook.getPlugin() == plugin)
|
||||
return hook;
|
||||
return null;
|
||||
|
||||
}
|
||||
|
||||
public boolean isHookActive(Class<? extends PluginHook> hookClass) {
|
||||
|
||||
for (PluginHook hook : activeHooks) {
|
||||
|
||||
if (hook.getClass().equals(hookClass)) {
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -23,28 +23,37 @@ import ca.jamiesinn.trailgui.TrailGUI;
|
||||
public class TrailGUIHook extends PluginHook {
|
||||
|
||||
public TrailGUIHook(SuperVanish superVanish) {
|
||||
|
||||
super(superVanish);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPluginEnable(Plugin plugin) {
|
||||
|
||||
if (!(plugin instanceof TrailGUI)) {
|
||||
superVanish.log(Level.WARNING,
|
||||
"Failed to hook into TrailGUI. (PluginNotFound)");
|
||||
|
||||
superVanish.log(Level.WARNING, "Failed to hook into TrailGUI. (PluginNotFound)");
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
PlayerMoveEvent.getHandlerList().unregister(plugin);
|
||||
final Listeners trailGUIListeners = new Listeners((TrailGUI) plugin);
|
||||
plugin.getServer().getPluginManager().registerEvents(new Listener() {
|
||||
|
||||
@EventHandler
|
||||
public void onPlayerMove(PlayerMoveEvent event) {
|
||||
if (superVanish.getVanishStateMgr()
|
||||
.getOnlineVanishedPlayers().contains(
|
||||
event.getPlayer().getUniqueId()))
|
||||
|
||||
if (superVanish.getVanishStateMgr().getOnlineVanishedPlayers()
|
||||
.contains(event.getPlayer().getUniqueId()))
|
||||
return;
|
||||
trailGUIListeners.onPlayerMove(event);
|
||||
|
||||
}
|
||||
|
||||
}, plugin);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -10,7 +10,6 @@ package de.myzelyam.supervanish.listeners;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.VanishPlayer;
|
||||
import de.myzelyam.supervanish.features.Broadcast;
|
||||
import org.bukkit.configuration.file.FileConfiguration;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
@@ -19,8 +18,6 @@ import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.block.Action;
|
||||
import org.bukkit.event.entity.*;
|
||||
import org.bukkit.event.player.PlayerInteractEvent;
|
||||
import org.bukkit.event.player.PlayerPickupItemEvent;
|
||||
|
||||
|
||||
public class GeneralListener implements Listener {
|
||||
|
||||
@@ -29,110 +26,158 @@ public class GeneralListener implements Listener {
|
||||
private final FileConfiguration config;
|
||||
|
||||
public GeneralListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
config = plugin.getSettings();
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onDamage(EntityDamageByEntityEvent e) {
|
||||
|
||||
try {
|
||||
if (!(e.getDamager() instanceof Player)) return;
|
||||
if (e.getEntity() == null) return;
|
||||
|
||||
if (!(e.getDamager() instanceof Player))
|
||||
return;
|
||||
if (e.getEntity() == null)
|
||||
return;
|
||||
Player p = (Player) e.getDamager();
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
if (config.getBoolean("RestrictiveOptions.PreventHittingEntities")
|
||||
&& !p.hasPermission("sv.damageentities") && !p.hasPermission("sv.damage")) {
|
||||
&& !p.hasPermission("sv.damageentities") && !p.hasPermission("sv.damage"))
|
||||
{
|
||||
|
||||
plugin.sendMessage(p, "EntityHitDenied", p);
|
||||
e.setCancelled(true);
|
||||
}
|
||||
}
|
||||
} catch (Exception er) {
|
||||
plugin.logException(er);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onPlayerDeath(PlayerDeathEvent e) {
|
||||
try {
|
||||
Player p = e.getEntity();
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
String deathMessage = e.getDeathMessage();
|
||||
e.setDeathMessage(null);
|
||||
if (deathMessage != null)
|
||||
Broadcast.announceSilentDeath(p, plugin, deathMessage);
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onFoodLevelChange(FoodLevelChangeEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
if (e.getEntity() instanceof Player && config.getBoolean("InvisibilityFeatures.DisableHunger")) {
|
||||
|
||||
Player p = (Player) e.getEntity();
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())
|
||||
&& e.getFoodLevel() <= p.getFoodLevel())
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId()) && e.getFoodLevel() <= p.getFoodLevel())
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onDamage(EntityDamageEvent e) {
|
||||
|
||||
try {
|
||||
if (!(e.getEntity() instanceof Player)) return;
|
||||
|
||||
if (!(e.getEntity() instanceof Player))
|
||||
return;
|
||||
Player p = (Player) e.getEntity();
|
||||
if (!config.getBoolean("InvisibilityFeatures.DisableDamage")) return;
|
||||
if (!config.getBoolean("InvisibilityFeatures.DisableDamage"))
|
||||
return;
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onTarget(EntityTargetEvent e) {
|
||||
|
||||
try {
|
||||
if (!(e.getTarget() instanceof Player)) return;
|
||||
if (!config.getBoolean("InvisibilityFeatures.DisableMobTarget")) return;
|
||||
|
||||
if (!(e.getTarget() instanceof Player))
|
||||
return;
|
||||
if (!config.getBoolean("InvisibilityFeatures.DisableMobTarget"))
|
||||
return;
|
||||
Player p = (Player) e.getTarget();
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onItemPickUp(PlayerPickupItemEvent e) {
|
||||
public void onItemPickUp(EntityPickupItemEvent e) {
|
||||
|
||||
try {
|
||||
VanishPlayer vanishPlayer = plugin.getVanishPlayer(e.getPlayer());
|
||||
if (vanishPlayer == null || !vanishPlayer.isOnlineVanished()) return;
|
||||
|
||||
if (!(e.getEntity() instanceof Player player))
|
||||
return;
|
||||
VanishPlayer vanishPlayer = plugin.getVanishPlayer(player);
|
||||
if (vanishPlayer == null || !vanishPlayer.isOnlineVanished())
|
||||
return;
|
||||
if (!vanishPlayer.hasItemPickUpsEnabled())
|
||||
e.setCancelled(true);
|
||||
if (plugin.getSettings().getBoolean("RestrictiveOptions.PreventModifyingOwnInventory")
|
||||
&& !e.getPlayer().hasPermission("sv.modifyowninv")) {
|
||||
&& !player.hasPermission("sv.modifyowninv"))
|
||||
{
|
||||
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onPlayerCropTrample(PlayerInteractEvent e) {
|
||||
|
||||
try {
|
||||
if (!plugin.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId())) return;
|
||||
if (e.getAction() != Action.PHYSICAL) return;
|
||||
|
||||
if (!plugin.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId()))
|
||||
return;
|
||||
if (e.getAction() != Action.PHYSICAL)
|
||||
return;
|
||||
if (e.getClickedBlock() != null && e.getClickedBlock().getType().toString().matches("SOIL|FARMLAND"))
|
||||
e.setCancelled(true);
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -9,7 +9,6 @@
|
||||
package de.myzelyam.supervanish.listeners;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.features.Broadcast;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
@@ -25,13 +24,18 @@ public class JoinListener implements EventExecutor, Listener {
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public JoinListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Listener l, Event event) {
|
||||
|
||||
try {
|
||||
|
||||
if (event instanceof PlayerJoinEvent) {
|
||||
|
||||
PlayerJoinEvent e = (PlayerJoinEvent) event;
|
||||
final Player p = e.getPlayer();
|
||||
// hide others
|
||||
@@ -41,57 +45,79 @@ public class JoinListener implements EventExecutor, Listener {
|
||||
plugin.getVisibilityChanger().getHider().setHidden(onlinePlayer, p, true);
|
||||
// vanished:
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
// hide self
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers())
|
||||
if (!plugin.hasPermissionToSee(onlinePlayer, p))
|
||||
plugin.getVisibilityChanger().getHider().setHidden(p, onlinePlayer, true);
|
||||
// Join message
|
||||
if (plugin.getSettings().getBoolean("MessageOptions.HideRealJoinQuitMessages")) {
|
||||
e.setJoinMessage(null);
|
||||
Broadcast.announceSilentJoin(p, plugin);
|
||||
}
|
||||
// reminding message
|
||||
if (plugin.getSettings().getBoolean("MessageOptions.RemindVanishedOnJoin")) {
|
||||
|
||||
plugin.sendMessage(p, "RemindingMessage", p);
|
||||
|
||||
}
|
||||
|
||||
// re-add action bar
|
||||
if (plugin.getActionBarMgr() != null && plugin.getSettings().getBoolean(
|
||||
"MessageOptions.DisplayActionBar")) {
|
||||
if (plugin.getActionBarMgr() != null
|
||||
&& plugin.getSettings().getBoolean("MessageOptions.DisplayActionBar"))
|
||||
{
|
||||
|
||||
plugin.getActionBarMgr().addActionBar(p);
|
||||
|
||||
}
|
||||
|
||||
// sleep state
|
||||
p.setSleepingIgnored(true);
|
||||
// adjust fly
|
||||
if (plugin.getSettings().getBoolean("InvisibilityFeatures.Fly.Enable")) {
|
||||
|
||||
p.setAllowFlight(true);
|
||||
|
||||
}
|
||||
|
||||
// metadata
|
||||
p.setMetadata("vanished", new FixedMetadataValue(plugin, true));
|
||||
|
||||
} else {
|
||||
|
||||
// not vanished:
|
||||
// metadata
|
||||
p.removeMetadata("vanished", plugin);
|
||||
|
||||
}
|
||||
|
||||
// not necessarily vanished:
|
||||
// recreate files msg
|
||||
if ((p.hasPermission("sv.recreatecfg") || p.hasPermission("sv.recreatefiles"))
|
||||
&& (plugin.getConfigMgr().isSettingsUpdateRequired()
|
||||
|| plugin.getConfigMgr().isMessagesUpdateRequired())) {
|
||||
String currentVersion = plugin.getDescription().getVersion();
|
||||
boolean isDismissed =
|
||||
plugin.getPlayerData().getBoolean("PlayerData." + p.getUniqueId() + ".dismissed."
|
||||
+ currentVersion.replace(".", "_"), false);
|
||||
|| plugin.getConfigMgr().isMessagesUpdateRequired()))
|
||||
{
|
||||
|
||||
String currentVersion = plugin.getPluginMeta().getVersion();
|
||||
boolean isDismissed = plugin.getPlayerData().getBoolean(
|
||||
"PlayerData." + p.getUniqueId() + ".dismissed." + currentVersion.replace(".", "_"), false);
|
||||
if (!isDismissed)
|
||||
new BukkitRunnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
plugin.sendMessage(p, "RecreationRequiredMsg", p);
|
||||
|
||||
}
|
||||
|
||||
}.runTaskLater(plugin, 1);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -18,39 +18,52 @@ import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.player.PlayerLoginEvent;
|
||||
|
||||
|
||||
public class LoginListener implements Listener {
|
||||
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public LoginListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR)
|
||||
public void onLogin(PlayerLoginEvent e) {
|
||||
|
||||
try {
|
||||
if (e.getResult() != PlayerLoginEvent.Result.ALLOWED) return;
|
||||
|
||||
if (e.getResult() != PlayerLoginEvent.Result.ALLOWED)
|
||||
return;
|
||||
final Player p = e.getPlayer();
|
||||
boolean vanished = plugin.getVanishStateMgr().isVanished(p.getUniqueId());
|
||||
boolean itemPickUps = plugin.getPlayerData().getBoolean(
|
||||
"PlayerData." + p.getUniqueId() + ".itemPickUps",
|
||||
boolean itemPickUps = plugin.getPlayerData().getBoolean("PlayerData." + p.getUniqueId() + ".itemPickUps",
|
||||
plugin.getSettings().getBoolean("InvisibilityFeatures.DefaultPickUpItemsOption"));
|
||||
plugin.createVanishPlayer(p, itemPickUps);
|
||||
if (vanished && plugin.getSettings().getBoolean("VanishStateFeatures.CheckPermissionOnLogin", false)
|
||||
&& !CommandAction.VANISH_SELF.checkPermission(p, plugin)) {
|
||||
&& !CommandAction.VANISH_SELF.checkPermission(p, plugin))
|
||||
{
|
||||
|
||||
vanished = false;
|
||||
|
||||
}
|
||||
|
||||
if (!vanished && p.hasPermission("sv.joinvanished")
|
||||
&& plugin.getSettings().getBoolean("VanishStateFeatures.AutoVanishOnJoin", false)) {
|
||||
&& plugin.getSettings().getBoolean("VanishStateFeatures.AutoVanishOnJoin", false))
|
||||
{
|
||||
|
||||
plugin.getVanishStateMgr().setVanishedState(p.getUniqueId(), p.getName(), true, null);
|
||||
vanished = true;
|
||||
|
||||
}
|
||||
|
||||
if (vanished) {
|
||||
|
||||
// hide self
|
||||
for (Player onlinePlayer : Bukkit.getOnlinePlayers())
|
||||
if (!plugin.hasPermissionToSee(onlinePlayer, p))
|
||||
plugin.getVisibilityChanger().getHider().setHidden(p, onlinePlayer, true);
|
||||
|
||||
}
|
||||
|
||||
// hide others
|
||||
@@ -58,8 +71,13 @@ public class LoginListener implements Listener {
|
||||
if (plugin.getVanishStateMgr().isVanished(onlinePlayer.getUniqueId())
|
||||
&& !plugin.hasPermissionToSee(p, onlinePlayer))
|
||||
plugin.getVisibilityChanger().getHider().setHidden(onlinePlayer, p, true);
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -29,15 +29,20 @@ public class PlayerBlockModifyListener implements Listener {
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public PlayerBlockModifyListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onInteract(PlayerInteractEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
if (!plugin.getVanishStateMgr().isVanished(e.getPlayer().getUniqueId()))
|
||||
return;
|
||||
if (e.getAction().equals(Action.PHYSICAL) && e.getClickedBlock() != null) {
|
||||
|
||||
if (!plugin.getSettings().getBoolean("InvisibilityFeatures.DisablePressurePlates"))
|
||||
return;
|
||||
String material = e.getClickedBlock().getType().toString();
|
||||
@@ -45,42 +50,70 @@ public class PlayerBlockModifyListener implements Listener {
|
||||
"WOOD_PLATE"/* <- LEGACY */, "TRIPWIRE", "PRESSURE_PLATE");
|
||||
for (String disallowedMaterial : disallowedMaterials)
|
||||
if (material.equals(disallowedMaterial) || material.contains(disallowedMaterial)) {
|
||||
|
||||
e.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onPlace(BlockPlaceEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
if (plugin.getSettings().getBoolean("RestrictiveOptions.PreventBlockPlacing")) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
Collection<UUID> vanishedPlayers = plugin.getVanishStateMgr().getOnlineVanishedPlayers();
|
||||
if (vanishedPlayers.contains(p.getUniqueId()) && !p.hasPermission("sv.placeblocks")) {
|
||||
|
||||
e.setCancelled(true);
|
||||
plugin.sendMessage(e.getPlayer(), "BlockPlaceDenied", e.getPlayer());
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onBreak(BlockBreakEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
if (plugin.getSettings().getBoolean("RestrictiveOptions.PreventBlockBreaking")) {
|
||||
|
||||
Player p = e.getPlayer();
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId()) && !p.hasPermission("sv.breakblocks")) {
|
||||
|
||||
e.setCancelled(true);
|
||||
plugin.sendMessage(e.getPlayer(), "BlockBreakDenied", e.getPlayer());
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -10,9 +10,7 @@ package de.myzelyam.supervanish.listeners;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.commands.CommandAction;
|
||||
import de.myzelyam.supervanish.features.Broadcast;
|
||||
|
||||
import org.bukkit.configuration.file.FileConfiguration;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.Event;
|
||||
import org.bukkit.event.Listener;
|
||||
@@ -24,44 +22,55 @@ public class QuitListener implements EventExecutor, Listener {
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public QuitListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(Listener l, Event event) {
|
||||
|
||||
try {
|
||||
|
||||
if (event instanceof PlayerQuitEvent) {
|
||||
|
||||
PlayerQuitEvent e = (PlayerQuitEvent) event;
|
||||
FileConfiguration config = plugin.getConfig();
|
||||
Player p = e.getPlayer();
|
||||
// if is invisible
|
||||
if (plugin.getVanishStateMgr().isVanished(p.getUniqueId())) {
|
||||
|
||||
// remove action bar
|
||||
if (plugin.getActionBarMgr() != null && plugin.getSettings().getBoolean(
|
||||
"MessageOptions.DisplayActionBar")) {
|
||||
if (plugin.getActionBarMgr() != null
|
||||
&& plugin.getSettings().getBoolean("MessageOptions.DisplayActionBar"))
|
||||
{
|
||||
|
||||
plugin.getActionBarMgr().removeActionBar(p);
|
||||
|
||||
}
|
||||
|
||||
// check auto-reappear-option
|
||||
boolean noMsg = false;
|
||||
if (plugin.getSettings().getBoolean("VanishStateFeatures.ReappearOnQuit")
|
||||
|| plugin.getSettings().getBoolean("VanishStateFeatures.CheckPermissionOnQuit")
|
||||
&& !CommandAction.VANISH_SELF.checkPermission(p, plugin)) {
|
||||
&& !CommandAction.VANISH_SELF.checkPermission(p, plugin))
|
||||
{
|
||||
|
||||
plugin.getVanishStateMgr().setVanishedState(p.getUniqueId(), p.getName(), false, null);
|
||||
// check if it should handle the quit msg
|
||||
if (!config.getBoolean("MessageOptions.ReappearOnQuitHideLeaveMsg"))
|
||||
noMsg = true;
|
||||
}
|
||||
// check remove-quit-msg option
|
||||
if (!noMsg && config.getBoolean("MessageOptions.HideRealJoinQuitMessages")) {
|
||||
e.setQuitMessage(null);
|
||||
Broadcast.announceSilentQuit(p, plugin);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// remove VanishPlayer
|
||||
plugin.removeVanishPlayer(plugin.getVanishPlayer(p));
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -21,7 +21,6 @@ import java.util.Locale;
|
||||
import java.util.Objects;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public class TabCompleteListener implements Listener {
|
||||
|
||||
@@ -30,39 +29,56 @@ public class TabCompleteListener implements Listener {
|
||||
private boolean errorLogged = false;
|
||||
|
||||
public TabCompleteListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onTabComplete(TabCompleteEvent e) {
|
||||
|
||||
try {
|
||||
if (!(e.getSender() instanceof Player)) return;
|
||||
|
||||
if (!(e.getSender() instanceof Player))
|
||||
return;
|
||||
Player p = (Player) e.getSender();
|
||||
Set<String> hiddenNames = plugin.getVanishStateMgr().getOnlineVanishedPlayers().stream()
|
||||
.map(Bukkit::getPlayer).filter(Objects::nonNull)
|
||||
.filter(vanishedPlayer -> !plugin.canSee(p, vanishedPlayer))
|
||||
.map(HumanEntity::getName)
|
||||
.map(name -> name.toLowerCase(Locale.ENGLISH))
|
||||
.collect(Collectors.toSet());
|
||||
.filter(vanishedPlayer -> !plugin.canSee(p, vanishedPlayer)).map(HumanEntity::getName)
|
||||
.map(name -> name.toLowerCase(Locale.ENGLISH)).collect(Collectors.toSet());
|
||||
Iterator<String> it = e.getCompletions().iterator();
|
||||
while (it.hasNext()) {
|
||||
|
||||
String completion = it.next();
|
||||
boolean allowedCompletion = !hiddenNames.contains(completion.toLowerCase(Locale.ENGLISH));
|
||||
if (!allowedCompletion) {
|
||||
|
||||
it.remove();
|
||||
}
|
||||
}
|
||||
} catch (UnsupportedOperationException uoe) {
|
||||
if (!errorLogged) {
|
||||
plugin.getLogger().warning("UnsupportedOperationException while modifying TabCompleteEvent");
|
||||
errorLogged = true;
|
||||
}
|
||||
} catch (Exception er) {
|
||||
if (!errorLogged) {
|
||||
plugin.logException(er);
|
||||
errorLogged = true;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (UnsupportedOperationException uoe) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
plugin.getLogger().warning("UnsupportedOperationException while modifying TabCompleteEvent");
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
plugin.logException(er);
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -22,23 +22,35 @@ public class WorldChangeListener implements Listener {
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public WorldChangeListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR)
|
||||
public void onWorldChange(PlayerChangedWorldEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
final Player p = e.getPlayer();
|
||||
if (!plugin.getVanishStateMgr().isVanished(p.getUniqueId()))
|
||||
return;
|
||||
// check auto-reappear option
|
||||
if (plugin.getSettings().getBoolean("VanishStateFeatures.ReappearOnWorldChange")
|
||||
|| plugin.getSettings().getBoolean("VanishStateFeatures.CheckPermissionOnWorldChange")
|
||||
&& !CommandAction.VANISH_SELF.checkPermission(p, plugin)) {
|
||||
&& !CommandAction.VANISH_SELF.checkPermission(p, plugin))
|
||||
{
|
||||
|
||||
plugin.getVisibilityChanger().showPlayer(p);
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,143 +0,0 @@
|
||||
/*
|
||||
* Copyright © 2015, Leon Mangler and the SuperVanish contributors
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
package de.myzelyam.supervanish.net;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
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.scheduler.BukkitRunnable;
|
||||
import org.bukkit.scheduler.BukkitTask;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.InputStreamReader;
|
||||
import java.net.URL;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import javax.net.ssl.HttpsURLConnection;
|
||||
|
||||
import lombok.Getter;
|
||||
|
||||
public class UpdateNotifier {
|
||||
|
||||
// 20 minutes
|
||||
private static final long CHECK_INTERVAL = 20 * 60 * 20;
|
||||
|
||||
private final SuperVanish plugin;
|
||||
private final BukkitTask checkTask;
|
||||
@Getter
|
||||
private final String currentVersion;
|
||||
private final Set<UUID> notifiedPlayers = new HashSet<>();
|
||||
@Getter
|
||||
private volatile String latestVersion;
|
||||
private boolean notifiedConsole = false;
|
||||
|
||||
public UpdateNotifier(final SuperVanish plugin) {
|
||||
this.plugin = plugin;
|
||||
currentVersion = plugin.getDescription().getVersion();
|
||||
checkTask = start();
|
||||
Bukkit.getPluginManager().registerEvents(new Listener() {
|
||||
@EventHandler
|
||||
public void onJoin(final PlayerJoinEvent e) {
|
||||
new BukkitRunnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
if (!isUpToDate())
|
||||
notifyPlayer(e.getPlayer());
|
||||
}
|
||||
}.runTaskLater(plugin, 2);
|
||||
}
|
||||
}, plugin);
|
||||
}
|
||||
|
||||
public boolean isUpToDate() {
|
||||
try {
|
||||
if (latestVersion == null) throw new NumberFormatException();
|
||||
int comparision = plugin.getVersionUtil().compareVersions(currentVersion, latestVersion);
|
||||
return comparision >= 0;
|
||||
} catch (NumberFormatException e) {
|
||||
return currentVersion.equals(latestVersion);
|
||||
}
|
||||
}
|
||||
|
||||
private void notifyPlayer(Player p) {
|
||||
if (p.hasPermission("sv.notify") && latestVersion != null) {
|
||||
if (notifiedPlayers.contains(p.getUniqueId())) return;
|
||||
notifiedPlayers.add(p.getUniqueId());
|
||||
plugin.sendMessage(p,
|
||||
plugin.getMessage("PluginOutdated").replace("%new%", latestVersion)
|
||||
.replace("%current%", currentVersion), p);
|
||||
}
|
||||
}
|
||||
|
||||
private void notifyAdmins() {
|
||||
for (Player p : plugin.getServer().getOnlinePlayers()) {
|
||||
notifyPlayer(p);
|
||||
}
|
||||
}
|
||||
|
||||
private void notifyConsole() {
|
||||
if (!notifiedConsole) {
|
||||
plugin.log(Level.INFO, "Your current version of SuperVanish is outdated" +
|
||||
" - New version: '" + latestVersion + "'; Currently: '" + currentVersion + "'");
|
||||
notifiedConsole = true;
|
||||
}
|
||||
}
|
||||
|
||||
private BukkitTask start() {
|
||||
if (checkTask != null) throw new IllegalStateException("Task is already running");
|
||||
return new BukkitRunnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
String latestVersion = fetchLatestVersion();
|
||||
UpdateNotifier.this.latestVersion = latestVersion.equals("Error")
|
||||
? UpdateNotifier.this.latestVersion == null
|
||||
? currentVersion
|
||||
: UpdateNotifier.this.latestVersion
|
||||
: latestVersion;
|
||||
if (!isUpToDate())
|
||||
new BukkitRunnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
notifyConsole();
|
||||
if (plugin.getSettings().getBoolean(
|
||||
"MiscellaneousOptions.UpdateChecker.NotifyAdmins")) notifyAdmins();
|
||||
}
|
||||
}.runTask(plugin);
|
||||
}
|
||||
}.runTaskTimerAsynchronously(plugin, 0, CHECK_INTERVAL);
|
||||
}
|
||||
|
||||
private String fetchLatestVersion() {
|
||||
try {
|
||||
HttpsURLConnection con = (HttpsURLConnection) new URL(
|
||||
"https://api.spigotmc.org/legacy/update.php?resource=1331").openConnection();
|
||||
con.setConnectTimeout(20 * 1000);
|
||||
con.setReadTimeout(20 * 1000);
|
||||
String version;
|
||||
try (BufferedReader reader = new BufferedReader(new InputStreamReader(con.getInputStream()))) {
|
||||
version = reader.readLine();
|
||||
}
|
||||
con.disconnect();
|
||||
if (version.length() <= 7)
|
||||
return version;
|
||||
else throw new RuntimeException("'" + version + "' is not a valid version");
|
||||
} catch (Exception e) {
|
||||
plugin.log(Level.WARNING, "Failed to check for an update: "
|
||||
+ e.getMessage());
|
||||
return "Error";
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -7,25 +7,59 @@ import org.bukkit.entity.Player;
|
||||
public class BukkitPlayerHidingUtil {
|
||||
|
||||
private BukkitPlayerHidingUtil() {
|
||||
|
||||
}
|
||||
|
||||
public static void hidePlayer(Player player, Player viewer, SuperVanish plugin) {
|
||||
if (isNewPlayerHidingAPISupported(plugin))
|
||||
viewer.hidePlayer(plugin, player);
|
||||
else
|
||||
//noinspection deprecation
|
||||
viewer.hidePlayer(player);
|
||||
|
||||
try {
|
||||
|
||||
if (isNewPlayerHidingAPISupported(plugin)) {
|
||||
|
||||
Player.class.getMethod("hidePlayer", org.bukkit.plugin.Plugin.class, Player.class).invoke(viewer,
|
||||
plugin, player);
|
||||
|
||||
} else {
|
||||
|
||||
Player.class.getMethod("hidePlayer", Player.class).invoke(viewer, player);
|
||||
|
||||
}
|
||||
|
||||
} catch (ReflectiveOperationException e) {
|
||||
|
||||
throw new RuntimeException("Failed to hide player " + player.getName() + " from " + viewer.getName(), e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static void showPlayer(Player player, Player viewer, SuperVanish plugin) {
|
||||
if (isNewPlayerHidingAPISupported(plugin))
|
||||
viewer.showPlayer(plugin, player);
|
||||
else
|
||||
//noinspection deprecation
|
||||
viewer.showPlayer(player);
|
||||
|
||||
try {
|
||||
|
||||
if (isNewPlayerHidingAPISupported(plugin)) {
|
||||
|
||||
Player.class.getMethod("showPlayer", org.bukkit.plugin.Plugin.class, Player.class).invoke(viewer,
|
||||
plugin, player);
|
||||
|
||||
} else {
|
||||
|
||||
Player.class.getMethod("showPlayer", Player.class).invoke(viewer, player);
|
||||
|
||||
}
|
||||
|
||||
} catch (ReflectiveOperationException e) {
|
||||
|
||||
throw new RuntimeException("Failed to show player " + player.getName() + " to " + viewer.getName(), e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static boolean isNewPlayerHidingAPISupported(SuperVanish plugin) {
|
||||
|
||||
return plugin.getVersionUtil().isOneDotXOrHigher(19);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -3,4 +3,5 @@ package de.myzelyam.supervanish.utils;
|
||||
public interface ExceptionHandler {
|
||||
|
||||
void handle(Exception e);
|
||||
|
||||
}
|
||||
@@ -10,70 +10,98 @@ import java.util.logging.Level;
|
||||
public class ExceptionLogger {
|
||||
|
||||
private ExceptionLogger() {
|
||||
|
||||
}
|
||||
|
||||
public static void logException(Throwable e, SuperVanish plugin) {
|
||||
|
||||
try {
|
||||
|
||||
final boolean realEx = e != null;
|
||||
Level loggingLevel = realEx ? Level.WARNING : Level.INFO;
|
||||
if (realEx) plugin.log(loggingLevel, "Unknown exception occurred!");
|
||||
else plugin.log(loggingLevel, "Printing information...");
|
||||
if (plugin.getConfigMgr().isSettingsUpdateRequired()
|
||||
|| plugin.getConfigMgr().isMessagesUpdateRequired()) {
|
||||
if (realEx) plugin.log(loggingLevel, "You have an outdated configuration, " +
|
||||
"regenerating it by using '/sv recreatefiles' might fix this problem!");
|
||||
else plugin.log(loggingLevel, "Configuration is outdated.");
|
||||
} else if (realEx) plugin.log(loggingLevel, "Please report this issue!");
|
||||
if (!realEx) e = new RuntimeException("Information for reporting an issue");
|
||||
if (realEx)
|
||||
plugin.log(loggingLevel, "Unknown exception occurred!");
|
||||
else
|
||||
plugin.log(loggingLevel, "Printing information...");
|
||||
if (plugin.getConfigMgr().isSettingsUpdateRequired() || plugin.getConfigMgr().isMessagesUpdateRequired()) {
|
||||
|
||||
if (realEx)
|
||||
plugin.log(loggingLevel, "Your config files may need to be recreated. "
|
||||
+ "Running '/sv recreatefiles' might fix this problem.");
|
||||
else
|
||||
plugin.log(loggingLevel, "Config file recreation may be required.");
|
||||
|
||||
} else if (realEx)
|
||||
plugin.log(loggingLevel, "Please report this issue!");
|
||||
|
||||
if (!realEx)
|
||||
e = new RuntimeException("Information for reporting an issue");
|
||||
plugin.log(loggingLevel, "Message: ");
|
||||
plugin.log(loggingLevel, " " + e.getMessage());
|
||||
plugin.log(loggingLevel, "General information: ");
|
||||
StringBuilder plugins = new StringBuilder();
|
||||
for (Plugin pl : Bukkit.getServer().getPluginManager().getPlugins()) {
|
||||
if (pl.getName().equalsIgnoreCase("SuperVanish")) continue;
|
||||
plugins.append(pl.getName()).append(" v")
|
||||
.append(pl.getDescription().getVersion()).append(", ");
|
||||
|
||||
if (pl.getName().equalsIgnoreCase("SuperVanish"))
|
||||
continue;
|
||||
plugins.append(pl.getName()).append(" v").append(pl.getPluginMeta().getVersion()).append(", ");
|
||||
|
||||
}
|
||||
|
||||
plugins = new StringBuilder(plugins.substring(0, plugins.length() - 1));
|
||||
plugin.log(loggingLevel, " ServerVersion: " + plugin.getServer().getVersion());
|
||||
plugin.log(loggingLevel, " PluginVersion: "
|
||||
+ plugin.getDescription().getVersion());
|
||||
plugin.log(loggingLevel, " PluginVersion: " + plugin.getPluginMeta().getVersion());
|
||||
plugin.log(loggingLevel, " ServerPlugins: " + plugins);
|
||||
try {
|
||||
|
||||
plugin.log(loggingLevel, "Settings:");
|
||||
plugin.log(loggingLevel, " MsgsVersion: "
|
||||
+ plugin.getMessages().getString("MessagesVersion"));
|
||||
plugin.log(loggingLevel, " MsgsVersion: " + plugin.getMessages().getString("MessagesVersion"));
|
||||
StringBuilder settings = new StringBuilder("||");
|
||||
for (String key : plugin.getSettings().getKeys(true)) {
|
||||
|
||||
if (!plugin.getSettings().getString(key).contains("MemorySection"))
|
||||
settings.append(key).append(">")
|
||||
.append(plugin.getSettings().getString(key)).append("||");
|
||||
settings.append(key).append(">").append(plugin.getSettings().getString(key)).append("||");
|
||||
|
||||
}
|
||||
|
||||
plugin.log(loggingLevel, " Settings: " + settings);
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
plugin.log(Level.SEVERE, ">> Error occurred while trying to print config info <<");
|
||||
|
||||
}
|
||||
|
||||
plugin.log(loggingLevel, "StackTrace: ");
|
||||
e.printStackTrace();
|
||||
if (realEx) {
|
||||
|
||||
if (plugin.getConfigMgr().isSettingsUpdateRequired()
|
||||
|| plugin.getConfigMgr().isMessagesUpdateRequired())
|
||||
plugin.log(loggingLevel, "You have an outdated configuration, " +
|
||||
"regenerating it by using '/sv recreatefiles' might fix this problem!");
|
||||
plugin.log(loggingLevel, "Your config files may need to be recreated. "
|
||||
+ "Running '/sv recreatefiles' might fix this problem.");
|
||||
plugin.log(loggingLevel, "Please include this information");
|
||||
plugin.log(loggingLevel, "if you report the issue.");
|
||||
|
||||
} else
|
||||
plugin.log(loggingLevel, "End of information.");
|
||||
|
||||
} catch (Exception e2) {
|
||||
plugin.log(Level.WARNING,
|
||||
"An exception occurred while trying to print a detailed stacktrace, " +
|
||||
"printing an undetailed stacktrace of both exceptions:");
|
||||
|
||||
plugin.log(Level.WARNING, "An exception occurred while trying to print a detailed stacktrace, "
|
||||
+ "printing an undetailed stacktrace of both exceptions:");
|
||||
plugin.log(Level.SEVERE, "ORIGINAL EXCEPTION:");
|
||||
if (e != null) {
|
||||
|
||||
e.printStackTrace();
|
||||
|
||||
}
|
||||
|
||||
plugin.log(Level.SEVERE, "SECOND EXCEPTION:");
|
||||
e2.printStackTrace();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -9,5 +9,7 @@
|
||||
package de.myzelyam.supervanish.utils;
|
||||
|
||||
public interface Requirement<T> {
|
||||
|
||||
boolean fulfilledBy(T testSubject);
|
||||
|
||||
}
|
||||
@@ -7,40 +7,62 @@ import java.util.logging.Level;
|
||||
public abstract class Validation {
|
||||
|
||||
public static void checkNotNull(Object... objects) {
|
||||
|
||||
checkNotNull(null, objects);
|
||||
|
||||
}
|
||||
|
||||
public static void checkIsTrue(boolean... bool) {
|
||||
|
||||
checkIsTrue(null, bool);
|
||||
|
||||
}
|
||||
|
||||
public static void checkNotNull(String message, Object... objects) {
|
||||
|
||||
for (Object obj : objects) {
|
||||
|
||||
if (obj == null) {
|
||||
|
||||
if (message != null)
|
||||
log(Level.SEVERE, message);
|
||||
throw new IllegalArgumentException(message == null ? "" : message);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static void checkIsTrue(String message, boolean... booleans) {
|
||||
|
||||
for (boolean bool : booleans) {
|
||||
|
||||
if (!bool) {
|
||||
|
||||
if (message != null)
|
||||
log(Level.SEVERE, message);
|
||||
throw new IllegalArgumentException(message == null ? "" : message);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private static void log(Level level, String message) {
|
||||
|
||||
try {
|
||||
|
||||
Class.forName("org.bukkit.plugin.java.JavaPlugin");
|
||||
Bukkit.getLogger().log(level, message);
|
||||
|
||||
} catch (ClassNotFoundException e) {
|
||||
|
||||
e.printStackTrace();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,42 +1,65 @@
|
||||
package de.myzelyam.supervanish.utils;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
public class VersionUtil {
|
||||
|
||||
private final SuperVanish plugin;
|
||||
private final String minecraftVersion;
|
||||
|
||||
public VersionUtil(SuperVanish plugin) {
|
||||
this.plugin = plugin;
|
||||
// saves versions in the format x.x.x (e.g. 1.20.1)
|
||||
|
||||
// Saves versions in the format x.x.x (e.g. 1.20.1).
|
||||
minecraftVersion = plugin.getServer().getBukkitVersion().split(Pattern.quote("-"))[0];
|
||||
|
||||
}
|
||||
|
||||
public int compareVersions(String version1, String version2) {
|
||||
String[] levels1 = version1.split("\\.");
|
||||
String[] levels2 = version2.split("\\.");
|
||||
int length = Math.max(levels1.length, levels2.length);
|
||||
|
||||
final String[] levels1 = version1.split("\\.");
|
||||
final String[] levels2 = version2.split("\\.");
|
||||
final int length = Math.max(levels1.length, levels2.length);
|
||||
for (int i = 0; i < length; i++) {
|
||||
Integer v1 = i < levels1.length ? Integer.parseInt(levels1[i]) : 0;
|
||||
Integer v2 = i < levels2.length ? Integer.parseInt(levels2[i]) : 0;
|
||||
int compare = v1.compareTo(v2);
|
||||
|
||||
final Integer v1 = i < levels1.length ? Integer.parseInt(levels1[i]) : 0;
|
||||
final Integer v2 = i < levels2.length ? Integer.parseInt(levels2[i]) : 0;
|
||||
final int compare = v1.compareTo(v2);
|
||||
if (compare != 0) {
|
||||
|
||||
return compare;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
public boolean isOneDotX(int majorRelease) {
|
||||
return minecraftVersion.equals("1." + majorRelease) || minecraftVersion.startsWith("1." + majorRelease + ".");
|
||||
|
||||
return minecraftVersion.equals("1." + majorRelease)
|
||||
|| StringUtils.startsWith(minecraftVersion, "1." + majorRelease + ".");
|
||||
|
||||
}
|
||||
|
||||
public boolean isOneDotXOrHigher(int majorRelease) {
|
||||
for (int i = majorRelease; i < 40; i++)
|
||||
if (minecraftVersion.equals("1." + i) || minecraftVersion.startsWith("1." + i + ".")) return true;
|
||||
return minecraftVersion.startsWith("2.");
|
||||
|
||||
for (int i = majorRelease; i < 40; i++) {
|
||||
|
||||
if (minecraftVersion.equals("1." + i) || StringUtils.startsWith(minecraftVersion, "1." + i + ".")) {
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return StringUtils.startsWith(minecraftVersion, "2.");
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -14,13 +14,11 @@ import com.comphenix.protocol.events.PacketContainer;
|
||||
import com.comphenix.protocol.wrappers.EnumWrappers;
|
||||
import com.comphenix.protocol.wrappers.WrappedChatComponent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import net.md_5.bungee.api.ChatMessageType;
|
||||
import net.md_5.bungee.api.chat.TextComponent;
|
||||
import org.bukkit.ChatColor;
|
||||
import net.kyori.adventure.text.Component;
|
||||
import net.kyori.adventure.text.serializer.gson.GsonComponentSerializer;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.scheduler.BukkitRunnable;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
@@ -30,65 +28,95 @@ public class ActionBarMgr {
|
||||
private final List<Player> actionBars = new ArrayList<>();
|
||||
|
||||
public ActionBarMgr(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
startTask();
|
||||
|
||||
}
|
||||
|
||||
private void startTask() {
|
||||
|
||||
new BukkitRunnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
for (Player p : actionBars) {
|
||||
|
||||
try {
|
||||
sendActionBar(p, plugin.replacePlaceholders(plugin.getMessage("ActionBarMessage"), p));
|
||||
|
||||
sendActionBar(p, plugin.expandPlaceholders(p, plugin.getMessage("ActionBarMessage"), p));
|
||||
|
||||
} catch (Exception | NoSuchMethodError | NoClassDefFoundError e) {
|
||||
|
||||
cancel();
|
||||
plugin.logException(e);
|
||||
plugin.getLogger().warning("IMPORTANT: Please make sure that you are using the latest " +
|
||||
"dev-build of ProtocolLib and that your server is up-to-date! This error likely " +
|
||||
"happened inside of ProtocolLib code which is out of SuperVanish's control. It's part " +
|
||||
"of an optional feature module and can be removed safely by disabling " +
|
||||
"DisplayActionBar in the config file. Please report this " +
|
||||
"error if you can reproduce it on an up-to-date server with only latest " +
|
||||
"ProtocolLib and latest SV installed.");
|
||||
}
|
||||
}
|
||||
}
|
||||
}.runTaskTimer(plugin, 0, 2 * 20);
|
||||
plugin.getLogger().warning("IMPORTANT: Please make sure that you are using the latest "
|
||||
+ "dev-build of ProtocolLib and that your server is up-to-date! This error likely "
|
||||
+ "happened inside of ProtocolLib code which is out of SuperVanish's control. It's part "
|
||||
+ "of an optional feature module and can be removed safely by disabling "
|
||||
+ "DisplayActionBar in the config file. Please report this "
|
||||
+ "error if you can reproduce it on an up-to-date server with only latest "
|
||||
+ "ProtocolLib and latest SV installed.");
|
||||
|
||||
}
|
||||
|
||||
private void sendActionBar(Player p, String bar) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}.runTaskTimer(plugin, 0, 2 * 20);
|
||||
|
||||
}
|
||||
|
||||
private void sendActionBar(Player p, Component bar) {
|
||||
|
||||
try {
|
||||
Class.forName("net.md_5.bungee.api.chat.ComponentBuilder");
|
||||
p.spigot().sendMessage(ChatMessageType.ACTION_BAR, TextComponent.fromLegacyText(bar));
|
||||
} catch (ClassNotFoundException | NoSuchMethodError | NoClassDefFoundError er) {
|
||||
String json = "{\"text\": \"" + ChatColor.translateAlternateColorCodes('&', bar) + "\"}";
|
||||
|
||||
p.sendActionBar(bar);
|
||||
|
||||
} catch (NoSuchMethodError | NoClassDefFoundError er) {
|
||||
|
||||
String json = GsonComponentSerializer.gson().serialize(bar);
|
||||
WrappedChatComponent msg = WrappedChatComponent.fromJson(json);
|
||||
PacketContainer chatMsg = new PacketContainer(PacketType.Play.Server.CHAT);
|
||||
chatMsg.getChatComponents().write(0, msg);
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(12))
|
||||
try {
|
||||
|
||||
chatMsg.getChatTypes().write(0, EnumWrappers.ChatType.GAME_INFO);
|
||||
|
||||
} catch (NoSuchMethodError e) {
|
||||
p.spigot().sendMessage(ChatMessageType.ACTION_BAR, TextComponent.fromLegacyText
|
||||
("SuperVanish: Please update ProtocolLib"));
|
||||
|
||||
p.sendActionBar(Component.text("SuperVanish: Please update ProtocolLib"));
|
||||
|
||||
}
|
||||
else
|
||||
chatMsg.getBytes().write(0, (byte) 2);
|
||||
try {
|
||||
|
||||
ProtocolLibrary.getProtocolManager().sendServerPacket(p, chatMsg);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
throw new RuntimeException("Cannot send packet " + chatMsg, e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void addActionBar(Player p) {
|
||||
|
||||
actionBars.add(p);
|
||||
|
||||
}
|
||||
|
||||
public void removeActionBar(Player p) {
|
||||
|
||||
actionBars.remove(p);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -8,11 +8,6 @@
|
||||
|
||||
package de.myzelyam.supervanish.visibility;
|
||||
|
||||
import de.myzelyam.api.vanish.PlayerVanishStateChangeEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.HashSet;
|
||||
@@ -21,85 +16,121 @@ import java.util.Set;
|
||||
import java.util.UUID;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.bukkit.Bukkit;
|
||||
|
||||
import de.myzelyam.api.vanish.PlayerVanishStateChangeEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
|
||||
public class FileVanishStateMgr extends VanishStateMgr {
|
||||
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public FileVanishStateMgr(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isVanished(final UUID uuid) {
|
||||
|
||||
return getVanishedPlayersOnFile().contains(uuid);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setVanishedState(final UUID uuid, String name, boolean hide, String causeName) {
|
||||
PlayerVanishStateChangeEvent event = new PlayerVanishStateChangeEvent(uuid, name, hide, causeName);
|
||||
|
||||
final PlayerVanishStateChangeEvent event = new PlayerVanishStateChangeEvent(uuid, name, hide, causeName);
|
||||
Bukkit.getPluginManager().callEvent(event);
|
||||
if (event.isCancelled()) return;
|
||||
List<String> vanishedPlayerUUIDStrings = plugin.getPlayerData().getStringList("InvisiblePlayers");
|
||||
if (hide)
|
||||
vanishedPlayerUUIDStrings.add(uuid.toString());
|
||||
else
|
||||
vanishedPlayerUUIDStrings.remove(uuid.toString());
|
||||
plugin.getPlayerData().set("InvisiblePlayers", vanishedPlayerUUIDStrings);
|
||||
if (hide)
|
||||
if (event.isCancelled()) {
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
final Set<UUID> vanishedPlayers = getVanishedPlayersOnFile();
|
||||
if (hide) {
|
||||
|
||||
vanishedPlayers.add(uuid);
|
||||
|
||||
} else {
|
||||
|
||||
vanishedPlayers.remove(uuid);
|
||||
|
||||
}
|
||||
|
||||
setVanishedPlayersOnFile(vanishedPlayers);
|
||||
if (hide) {
|
||||
|
||||
plugin.getPlayerData().set("PlayerData." + uuid + ".information.name", name);
|
||||
plugin.getConfigMgr().getPlayerDataFile().save();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<UUID> getVanishedPlayers() {
|
||||
|
||||
return getVanishedPlayersOnFile();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public Collection<UUID> getOnlineVanishedPlayers() {
|
||||
Set<UUID> onlineVanishedPlayers = new HashSet<>();
|
||||
for (UUID vanishedUUID : getVanishedPlayers()) {
|
||||
if (Bukkit.getPlayer(vanishedUUID) != null)
|
||||
onlineVanishedPlayers.add(vanishedUUID);
|
||||
}
|
||||
|
||||
final Set<UUID> onlineVanishedPlayers = new HashSet<>();
|
||||
getVanishedPlayers().stream().filter(vanishedUUID -> Bukkit.getPlayer(vanishedUUID) != null)
|
||||
.forEach(onlineVanishedPlayers::add);
|
||||
|
||||
return onlineVanishedPlayers;
|
||||
|
||||
}
|
||||
|
||||
public UUID getVanishedUUIDFromNameOnFile(String name) {
|
||||
for (UUID uuid : getVanishedPlayersOnFile()) {
|
||||
if (plugin.getPlayerData().getString("PlayerData." + uuid + ".information.name")
|
||||
.equalsIgnoreCase(name)) {
|
||||
return uuid;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
|
||||
return getVanishedPlayersOnFile().stream()
|
||||
.filter(uuid -> StringUtils.equalsIgnoreCase(
|
||||
plugin.getPlayerData().getString("PlayerData." + uuid + ".information.name"), name))
|
||||
.findFirst().orElse(null);
|
||||
|
||||
}
|
||||
|
||||
private Set<UUID> getVanishedPlayersOnFile() {
|
||||
List<String> vanishedPlayerUUIDStrings = plugin.getPlayerData().getStringList("InvisiblePlayers");
|
||||
Set<UUID> vanishedPlayerUUIDs = new HashSet<>();
|
||||
for (String uuidString : new ArrayList<>(vanishedPlayerUUIDStrings)) {
|
||||
|
||||
final List<String> vanishedPlayerUUIDStrings = plugin.getPlayerData().getStringList("InvisiblePlayers");
|
||||
final Set<UUID> vanishedPlayerUUIDs = new HashSet<>();
|
||||
new ArrayList<>(vanishedPlayerUUIDStrings).forEach(uuidString -> {
|
||||
|
||||
try {
|
||||
|
||||
vanishedPlayerUUIDs.add(UUID.fromString(uuidString));
|
||||
|
||||
} catch (IllegalArgumentException e) {
|
||||
|
||||
vanishedPlayerUUIDStrings.remove(uuidString);
|
||||
plugin.log(Level.WARNING,
|
||||
"The data.yml file contains an invalid player uuid," +
|
||||
" deleting it.");
|
||||
plugin.log(Level.WARNING, "The data.yml file contains an invalid player uuid," + " deleting it.");
|
||||
plugin.getPlayerData().set("InvisiblePlayers", vanishedPlayerUUIDStrings);
|
||||
plugin.getConfigMgr().getPlayerDataFile().save();
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
return vanishedPlayerUUIDs;
|
||||
|
||||
}
|
||||
|
||||
private void setVanishedPlayersOnFile(Set<UUID> vanishedPlayers) {
|
||||
List<String> vanishedPlayerUUIDStrings = new ArrayList<>();
|
||||
for (UUID uuid : vanishedPlayers)
|
||||
vanishedPlayerUUIDStrings.add(uuid.toString());
|
||||
plugin.getPlayerData().set("InvisiblePlayers",
|
||||
vanishedPlayerUUIDStrings);
|
||||
|
||||
final List<String> vanishedPlayerUUIDStrings = new ArrayList<>();
|
||||
vanishedPlayers.forEach(uuid -> vanishedPlayerUUIDStrings.add(uuid.toString()));
|
||||
plugin.getPlayerData().set("InvisiblePlayers", vanishedPlayerUUIDStrings);
|
||||
plugin.getConfigMgr().getPlayerDataFile().save();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -20,32 +20,47 @@ public class PaperServerPingListener implements Listener {
|
||||
private final SuperVanish plugin;
|
||||
|
||||
public PaperServerPingListener(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.HIGH)
|
||||
public void onServerListPing(PaperServerListPingEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
final FileConfiguration settings = plugin.getSettings();
|
||||
if (!settings.getBoolean("ExternalInvisibility.ServerList.AdjustAmountOfOnlinePlayers")
|
||||
&& !settings.getBoolean("ExternalInvisibility.ServerList.AdjustListOfLoggedInPlayers"))
|
||||
return;
|
||||
Collection<UUID> onlineVanishedPlayers = plugin.getVanishStateMgr().getOnlineVanishedPlayers();
|
||||
int vanishedPlayersCount = onlineVanishedPlayers.size(),
|
||||
playerCount = Bukkit.getOnlinePlayers().size();
|
||||
int vanishedPlayersCount = onlineVanishedPlayers.size(), playerCount = Bukkit.getOnlinePlayers().size();
|
||||
if (settings.getBoolean("ExternalInvisibility.ServerList.AdjustAmountOfOnlinePlayers")) {
|
||||
|
||||
e.setNumPlayers(playerCount - vanishedPlayersCount);
|
||||
|
||||
}
|
||||
|
||||
if (settings.getBoolean("ExternalInvisibility.ServerList.AdjustListOfLoggedInPlayers")) {
|
||||
|
||||
List<PlayerProfile> playerSample = e.getPlayerSample();
|
||||
|
||||
playerSample.removeIf(profile -> onlineVanishedPlayers.contains(profile.getId()));
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
if (!errorLogged) {
|
||||
|
||||
plugin.logException(er);
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -35,46 +35,75 @@ public class ServerListPacketListener extends PacketAdapter {
|
||||
private boolean errorLogged = false;
|
||||
|
||||
public ServerListPacketListener(SuperVanish plugin) {
|
||||
|
||||
super(plugin, ListenerPriority.NORMAL, PacketType.Status.Server.SERVER_INFO);
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for legacy ProtocolLib API
|
||||
*/
|
||||
public ServerListPacketListener(SuperVanish plugin, boolean use_legacy) {
|
||||
//noinspection deprecation
|
||||
super(plugin, ListenerPriority.NORMAL, PacketType.Status.Server.OUT_SERVER_INFO);
|
||||
|
||||
super(plugin, ListenerPriority.NORMAL, getLegacyServerInfoPacketType());
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
private static PacketType getLegacyServerInfoPacketType() {
|
||||
|
||||
try {
|
||||
|
||||
return (PacketType) PacketType.Status.Server.class.getField("OUT_SERVER_INFO").get(null);
|
||||
|
||||
} catch (ReflectiveOperationException e) {
|
||||
|
||||
throw new IllegalStateException("Legacy ProtocolLib server info packet type is unavailable", e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static void register(SuperVanish plugin) {
|
||||
|
||||
// Use Paper event listener if available
|
||||
try {
|
||||
|
||||
Class.forName("com.destroystokyo.paper.event.server.PaperServerListPingEvent");
|
||||
plugin.getLogger().log(Level.INFO, "Hooked into PaperSpigot for server list ping support");
|
||||
plugin.getServer().getPluginManager().registerEvents(new PaperServerPingListener(plugin), plugin);
|
||||
|
||||
} catch (ClassNotFoundException ignored) {
|
||||
|
||||
// Otherwise use ProtocolLib
|
||||
if (plugin.getVersionUtil().isOneDotXOrHigher(19)) {
|
||||
|
||||
ProtocolLibrary.getProtocolManager().addPacketListener(new ServerListPacketListener(plugin));
|
||||
|
||||
} else {
|
||||
|
||||
ProtocolLibrary.getProtocolManager().addPacketListener(new ServerListPacketListener(plugin, true));
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static boolean isEnabled(SuperVanish plugin) {
|
||||
|
||||
final FileConfiguration config = plugin.getSettings();
|
||||
return config.getBoolean(
|
||||
"ExternalInvisibility.ServerList.AdjustAmountOfOnlinePlayers")
|
||||
|| config.getBoolean(
|
||||
"ExternalInvisibility.ServerList.AdjustListOfLoggedInPlayers");
|
||||
return config.getBoolean("ExternalInvisibility.ServerList.AdjustAmountOfOnlinePlayers")
|
||||
|| config.getBoolean("ExternalInvisibility.ServerList.AdjustListOfLoggedInPlayers");
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPacketSending(PacketEvent e) {
|
||||
|
||||
try {
|
||||
|
||||
final FileConfiguration settings = plugin.getSettings();
|
||||
if (!settings.getBoolean("ExternalInvisibility.ServerList.AdjustAmountOfOnlinePlayers")
|
||||
&& !settings.getBoolean("ExternalInvisibility.ServerList.AdjustListOfLoggedInPlayers"))
|
||||
@@ -84,30 +113,62 @@ public class ServerListPacketListener extends PacketAdapter {
|
||||
int vanishedPlayersCount = plugin.getVanishStateMgr().getOnlineVanishedPlayers().size(),
|
||||
playerCount = Bukkit.getOnlinePlayers().size();
|
||||
if (settings.getBoolean("ExternalInvisibility.ServerList.AdjustAmountOfOnlinePlayers")) {
|
||||
|
||||
ping.setPlayersOnline(playerCount - vanishedPlayersCount);
|
||||
|
||||
}
|
||||
|
||||
if (settings.getBoolean("ExternalInvisibility.ServerList.AdjustListOfLoggedInPlayers")) {
|
||||
|
||||
List<WrappedGameProfile> wrappedGameProfiles = new ArrayList<>(ping.getPlayers());
|
||||
Iterator<WrappedGameProfile> iterator = wrappedGameProfiles.iterator();
|
||||
while (iterator.hasNext()) {
|
||||
|
||||
if (onlineVanishedPlayers.contains(iterator.next().getUUID())) {
|
||||
|
||||
iterator.remove();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
ping.setPlayers(wrappedGameProfiles);
|
||||
|
||||
}
|
||||
|
||||
e.getPacket().getServerPings().write(0, ping);
|
||||
|
||||
} catch (Exception er) {
|
||||
|
||||
if (!errorLogged) {
|
||||
if (er.getMessage() != null && er.getMessage().contains("Unable to construct new instance using public net.minecraft.network.protocol.status.ServerPing")) {
|
||||
plugin.getLogger().warning("The spigot-sided serverlist features are not supported by ProtocolLib on your server. Please make sure you are using the latest ProtocolLib dev build. (" + er.getMessage() + ")\n");
|
||||
} else if (er.getMessage() != null && er.getMessage().contains("Cannot assign field \"online\" because \"this.playerSample\" is null")) {
|
||||
plugin.getLogger().warning("The spigot-sided serverlist features are not supported yet by ProtocolLib. Please make sure you are using the latest ProtocolLib dev build.");
|
||||
|
||||
if (er.getMessage() != null && er.getMessage().contains(
|
||||
"Unable to construct new instance using public net.minecraft.network.protocol.status.ServerPing"))
|
||||
{
|
||||
|
||||
plugin.getLogger().warning(
|
||||
"The spigot-sided serverlist features are not supported by ProtocolLib on your server. Please make sure you are using the latest ProtocolLib dev build. ("
|
||||
+ er.getMessage() + ")\n");
|
||||
|
||||
} else if (er.getMessage() != null && er.getMessage()
|
||||
.contains("Cannot assign field \"online\" because \"this.playerSample\" is null"))
|
||||
{
|
||||
|
||||
plugin.getLogger().warning(
|
||||
"The spigot-sided serverlist features are not supported yet by ProtocolLib. Please make sure you are using the latest ProtocolLib dev build.");
|
||||
|
||||
} else {
|
||||
|
||||
plugin.logException(er);
|
||||
|
||||
}
|
||||
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -19,7 +19,9 @@ public abstract class VanishStateMgr {
|
||||
protected final SuperVanishPlugin plugin;
|
||||
|
||||
public VanishStateMgr(SuperVanishPlugin plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
|
||||
}
|
||||
|
||||
public abstract boolean isVanished(final UUID uuid);
|
||||
@@ -27,10 +29,13 @@ public abstract class VanishStateMgr {
|
||||
public abstract void setVanishedState(final UUID uuid, String name, boolean hide, String causeName);
|
||||
|
||||
public final void setVanishedState(final UUID uuid, String name, boolean hide) {
|
||||
|
||||
setVanishedState(uuid, name, hide, null);
|
||||
|
||||
}
|
||||
|
||||
public abstract Set<UUID> getVanishedPlayers();
|
||||
|
||||
public abstract Collection<UUID> getOnlineVanishedPlayers();
|
||||
|
||||
}
|
||||
@@ -15,7 +15,6 @@ import de.myzelyam.api.vanish.PostPlayerShowEvent;
|
||||
import de.myzelyam.supervanish.SuperVanish;
|
||||
import de.myzelyam.supervanish.utils.Validation;
|
||||
import de.myzelyam.supervanish.visibility.hiders.PlayerHider;
|
||||
import lombok.Getter;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.GameMode;
|
||||
import org.bukkit.configuration.file.FileConfiguration;
|
||||
@@ -27,49 +26,63 @@ import java.util.logging.Level;
|
||||
|
||||
public class VisibilityChanger {
|
||||
|
||||
@Getter
|
||||
private final PlayerHider hider;
|
||||
private final SuperVanish plugin;
|
||||
private final FileConfiguration config;
|
||||
|
||||
public VisibilityChanger(PlayerHider hider, SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
this.hider = hider;
|
||||
config = plugin.getSettings();
|
||||
|
||||
}
|
||||
|
||||
public void hidePlayer(Player player) {
|
||||
|
||||
hidePlayer(player, null, false);
|
||||
|
||||
}
|
||||
|
||||
public void showPlayer(Player player) {
|
||||
|
||||
showPlayer(player, null, false);
|
||||
|
||||
}
|
||||
|
||||
public void hidePlayer(Player player, String hiderName) {
|
||||
|
||||
hidePlayer(player, hiderName, false);
|
||||
|
||||
}
|
||||
|
||||
public void showPlayer(Player player, String hiderName) {
|
||||
|
||||
showPlayer(player, hiderName, false);
|
||||
|
||||
}
|
||||
|
||||
public void hidePlayer(final Player player, final String hiderName, boolean silent) {
|
||||
|
||||
try {
|
||||
|
||||
Validation.checkNotNull("player cannot be null", player);
|
||||
if (plugin.getVanishStateMgr().isVanished(player.getUniqueId())) {
|
||||
plugin.log(Level.WARNING, "Failed to hide " + player.getName()
|
||||
+ " since that player is already invisible.");
|
||||
|
||||
plugin.log(Level.WARNING,
|
||||
"Failed to hide " + player.getName() + " since that player is already invisible.");
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
// call event
|
||||
PlayerHideEvent e = new PlayerHideEvent(player, silent);
|
||||
plugin.getServer().getPluginManager().callEvent(e);
|
||||
if (e.isCancelled()) return;
|
||||
if (e.isCancelled())
|
||||
return;
|
||||
silent = e.isSilent();
|
||||
// state
|
||||
plugin.getVanishStateMgr().setVanishedState(player.getUniqueId(),
|
||||
player.getName(), true, hiderName);
|
||||
plugin.getVanishStateMgr().setVanishedState(player.getUniqueId(), player.getName(), true, hiderName);
|
||||
// metadata
|
||||
player.setMetadata("vanished", new FixedMetadataValue(plugin, true));
|
||||
// hide
|
||||
@@ -78,12 +91,18 @@ public class VisibilityChanger {
|
||||
plugin.getVisibilityChanger().getHider().setHidden(player, onlinePlayer, true);
|
||||
// fly check
|
||||
if (config.getBoolean("InvisibilityFeatures.Fly.Enable")) {
|
||||
|
||||
player.setAllowFlight(true);
|
||||
|
||||
}
|
||||
|
||||
// action bars
|
||||
if (plugin.getActionBarMgr() != null && config.getBoolean("MessageOptions.DisplayActionBar")) {
|
||||
|
||||
plugin.getActionBarMgr().addActionBar(player);
|
||||
|
||||
}
|
||||
|
||||
// sleep state
|
||||
player.setSleepingIgnored(true);
|
||||
// chat message
|
||||
@@ -93,33 +112,44 @@ public class VisibilityChanger {
|
||||
plugin.sendMessage(player, "OnVanishCausedByOtherPlayer", player, hiderName);
|
||||
// stop player from being a mob target
|
||||
if (config.getBoolean("InvisibilityFeatures.DisableMobTarget")) {
|
||||
player.getWorld().getEntities().stream()
|
||||
.filter(ent -> ent instanceof Creature)
|
||||
.map(ent -> (Creature) ent)
|
||||
.filter(mob -> mob.getTarget() != null)
|
||||
|
||||
player.getWorld().getEntities().stream().filter(ent -> ent instanceof Creature)
|
||||
.map(ent -> (Creature) ent).filter(mob -> mob.getTarget() != null)
|
||||
.filter(mob -> player.getUniqueId().equals(mob.getTarget().getUniqueId()))
|
||||
.forEach(mob -> mob.setTarget(null));
|
||||
|
||||
}
|
||||
|
||||
// call post event
|
||||
PostPlayerHideEvent e2 = new PostPlayerHideEvent(player, silent);
|
||||
plugin.getServer().getPluginManager().callEvent(e2);
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
plugin.logException(e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void showPlayer(final Player player, final String showerName, boolean silent) {
|
||||
|
||||
try {
|
||||
|
||||
Validation.checkNotNull("player cannot be null", player);
|
||||
if (!plugin.getVanishStateMgr().isVanished(player.getUniqueId())) {
|
||||
|
||||
plugin.log(Level.WARNING,
|
||||
"Failed to show " + player.getName() + " since that player is already visible.");
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
// call event
|
||||
PlayerShowEvent e = new PlayerShowEvent(player, silent);
|
||||
plugin.getServer().getPluginManager().callEvent(e);
|
||||
if (e.isCancelled()) return;
|
||||
if (e.isCancelled())
|
||||
return;
|
||||
silent = e.isSilent();
|
||||
// metadata
|
||||
player.removeMetadata("vanished", plugin);
|
||||
@@ -129,13 +159,15 @@ public class VisibilityChanger {
|
||||
plugin.getVisibilityChanger().getHider().setHidden(player, onlinePlayer, false);
|
||||
// action bars
|
||||
if (plugin.getActionBarMgr() != null && config.getBoolean("MessageOptions.DisplayActionBar")) {
|
||||
|
||||
plugin.getActionBarMgr().removeActionBar(player);
|
||||
|
||||
}
|
||||
|
||||
// sleep state
|
||||
player.setSleepingIgnored(false);
|
||||
// state
|
||||
plugin.getVanishStateMgr().setVanishedState(player.getUniqueId(),
|
||||
player.getName(), false, showerName);
|
||||
plugin.getVanishStateMgr().setVanishedState(player.getUniqueId(), player.getName(), false, showerName);
|
||||
// chat message
|
||||
if (showerName == null)
|
||||
plugin.sendMessage(player, "OnReappear", player);
|
||||
@@ -143,18 +175,31 @@ public class VisibilityChanger {
|
||||
plugin.sendMessage(player, "OnReappearCausedByOtherPlayer", player, showerName);
|
||||
// fly
|
||||
// remove fly if not spectator or creative and no perm
|
||||
if (config.getBoolean("InvisibilityFeatures.Fly.DisableOnReappear")
|
||||
&& !player.hasPermission("sv.keepfly")
|
||||
&& (player.getGameMode() == GameMode.SURVIVAL
|
||||
|| player.getGameMode() == GameMode.ADVENTURE)
|
||||
&& config.getBoolean("InvisibilityFeatures.Fly.Enable")) {
|
||||
if (config.getBoolean("InvisibilityFeatures.Fly.DisableOnReappear") && !player.hasPermission("sv.keepfly")
|
||||
&& (player.getGameMode() == GameMode.SURVIVAL || player.getGameMode() == GameMode.ADVENTURE)
|
||||
&& config.getBoolean("InvisibilityFeatures.Fly.Enable"))
|
||||
{
|
||||
|
||||
player.setAllowFlight(false);
|
||||
|
||||
}
|
||||
|
||||
// call post event
|
||||
PostPlayerShowEvent e2 = new PostPlayerShowEvent(player, silent);
|
||||
plugin.getServer().getPluginManager().callEvent(e2);
|
||||
|
||||
} catch (Exception e) {
|
||||
|
||||
plugin.logException(e);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public PlayerHider getHider() {
|
||||
|
||||
return hider;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -30,75 +30,116 @@ public abstract class PlayerHider implements Listener {
|
||||
protected final Map<Player, Set<Player>> playerHiddenFromPlayersMap = new ConcurrentHashMap<>();
|
||||
|
||||
public PlayerHider(SuperVanish plugin) {
|
||||
|
||||
this.plugin = plugin;
|
||||
registerQuitListener();
|
||||
|
||||
}
|
||||
|
||||
public abstract String getName();
|
||||
|
||||
public boolean isHidden(Player player, Player viewer) {
|
||||
return !player.getUniqueId().equals(viewer.getUniqueId())
|
||||
&& playerHiddenFromPlayersMap.containsKey(player)
|
||||
|
||||
return !player.getUniqueId().equals(viewer.getUniqueId()) && playerHiddenFromPlayersMap.containsKey(player)
|
||||
&& playerHiddenFromPlayersMap.get(player).contains(viewer);
|
||||
|
||||
}
|
||||
|
||||
public boolean isHidden(UUID playerUUID, Player viewer) {
|
||||
if (playerUUID.equals(viewer.getUniqueId())) return false;
|
||||
for (Player p : playerHiddenFromPlayersMap.keySet()) {
|
||||
if (p.getUniqueId().equals(playerUUID)) {
|
||||
return playerHiddenFromPlayersMap.get(p).contains(viewer);
|
||||
}
|
||||
}
|
||||
|
||||
if (playerUUID.equals(viewer.getUniqueId()))
|
||||
return false;
|
||||
for (Player p : playerHiddenFromPlayersMap.keySet()) {
|
||||
|
||||
if (p.getUniqueId().equals(playerUUID)) {
|
||||
|
||||
return playerHiddenFromPlayersMap.get(p).contains(viewer);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
public boolean isHidden(String playerName, Player viewer) {
|
||||
if (playerName.equalsIgnoreCase(viewer.getName())) return false;
|
||||
for (Player p : playerHiddenFromPlayersMap.keySet()) {
|
||||
if (p.getName().equalsIgnoreCase(playerName)) {
|
||||
return playerHiddenFromPlayersMap.get(p).contains(viewer);
|
||||
}
|
||||
}
|
||||
|
||||
if (playerName.equalsIgnoreCase(viewer.getName()))
|
||||
return false;
|
||||
for (Player p : playerHiddenFromPlayersMap.keySet()) {
|
||||
|
||||
if (p.getName().equalsIgnoreCase(playerName)) {
|
||||
|
||||
return playerHiddenFromPlayersMap.get(p).contains(viewer);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @return TRUE if the operation changed the state, FALSE if it did not
|
||||
*/
|
||||
public boolean setHidden(Player player, Player viewer, boolean hidden) {
|
||||
|
||||
if (!playerHiddenFromPlayersMap.containsKey(player))
|
||||
playerHiddenFromPlayersMap.put(player, new HashSet<>());
|
||||
if (viewer == player) return false;
|
||||
if (viewer == player)
|
||||
return false;
|
||||
Set<Player> hiddenFromPlayers = playerHiddenFromPlayersMap.get(player);
|
||||
if (hidden && !hiddenFromPlayers.contains(viewer)) {
|
||||
|
||||
hiddenFromPlayers.add(viewer);
|
||||
return true;
|
||||
|
||||
} else if (!hidden && hiddenFromPlayers.contains(viewer)) {
|
||||
|
||||
hiddenFromPlayers.remove(viewer);
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
public Set<Player> getHiddenPlayerKeys() {
|
||||
|
||||
return playerHiddenFromPlayersMap.keySet();
|
||||
|
||||
}
|
||||
|
||||
private void registerQuitListener() {
|
||||
|
||||
plugin.getServer().getPluginManager().registerEvents(new Listener() {
|
||||
|
||||
@EventHandler(priority = EventPriority.MONITOR)
|
||||
public void onQuit(final PlayerQuitEvent e) {
|
||||
|
||||
plugin.getServer().getScheduler().runTaskLater(plugin, new Runnable() {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
playerHiddenFromPlayersMap.remove(e.getPlayer());
|
||||
for (Player p : ImmutableSet.copyOf(playerHiddenFromPlayersMap.keySet())) {
|
||||
|
||||
playerHiddenFromPlayersMap.get(p).remove(e.getPlayer());
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}, 1);
|
||||
|
||||
}
|
||||
|
||||
}, plugin);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -19,47 +19,76 @@ public class PreventionHider extends PlayerHider implements Runnable {
|
||||
private int taskId;
|
||||
|
||||
public PreventionHider(SuperVanish plugin) {
|
||||
|
||||
super(plugin);
|
||||
if (!BukkitPlayerHidingUtil.isNewPlayerHidingAPISupported(plugin)) {
|
||||
|
||||
taskId = plugin.getServer().getScheduler().runTaskTimer(plugin, this, 2, 2).getTaskId();
|
||||
|
||||
}
|
||||
|
||||
// Server is Purpur 1.19.4 and ProtocolLib 5.0+ maps PLAYER_INFO to the new
|
||||
// ClientboundPlayerInfoUpdatePacket; ViaSuite re-encodes for clients on
|
||||
// 1.8-1.21.x.
|
||||
if (plugin.isUseProtocolLib() && plugin.getVersionUtil().isOneDotXOrHigher(8)
|
||||
&& !plugin.getVersionUtil().isOneDotXOrHigher(19)
|
||||
&& plugin.getSettings().getBoolean("InvisibilityFeatures.ModifyTablistPackets", true))
|
||||
PlayerInfoModule.register(plugin, this);
|
||||
if (plugin.isUseProtocolLib()
|
||||
&& plugin.getSettings().getBoolean("InvisibilityFeatures.ModifyTabCompletePackets", true)
|
||||
&& !plugin.getVersionUtil().isOneDotXOrHigher(21)) {
|
||||
&& !plugin.getVersionUtil().isOneDotXOrHigher(21))
|
||||
{
|
||||
|
||||
// Not supported anymore on 1.21 and above (ProtocolLib broken)
|
||||
TabCompleteModule.register(plugin, this);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean setHidden(Player player, Player viewer, boolean hidden) {
|
||||
|
||||
if (super.setHidden(player, viewer, hidden) || BukkitPlayerHidingUtil.isNewPlayerHidingAPISupported(plugin)) {
|
||||
if (hidden) BukkitPlayerHidingUtil.hidePlayer(player, viewer, plugin);
|
||||
else BukkitPlayerHidingUtil.showPlayer(player, viewer, plugin);
|
||||
|
||||
if (hidden)
|
||||
BukkitPlayerHidingUtil.hidePlayer(player, viewer, plugin);
|
||||
else
|
||||
BukkitPlayerHidingUtil.showPlayer(player, viewer, plugin);
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
|
||||
return "Prevention";
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
|
||||
for (Player hidden : playerHiddenFromPlayersMap.keySet()) {
|
||||
|
||||
if (BukkitPlayerHidingUtil.isNewPlayerHidingAPISupported(plugin)) {
|
||||
|
||||
plugin.getServer().getScheduler().cancelTask(taskId);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
for (Player viewer : playerHiddenFromPlayersMap.get(hidden)) {
|
||||
|
||||
BukkitPlayerHidingUtil.hidePlayer(hidden, viewer, plugin);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+55
-12
@@ -21,9 +21,14 @@ import org.bukkit.entity.Player;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* This is currently unused on Minecraft 1.19 or higher
|
||||
* Filters vanished players out of the server-bound PLAYER_INFO packet. On
|
||||
* Purpur 1.19.4 the server emits ClientboundPlayerInfoUpdatePacket which
|
||||
* ProtocolLib 5.0 maps to PacketType.Play.Server.PLAYER_INFO. ViaSuite handles
|
||||
* re-encoding for clients on 1.8-1.21.x, so this listener only needs to operate
|
||||
* on the server-native packet.
|
||||
*/
|
||||
public class PlayerInfoModule extends PacketAdapter {
|
||||
|
||||
@@ -33,46 +38,84 @@ public class PlayerInfoModule extends PacketAdapter {
|
||||
private boolean errorLogged = false;
|
||||
|
||||
public PlayerInfoModule(SuperVanish plugin, PlayerHider hider) {
|
||||
|
||||
super(plugin, ListenerPriority.HIGH, PacketType.Play.Server.PLAYER_INFO);
|
||||
this.plugin = plugin;
|
||||
this.hider = hider;
|
||||
|
||||
}
|
||||
|
||||
public static void register(SuperVanish plugin, PlayerHider hider) {
|
||||
|
||||
ProtocolLibrary.getProtocolManager().addPacketListener(new PlayerInfoModule(plugin, hider));
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPacketSending(PacketEvent event) {
|
||||
|
||||
// multiple events share same packet object
|
||||
event.setPacket(event.getPacket().shallowClone());
|
||||
try {
|
||||
|
||||
List<PlayerInfoData> infoDataList = new ArrayList<>(event.getPacket().getPlayerInfoDataLists().read(0));
|
||||
|
||||
Player receiver = event.getPlayer();
|
||||
for (PlayerInfoData infoData : ImmutableList.copyOf(infoDataList)) {
|
||||
if (hider.isHidden(infoData.getProfile().getUUID(), receiver)) {
|
||||
|
||||
UUID uuid = extractUUID(infoData);
|
||||
if (uuid == null)
|
||||
continue;
|
||||
if (hider.isHidden(uuid, receiver)) {
|
||||
|
||||
infoDataList.remove(infoData);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (infoDataList.isEmpty()) {
|
||||
|
||||
event.setCancelled(true);
|
||||
|
||||
}
|
||||
|
||||
event.getPacket().getPlayerInfoDataLists().write(0, infoDataList);
|
||||
|
||||
} catch (Exception | NoClassDefFoundError e) {
|
||||
if (e.getMessage() == null
|
||||
|| !e.getMessage().endsWith("is not supported for temporary players.")) {
|
||||
if (errorLogged) return;
|
||||
|
||||
if (e.getMessage() == null || !e.getMessage().endsWith("is not supported for temporary players.")) {
|
||||
|
||||
if (errorLogged)
|
||||
return;
|
||||
plugin.logException(e);
|
||||
plugin.getLogger().warning("IMPORTANT: Please make sure that you are using the latest " +
|
||||
"dev-build of ProtocolLib and that your server is up-to-date! This error likely " +
|
||||
"happened inside of ProtocolLib code which is out of SuperVanish's control. It's part " +
|
||||
"of an optional invisibility module and can be removed safely by disabling " +
|
||||
"ModifyTablistPackets in the config. Please report this " +
|
||||
"error if you can reproduce it on an up-to-date server with only latest " +
|
||||
"ProtocolLib and latest SV installed.");
|
||||
plugin.getLogger().warning("IMPORTANT: Please make sure that you are using the latest "
|
||||
+ "dev-build of ProtocolLib and that your server is up-to-date! This error likely "
|
||||
+ "happened inside of ProtocolLib code which is out of SuperVanish's control. It's part "
|
||||
+ "of an optional invisibility module and can be removed safely by disabling "
|
||||
+ "ModifyTablistPackets in the config. Please report this "
|
||||
+ "error if you can reproduce it on an up-to-date server with only latest "
|
||||
+ "ProtocolLib and latest SV installed.");
|
||||
errorLogged = true;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private UUID extractUUID(PlayerInfoData infoData) {
|
||||
|
||||
// On 1.19.3+ the per-entry profile is null for non-ADD_PLAYER actions, so
|
||||
// prefer
|
||||
// profileId which the wrapper exposes for both legacy and update packets.
|
||||
UUID uuid = infoData.getProfileId();
|
||||
if (uuid != null)
|
||||
return uuid;
|
||||
if (infoData.getProfile() != null)
|
||||
return infoData.getProfile().getUUID();
|
||||
return null;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
Loaded 100 of 104 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user