mirror of
https://github.com/songoda/SongodaCore.git
synced 2024-11-23 18:45:34 +01:00
merge with upstream
This commit is contained in:
commit
ccc9ef8810
207
.gitignore
vendored
207
.gitignore
vendored
@ -1,6 +1,177 @@
|
||||
### Eclipse ###
|
||||
.metadata
|
||||
bin/
|
||||
tmp/
|
||||
*.tmp
|
||||
*.bak
|
||||
*.swp
|
||||
*~.nib
|
||||
local.properties
|
||||
.settings/
|
||||
.loadpath
|
||||
.recommenders
|
||||
|
||||
# External tool builders
|
||||
.externalToolBuilders/
|
||||
|
||||
# Locally stored "Eclipse launch configurations"
|
||||
*.launch
|
||||
|
||||
# CDT- autotools
|
||||
.autotools
|
||||
|
||||
# Java annotation processor (APT)
|
||||
.factorypath
|
||||
|
||||
# PDT-specific (PHP Development Tools)
|
||||
.buildpath
|
||||
|
||||
# sbteclipse plugin
|
||||
.target
|
||||
|
||||
# Tern plugin
|
||||
.tern-project
|
||||
|
||||
# TeXlipse plugin
|
||||
.texlipse
|
||||
|
||||
# STS (Spring Tool Suite)
|
||||
.springBeans
|
||||
|
||||
# Code Recommenders
|
||||
.recommenders/
|
||||
|
||||
# Annotation Processing
|
||||
.apt_generated/
|
||||
|
||||
# Scala IDE specific (Scala & Java development for Eclipse)
|
||||
.cache-main
|
||||
.scala_dependencies
|
||||
.worksheet
|
||||
|
||||
### Eclipse Patch ###
|
||||
# Eclipse Core
|
||||
.project
|
||||
|
||||
# JDT-specific (Eclipse Java Development Tools)
|
||||
.classpath
|
||||
|
||||
# Annotation Processing
|
||||
.apt_generated
|
||||
|
||||
.sts4-cache/
|
||||
|
||||
### Intellij ###
|
||||
# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio and WebStorm
|
||||
# Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839
|
||||
|
||||
# User-specific stuff
|
||||
.idea/**/workspace.xml
|
||||
.idea/**/tasks.xml
|
||||
.idea/**/usage.statistics.xml
|
||||
.idea/**/dictionaries
|
||||
.idea/**/shelf
|
||||
|
||||
# Generated files
|
||||
.idea/**/contentModel.xml
|
||||
|
||||
# Sensitive or high-churn files
|
||||
.idea/**/dataSources/
|
||||
.idea/**/dataSources.ids
|
||||
.idea/**/dataSources.local.xml
|
||||
.idea/**/sqlDataSources.xml
|
||||
.idea/**/dynamic.xml
|
||||
.idea/**/uiDesigner.xml
|
||||
.idea/**/dbnavigator.xml
|
||||
|
||||
# Gradle
|
||||
.idea/**/gradle.xml
|
||||
.idea/**/libraries
|
||||
|
||||
# Gradle and Maven with auto-import
|
||||
auto-import.
|
||||
.idea/modules.xml
|
||||
.idea/*.iml
|
||||
.idea/modules
|
||||
*.iml
|
||||
*.ipr
|
||||
|
||||
# Mongo Explorer plugin
|
||||
.idea/**/mongoSettings.xml
|
||||
|
||||
# File-based project format
|
||||
*.iws
|
||||
|
||||
# IntelliJ
|
||||
out/
|
||||
|
||||
# mpeltonen/sbt-idea plugin
|
||||
.idea_modules/
|
||||
|
||||
# JIRA plugin
|
||||
atlassian-ide-plugin.xml
|
||||
|
||||
# Cursive Clojure plugin
|
||||
.idea/replstate.xml
|
||||
|
||||
# Crashlytics plugin (for Android Studio and IntelliJ)
|
||||
com_crashlytics_export_strings.xml
|
||||
crashlytics.properties
|
||||
crashlytics-build.properties
|
||||
fabric.properties
|
||||
|
||||
# Editor-based Rest Client
|
||||
.idea/httpRequests
|
||||
|
||||
# Android studio 3.1+ serialized cache file
|
||||
.idea/caches/build_file_checksums.ser
|
||||
|
||||
### Intellij Patch ###
|
||||
# Comment Reason: https://github.com/joeblau/gitignore.io/issues/186#issuecomment-215987721
|
||||
|
||||
*.iml
|
||||
modules.xml
|
||||
.idea/misc.xml
|
||||
*.ipr
|
||||
.idea/compiler.xml
|
||||
|
||||
# Sonarlint plugin
|
||||
.idea/**/sonarlint/
|
||||
|
||||
# SonarQube Plugin
|
||||
.idea/**/sonarIssues.xml
|
||||
|
||||
# Markdown Navigator plugin
|
||||
.idea/**/markdown-navigator.xml
|
||||
.idea/**/markdown-navigator/
|
||||
|
||||
### Java ###
|
||||
# Compiled class file
|
||||
*.class
|
||||
|
||||
# Log file
|
||||
*.log
|
||||
|
||||
# BlueJ files
|
||||
*.ctxt
|
||||
|
||||
# Mobile Tools for Java (J2ME)
|
||||
.mtj.tmp/
|
||||
|
||||
# Package Files #
|
||||
*.jar
|
||||
*.war
|
||||
*.nar
|
||||
*.ear
|
||||
*.zip
|
||||
*.tar.gz
|
||||
*.rar
|
||||
|
||||
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
|
||||
hs_err_pid*
|
||||
|
||||
### Maven ###
|
||||
target/
|
||||
.idea/
|
||||
songodaUpdater.iml
|
||||
pom.xml.tag
|
||||
pom.xml.releaseBackup
|
||||
pom.xml.versionsBackup
|
||||
@ -9,5 +180,33 @@ release.properties
|
||||
dependency-reduced-pom.xml
|
||||
buildNumber.properties
|
||||
.mvn/timing.properties
|
||||
nbactions.xml
|
||||
nb-configuration.xml
|
||||
.mvn/wrapper/maven-wrapper.jar
|
||||
.flattened-pom.xml
|
||||
|
||||
### NetBeans ###
|
||||
**/nbproject/private/
|
||||
**/nbproject/Makefile-*.mk
|
||||
**/nbproject/Package-*.bash
|
||||
build/
|
||||
nbbuild/
|
||||
dist/
|
||||
nbdist/
|
||||
.nb-gradle/
|
||||
|
||||
### Gradle ###
|
||||
.gradle
|
||||
|
||||
# Ignore Gradle GUI config
|
||||
gradle-app.setting
|
||||
|
||||
# Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored)
|
||||
!gradle-wrapper.jar
|
||||
|
||||
# Cache of project
|
||||
.gradletasknamecache
|
||||
|
||||
# # Work around https://youtrack.jetbrains.com/issue/IDEA-116898
|
||||
# gradle/wrapper/gradle-wrapper.properties
|
||||
|
||||
### Gradle Patch ###
|
||||
**/build/
|
||||
|
@ -4,7 +4,7 @@ stages:
|
||||
variables:
|
||||
name: "SongodaCore"
|
||||
path: "/builds/$CI_PROJECT_PATH"
|
||||
version: "2.2.7"
|
||||
version: "2.3.4"
|
||||
|
||||
build:
|
||||
stage: build
|
||||
|
5
.idea/codeStyles/codeStyleConfig.xml
Normal file
5
.idea/codeStyles/codeStyleConfig.xml
Normal file
@ -0,0 +1,5 @@
|
||||
<component name="ProjectCodeStyleConfiguration">
|
||||
<state>
|
||||
<option name="PREFERRED_PROJECT_CODE_STYLE" value="GoogleStyle" />
|
||||
</state>
|
||||
</component>
|
6
.idea/vcs.xml
Normal file
6
.idea/vcs.xml
Normal file
@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="VcsDirectoryMappings">
|
||||
<mapping directory="$PROJECT_DIR$" vcs="Git" />
|
||||
</component>
|
||||
</project>
|
41
Core/pom.xml
41
Core/pom.xml
@ -27,6 +27,34 @@
|
||||
<target>1.8</target>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-source-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>attach-sources</id>
|
||||
<goals>
|
||||
<goal>jar</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-javadoc-plugin</artifactId>
|
||||
<version>3.1.1</version>
|
||||
<configuration>
|
||||
<doclint>none</doclint>
|
||||
</configuration>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>attach-javadocs</id>
|
||||
<goals>
|
||||
<goal>jar</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-shade-plugin</artifactId>
|
||||
@ -86,10 +114,9 @@
|
||||
</build>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>com.destroystokyo.papermc</groupId>
|
||||
<artifactId>paper</artifactId>
|
||||
<version>1.14.4</version>
|
||||
<scope>provided</scope>
|
||||
<groupId>org.spigotmc</groupId>
|
||||
<artifactId>spigot</artifactId>
|
||||
<version>1.15</version>
|
||||
</dependency>
|
||||
<!--dependency>
|
||||
<groupId>org.spigotmc</groupId>
|
||||
@ -258,9 +285,9 @@
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.bgsoftware</groupId>
|
||||
<artifactId>WildStacker</artifactId>
|
||||
<version>2-9-0</version>
|
||||
<groupId>com.github.OmerBenGera</groupId>
|
||||
<artifactId>WildStackerAPI</artifactId>
|
||||
<version>b16</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
|
@ -315,7 +315,7 @@ public class CommandManager implements CommandExecutor, TabCompleter {
|
||||
// If we're on Paper 1.8, we need to register timings (spigot creates timings on init, paper creates it on register)
|
||||
// later versions of paper create timings if needed when the command is executed
|
||||
if (ServerProject.isServer(ServerProject.PAPER, ServerProject.TACO) && ServerVersion.isServerVersionBelow(ServerVersion.V1_9)) {
|
||||
commandObject.timings = co.aikar.timings.TimingsManager.getCommandTiming(plugin.getName().toLowerCase(), commandObject);
|
||||
// commandObject.timings = co.aikar.timings.TimingsManager.getCommandTiming(plugin.getName().toLowerCase(), commandObject);
|
||||
}
|
||||
|
||||
// Set command action
|
||||
|
@ -30,6 +30,16 @@ public enum CompatibleMaterial {
|
||||
DARK_OAK_DOOR_ITEM(431),
|
||||
|
||||
*/
|
||||
|
||||
/* 1.15 */
|
||||
BEE_SPAWN_EGG(),
|
||||
BEE_NEST(),
|
||||
BEEHIVE(),
|
||||
HONEY_BLOCK(),
|
||||
HONEY_BOTTLE(),
|
||||
HONEYCOMB(),
|
||||
HONEYCOMB_BLOCK(),
|
||||
|
||||
ACACIA_BOAT("BOAT_ACACIA"),
|
||||
ACACIA_BUTTON(),
|
||||
ACACIA_DOOR("ACACIA_DOOR_ITEM"),
|
||||
@ -348,7 +358,7 @@ public enum CompatibleMaterial {
|
||||
END_PORTAL_FRAME("ENDER_PORTAL_FRAME"),
|
||||
END_ROD,
|
||||
END_STONE("ENDER_STONE"),
|
||||
END_STONE_BRICKS,
|
||||
END_STONE_BRICKS("END_BRICKS"),
|
||||
END_STONE_BRICK_SLAB(),
|
||||
END_STONE_BRICK_STAIRS,
|
||||
END_STONE_BRICK_WALL,
|
||||
@ -617,7 +627,7 @@ public enum CompatibleMaterial {
|
||||
NETHERRACK,
|
||||
NETHER_BRICK("NETHER_BRICK_ITEM"),
|
||||
NETHER_BRICKS("NETHER_BRICK"),
|
||||
NETHER_BRICK_FENCE(),
|
||||
NETHER_BRICK_FENCE("NETHER_FENCE"),
|
||||
NETHER_BRICK_SLAB("STEP", (byte) 6),
|
||||
NETHER_BRICK_STAIRS,
|
||||
NETHER_BRICK_WALL,
|
||||
@ -2156,6 +2166,11 @@ public enum CompatibleMaterial {
|
||||
if(type == EntityType.MUSHROOM_COW) {
|
||||
return MOOSHROOM_SPAWN_EGG;
|
||||
}
|
||||
|
||||
if (type == EntityType.PIG_ZOMBIE) {
|
||||
return ZOMBIE_PIGMAN_SPAWN_EGG;
|
||||
}
|
||||
|
||||
return lookupMap.get(type.name() + "_SPAWN_EGG");
|
||||
}
|
||||
|
||||
|
@ -1,14 +1,15 @@
|
||||
package com.songoda.core.compatibility;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Stream;
|
||||
import org.bukkit.Color;
|
||||
import org.bukkit.Effect;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Particle;
|
||||
import org.bukkit.block.BlockFace;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
public class CompatibleParticleHandler {
|
||||
|
||||
public static enum ParticleType {
|
||||
@ -80,6 +81,11 @@ public class CompatibleParticleHandler {
|
||||
LANDING_LAVA(ServerVersion.V1_14, "LAVA"),
|
||||
FALLING_WATER(ServerVersion.V1_14, "DRIP_WATER"),
|
||||
/// End 1.14 ///
|
||||
DRIPPING_HONEY(ServerVersion.V1_15, "DRIP_WATER"),
|
||||
FALLING_HONEY(ServerVersion.V1_15, "DRIP_WATER"),
|
||||
FALLING_NECTAR(ServerVersion.V1_15, "DRIP_WATER"),
|
||||
LANDING_HONEY(ServerVersion.V1_15, "DRIP_WATER"),
|
||||
/// End 1.15 ///
|
||||
;
|
||||
|
||||
final boolean compatibilityMode;
|
||||
@ -214,17 +220,17 @@ public class CompatibleParticleHandler {
|
||||
public static void redstoneParticles(Location location, int red, int green, int blue) {
|
||||
redstoneParticles(location, red, green, blue, 1F, 1, 0);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Spawn colored redstone particles
|
||||
*
|
||||
*
|
||||
* @param location area to spawn the particle in
|
||||
* @param red red value 0-255
|
||||
* @param green green value 0-255
|
||||
* @param blue blue value 0-255
|
||||
* @param size (1.13+) size of the particles
|
||||
* @param count how many particles to spawn
|
||||
* @param radius how far to spread out the particles from location
|
||||
* @param red red value 0-255
|
||||
* @param green green value 0-255
|
||||
* @param blue blue value 0-255
|
||||
* @param size (1.13+) size of the particles
|
||||
* @param count how many particles to spawn
|
||||
* @param radius how far to spread out the particles from location
|
||||
*/
|
||||
public static void redstoneParticles(Location location, int red, int green, int blue, float size, int count, float radius) {
|
||||
if (ServerVersion.isServerVersionAtLeast(ServerVersion.V1_13)) {
|
||||
@ -247,23 +253,23 @@ public class CompatibleParticleHandler {
|
||||
float yy = (float) (radius * (Math.random() - Math.random()));
|
||||
float zz = (float) (radius * (Math.random() - Math.random()));
|
||||
Location at = location.clone().add(xx, yy, zz);
|
||||
LegacyParticleEffects.createParticle(at, LegacyParticleEffects.Type.REDSTONE,
|
||||
LegacyParticleEffects.createParticle(at, LegacyParticleEffects.Type.REDSTONE,
|
||||
red / 255F, green / 255F, blue / 255F, 1F, 0, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void bonemealSmoke(Location l) {
|
||||
final org.bukkit.World w = l.getWorld();
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SOUTH_EAST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SOUTH);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SOUTH_WEST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.EAST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SELF);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.WEST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.NORTH_EAST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.NORTH);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.NORTH_WEST);
|
||||
}
|
||||
public static void bonemealSmoke(Location l) {
|
||||
final org.bukkit.World w = l.getWorld();
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SOUTH_EAST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SOUTH);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SOUTH_WEST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.EAST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.SELF);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.WEST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.NORTH_EAST);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.NORTH);
|
||||
w.playEffect(l, Effect.SMOKE, BlockFace.NORTH_WEST);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -23,6 +23,29 @@ public enum CompatibleSound {
|
||||
// would using the raw strings be better?
|
||||
// 1.8 list:
|
||||
// https://www.minecraftforum.net/forums/mapping-and-modding-java-edition/mapping-and-modding-tutorials/2213619-1-8-all-playsound-sound-arguments
|
||||
|
||||
/* 1.15 */
|
||||
BLOCK_BEEHIVE_DRIP,
|
||||
BLOCK_BEEHIVE_ENTER,
|
||||
BLOCK_BEEHIVE_EXIT,
|
||||
BLOCK_BEEHIVE_SHEAR,
|
||||
BLOCK_BEEHIVE_WORK,
|
||||
BLOCK_HONEY_BLOCK_BREAK,
|
||||
BLOCK_HONEY_BLOCK_FALL,
|
||||
BLOCK_HONEY_BLOCK_HIT,
|
||||
BLOCK_HONEY_BLOCK_PLACE,
|
||||
BLOCK_HONEY_BLOCK_SLIDE,
|
||||
BLOCK_HONEY_BLOCK_STEP,
|
||||
ENTITY_BEE_DEATH,
|
||||
ENTITY_BEE_HURT,
|
||||
ENTITY_BEE_LOOP,
|
||||
ENTITY_BEE_LOOP_AGGRESSIVE,
|
||||
ENTITY_BEE_POLLINATE,
|
||||
ENTITY_BEE_STING,
|
||||
ENTITY_IRON_GOLEM_DAMAGE,
|
||||
ENTITY_IRON_GOLEM_REPAIR,
|
||||
ITEM_HONEY_BOTTLE_DRINK,
|
||||
|
||||
AMBIENT_CAVE(ServerVersion.V1_9, v("AMBIENCE_CAVE")),
|
||||
AMBIENT_UNDERWATER_ENTER,
|
||||
AMBIENT_UNDERWATER_EXIT,
|
||||
|
@ -613,6 +613,7 @@ public class Config extends ConfigSection {
|
||||
}
|
||||
yamlOptions.setIndent(indentation);
|
||||
yamlOptions.setDefaultFlowStyle(DumperOptions.FlowStyle.BLOCK);
|
||||
yamlOptions.setSplitLines(false);
|
||||
yamlRepresenter.setDefaultFlowStyle(DumperOptions.FlowStyle.BLOCK);
|
||||
StringWriter str = new StringWriter();
|
||||
if (headerComment != null) {
|
||||
|
@ -11,6 +11,7 @@ import java.util.stream.Collectors;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.Event.Result;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.Listener;
|
||||
@ -18,6 +19,7 @@ import org.bukkit.event.inventory.ClickType;
|
||||
import org.bukkit.event.inventory.InventoryAction;
|
||||
import org.bukkit.event.inventory.InventoryClickEvent;
|
||||
import org.bukkit.event.inventory.InventoryCloseEvent;
|
||||
import org.bukkit.event.inventory.InventoryDragEvent;
|
||||
import org.bukkit.event.inventory.InventoryType.SlotType;
|
||||
import org.bukkit.event.server.PluginDisableEvent;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
@ -158,6 +160,25 @@ public class GuiManager {
|
||||
this.manager = manager;
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.LOW)
|
||||
void onDragGUI(InventoryDragEvent event) {
|
||||
if (!(event.getWhoClicked() instanceof Player)) {
|
||||
return;
|
||||
}
|
||||
|
||||
Inventory openInv = event.getInventory();
|
||||
Gui gui;
|
||||
if (openInv.getHolder() != null && openInv.getHolder() instanceof GuiHolder
|
||||
&& ((GuiHolder) openInv.getHolder()).manager.uuid.equals(manager.uuid)) {
|
||||
gui = ((GuiHolder) openInv.getHolder()).getGUI();
|
||||
|
||||
if(event.getRawSlots().stream().filter(slot -> gui.inventory.getSize() > slot).anyMatch(slot -> !gui.unlockedCells.getOrDefault(slot, false))){
|
||||
event.setCancelled(true);
|
||||
event.setResult(Result.DENY);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@EventHandler(priority = EventPriority.LOW)
|
||||
void onClickGUI(InventoryClickEvent event) {
|
||||
if (!(event.getWhoClicked() instanceof Player)) {
|
||||
|
@ -61,6 +61,19 @@ public class EconomyManager {
|
||||
return manager.isEnabled() ? manager.getCurrentHook().formatEconomy(amt) : String.valueOf(amt);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the players available balance
|
||||
*
|
||||
* @param player player
|
||||
* @return the amount of available balance
|
||||
*/
|
||||
public static double getBalance(OfflinePlayer player) {
|
||||
if (!manager.isEnabled())
|
||||
return 0;
|
||||
return manager.getCurrentHook().getBalance(player);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Check to see if a player has at least some balance available. <br />
|
||||
* NOTE: using a default economy assumes that this library is shaded
|
||||
|
@ -6,6 +6,14 @@ import org.bukkit.OfflinePlayer;
|
||||
|
||||
public abstract class Economy implements Hook {
|
||||
|
||||
/**
|
||||
* Get the players available balance
|
||||
*
|
||||
* @param player player
|
||||
* @return the amount of available balance
|
||||
*/
|
||||
public abstract double getBalance(OfflinePlayer player);
|
||||
|
||||
/**
|
||||
* Check to see if a player has at least some balance available
|
||||
*
|
||||
|
@ -26,6 +26,11 @@ public class PlayerPointsEconomy extends Economy {
|
||||
return "PlayerPoints";
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getBalance(OfflinePlayer player) {
|
||||
return playerPoints.getAPI().look(player.getUniqueId());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasBalance(OfflinePlayer player, double cost) {
|
||||
int amount = convertAmount(cost);
|
||||
|
@ -30,6 +30,11 @@ public class ReserveEconomy extends Economy {
|
||||
return economyAPI.format(BigDecimal.valueOf(amt));
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getBalance(OfflinePlayer player) {
|
||||
return economyAPI.getBankHoldings(player.getUniqueId()).doubleValue();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasBalance(OfflinePlayer player, double cost) {
|
||||
return economyAPI.hasHoldings(player.getUniqueId(), new BigDecimal(cost));
|
||||
|
@ -9,7 +9,7 @@ public class VaultEconomy extends Economy {
|
||||
private final net.milkbowl.vault.economy.Economy vault;
|
||||
|
||||
public VaultEconomy() {
|
||||
// this returns null if we have Vault with no compatibe eco plugin
|
||||
// this returns null if we have Vault with no compatible eco plugin
|
||||
RegisteredServiceProvider<net.milkbowl.vault.economy.Economy> v = Bukkit.getServicesManager().getRegistration(net.milkbowl.vault.economy.Economy.class);
|
||||
if(v != null) {
|
||||
this.vault = v.getProvider();
|
||||
@ -34,6 +34,13 @@ public class VaultEconomy extends Economy {
|
||||
return vault != null ? vault.format(amt) : super.formatEconomy(amt);
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getBalance(OfflinePlayer player) {
|
||||
if (vault == null)
|
||||
return 0;
|
||||
return vault.getBalance(player);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasBalance(OfflinePlayer player, double cost) {
|
||||
return vault != null && vault.has(player, cost);
|
||||
|
@ -239,6 +239,8 @@ public class Locale {
|
||||
existingLang.setRootNodeSpacing(0);
|
||||
existingLang.save();
|
||||
}
|
||||
existingLang.setRootNodeSpacing(0);
|
||||
existingLang.save();
|
||||
return !added.isEmpty();
|
||||
} catch (InvalidConfigurationException ex) {
|
||||
plugin.getLogger().log(Level.SEVERE, "Error checking config " + existingFile.getName(), ex);
|
||||
@ -304,8 +306,12 @@ public class Locale {
|
||||
output.append(line1.substring(0, line1.length() - line.length()));
|
||||
}
|
||||
}
|
||||
|
||||
Matcher matcher;
|
||||
if ((line = line.replace('\r', ' ')).trim().isEmpty() || line.trim().startsWith("#") /* Comment */
|
||||
if ((line = line.replace('\r', ' ')
|
||||
.replaceAll("\\p{C}", "?")
|
||||
.replaceAll(";", "")).trim().isEmpty()
|
||||
|| line.trim().startsWith("#") /* Comment */
|
||||
// need to trim the search group because tab characters somehow ended up at the end of lines in a lot of these files
|
||||
|| !(matcher = OLD_NODE_PATTERN.matcher(line.trim())).find()) {
|
||||
if (line.startsWith("//")) {
|
||||
|
@ -1,22 +1,19 @@
|
||||
package com.songoda.core.utils;
|
||||
|
||||
import com.songoda.core.compatibility.CompatibleMaterial;
|
||||
import com.songoda.core.compatibility.ServerVersion;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.Effect;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.block.Block;
|
||||
import org.bukkit.block.BlockFace;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.EnumSet;
|
||||
import java.util.Set;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.CropState;
|
||||
import org.bukkit.Effect;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.block.Block;
|
||||
import org.bukkit.block.BlockFace;
|
||||
import org.bukkit.block.BlockState;
|
||||
import org.bukkit.material.Crops;
|
||||
|
||||
public class BlockUtils {
|
||||
|
||||
@ -69,10 +66,10 @@ public class BlockUtils {
|
||||
if (isOpenable(bType)) {
|
||||
toggleDoorStates(true, b);
|
||||
return true;
|
||||
} else if(bType == Material.LEVER) {
|
||||
} else if (bType == Material.LEVER) {
|
||||
toggleLever(b);
|
||||
return true;
|
||||
} else if(bType.name().endsWith("_BUTTON")) {
|
||||
} else if (bType.name().endsWith("_BUTTON")) {
|
||||
pressButton(b);
|
||||
return true;
|
||||
}
|
||||
@ -82,6 +79,7 @@ public class BlockUtils {
|
||||
|
||||
/**
|
||||
* Change a pressure plate's redstone state
|
||||
*
|
||||
* @param plate plate to update
|
||||
* @param power power to set to 0-15 (wood plates are active if greater than 0)
|
||||
*/
|
||||
@ -105,7 +103,7 @@ public class BlockUtils {
|
||||
Logger.getLogger(BlockUtils.class.getName()).log(Level.SEVERE, "Unexpected method error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static void pressButton(Block button) {
|
||||
if (useLegacy && legacySetBlockData != null) {
|
||||
_pressButtonLegacy(button);
|
||||
@ -113,7 +111,7 @@ public class BlockUtils {
|
||||
BlockUtilsModern._pressButtonModern(button);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static void releaseButton(Block button) {
|
||||
if (useLegacy && legacySetBlockData != null) {
|
||||
_releaseButtonLegacy(button);
|
||||
@ -124,7 +122,7 @@ public class BlockUtils {
|
||||
|
||||
private static void _pressButtonLegacy(Block button) {
|
||||
final Material m = button.getType();
|
||||
if(!m.name().endsWith("_BUTTON")) return;
|
||||
if (!m.name().endsWith("_BUTTON")) return;
|
||||
try {
|
||||
legacySetBlockData.invoke(button, (byte) (button.getData() | (31 & 0x8)));
|
||||
button.getState().update();
|
||||
@ -132,10 +130,10 @@ public class BlockUtils {
|
||||
Logger.getLogger(BlockUtils.class.getName()).log(Level.SEVERE, "Unexpected method error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static void _releaseButtonLegacy(Block button) {
|
||||
final Material m = button.getType();
|
||||
if(!m.name().endsWith("_BUTTON")) return;
|
||||
if (!m.name().endsWith("_BUTTON")) return;
|
||||
try {
|
||||
legacySetBlockData.invoke(button, (byte) (button.getData() & ~0x8));
|
||||
button.getState().update();
|
||||
@ -143,7 +141,7 @@ public class BlockUtils {
|
||||
Logger.getLogger(BlockUtils.class.getName()).log(Level.SEVERE, "Unexpected method error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static void toggleLever(Block lever) {
|
||||
if (useLegacy && legacySetBlockData != null) {
|
||||
_toggleLeverLegacy(lever);
|
||||
@ -154,7 +152,7 @@ public class BlockUtils {
|
||||
|
||||
private static void _toggleLeverLegacy(Block lever) {
|
||||
final Material m = lever.getType();
|
||||
if(m != Material.LEVER) return;
|
||||
if (m != Material.LEVER) return;
|
||||
try {
|
||||
legacySetBlockData.invoke(lever, (byte) (lever.getData() ^ 0x8));
|
||||
lever.getState().update();
|
||||
@ -189,6 +187,7 @@ public class BlockUtils {
|
||||
Logger.getLogger(BlockUtils.class.getName()).log(Level.SEVERE, "Unexpected method error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Change all of the given door states to be inverse; that is, if a door is
|
||||
* open, it will be closed afterwards. If the door is closed, it will become
|
||||
@ -197,8 +196,8 @@ public class BlockUtils {
|
||||
* Note that the blocks given must be the bottom block of the door.
|
||||
*
|
||||
* @param allowDoorToOpen If FALSE, and the door is currently CLOSED, it
|
||||
* will NOT be opened!
|
||||
* @param doors Blocks given must be the bottom block of the door
|
||||
* will NOT be opened!
|
||||
* @param doors Blocks given must be the bottom block of the door
|
||||
*/
|
||||
public static void toggleDoorStates(boolean allowDoorToOpen, Block... doors) {
|
||||
if (useLegacy && legacySetBlockData != null) {
|
||||
@ -312,6 +311,7 @@ public class BlockUtils {
|
||||
|
||||
/**
|
||||
* Manually trigger the updateAdjacentComparators method for containers
|
||||
*
|
||||
* @param containerLocation location of the container
|
||||
*/
|
||||
public static void updateAdjacentComparators(Location containerLocation) {
|
||||
@ -363,7 +363,8 @@ public class BlockUtils {
|
||||
if (mat == null || !mat.isCrop()) {
|
||||
return false;
|
||||
} else {
|
||||
return block.getData() >= (mat == CompatibleMaterial.BEETROOTS ? 3 : 7);
|
||||
return block.getData() >= (mat == CompatibleMaterial.BEETROOTS
|
||||
|| mat == CompatibleMaterial.NETHER_WART ? 3 : 7);
|
||||
}
|
||||
}
|
||||
|
||||
@ -383,7 +384,8 @@ public class BlockUtils {
|
||||
if (mat == null || !mat.isCrop()) {
|
||||
return -1;
|
||||
} else {
|
||||
return mat == CompatibleMaterial.BEETROOTS ? 3 : 7;
|
||||
return (mat == CompatibleMaterial.BEETROOTS
|
||||
|| mat == CompatibleMaterial.NETHER_WART ? 3 : 7);
|
||||
}
|
||||
}
|
||||
|
||||
@ -403,7 +405,8 @@ public class BlockUtils {
|
||||
if (mat == null || !mat.isCrop()) {
|
||||
return -1;
|
||||
} else {
|
||||
return mat == CompatibleMaterial.BEETROOTS ? 3 : 7;
|
||||
return (mat == CompatibleMaterial.BEETROOTS
|
||||
|| mat == CompatibleMaterial.NETHER_WART ? 3 : 7);
|
||||
}
|
||||
}
|
||||
|
||||
@ -421,7 +424,8 @@ public class BlockUtils {
|
||||
CompatibleMaterial mat = CompatibleMaterial.getBlockMaterial(block.getType());
|
||||
if (mat != null && mat.isCrop()) {
|
||||
try {
|
||||
legacySetBlockData.invoke(block, (byte) Math.max(0, Math.min(stage, mat == CompatibleMaterial.BEETROOTS ? 3 : 7)));
|
||||
legacySetBlockData.invoke(block, (byte) Math.max(0, Math.min(stage, (mat == CompatibleMaterial.BEETROOTS
|
||||
|| mat == CompatibleMaterial.NETHER_WART ? 3 : 7))));
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(BlockUtils.class.getName()).log(Level.SEVERE, "Unexpected method error", ex);
|
||||
}
|
||||
@ -440,7 +444,8 @@ public class BlockUtils {
|
||||
BlockUtilsModern._incrementGrowthStage(block);
|
||||
} else {
|
||||
CompatibleMaterial mat = CompatibleMaterial.getBlockMaterial(block.getType());
|
||||
if (mat != null && mat.isCrop() && block.getData() < (mat == CompatibleMaterial.BEETROOTS ? 3 : 7)) {
|
||||
if (mat != null && mat.isCrop() && block.getData() < (mat == CompatibleMaterial.BEETROOTS
|
||||
|| mat == CompatibleMaterial.NETHER_WART ? 3 : 7)) {
|
||||
try {
|
||||
legacySetBlockData.invoke(block, (byte) (block.getData() + 1));
|
||||
} catch (Exception ex) {
|
||||
@ -473,7 +478,7 @@ public class BlockUtils {
|
||||
|
||||
/**
|
||||
* Check to see if this material does not impede player/mob movement at all.
|
||||
*
|
||||
*
|
||||
* @param m material to check
|
||||
* @return true if this material doesn't have a solid hitbox
|
||||
*/
|
||||
@ -625,7 +630,7 @@ public class BlockUtils {
|
||||
case "WITHER_ROSE":
|
||||
case "YELLOW_BANNER":
|
||||
case "YELLOW_WALL_BANNER":
|
||||
// Legacy values:
|
||||
// Legacy values:
|
||||
case "WEB":
|
||||
case "LONG_GRASS":
|
||||
case "YELLOW_FLOWER":
|
||||
@ -658,7 +663,7 @@ public class BlockUtils {
|
||||
/**
|
||||
* Check to see if a player can walk into this material<br />
|
||||
* This includes blocks like slabs and stairs
|
||||
*
|
||||
*
|
||||
* @param m material to check
|
||||
* @return true if this is a block that can be walked though or up
|
||||
*/
|
||||
@ -936,7 +941,7 @@ public class BlockUtils {
|
||||
case "YELLOW_BANNER":
|
||||
case "YELLOW_CARPET":
|
||||
case "YELLOW_WALL_BANNER":
|
||||
// Legacy values:
|
||||
// Legacy values:
|
||||
case "WEB":
|
||||
case "LONG_GRASS":
|
||||
case "YELLOW_FLOWER":
|
||||
|
@ -46,8 +46,6 @@ public class ItemUtils {
|
||||
public static String getItemName(ItemStack it) {
|
||||
if (it == null) {
|
||||
return null;
|
||||
} else if (can_getI18NDisplayName) {
|
||||
return it.getI18NDisplayName();
|
||||
} else {
|
||||
return itemName(it.getType());
|
||||
}
|
||||
@ -257,6 +255,7 @@ public class ItemUtils {
|
||||
} else {
|
||||
meta.setOwner(player.getName());
|
||||
}
|
||||
head.setItemMeta(meta);
|
||||
return head;
|
||||
}
|
||||
|
||||
|
@ -1,22 +1,22 @@
|
||||
package com.songoda.core.nms.v1_14_R1;
|
||||
|
||||
import net.minecraft.server.v1_14_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_14_R1.IInventory;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_14_R1.inventory.CraftInventoryAnvil;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class AnvilInventoryCustom extends CraftInventoryAnvil {
|
||||
|
||||
final InventoryHolder holder;
|
||||
|
||||
public AnvilInventoryCustom(InventoryHolder holder, Location location, IInventory inventory, IInventory resultInventory, ContainerAnvil container) {
|
||||
super(location, inventory, resultInventory, container);
|
||||
this.holder = holder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public InventoryHolder getHolder() {
|
||||
return holder;
|
||||
}
|
||||
}
|
||||
package com.songoda.core.nms.v1_14_R1;
|
||||
|
||||
import net.minecraft.server.v1_14_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_14_R1.IInventory;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_14_R1.inventory.CraftInventoryAnvil;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class AnvilInventoryCustom extends CraftInventoryAnvil {
|
||||
|
||||
final InventoryHolder holder;
|
||||
|
||||
public AnvilInventoryCustom(InventoryHolder holder, Location location, IInventory inventory, IInventory resultInventory, ContainerAnvil container) {
|
||||
super(location, inventory, resultInventory, container);
|
||||
this.holder = holder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public InventoryHolder getHolder() {
|
||||
return holder;
|
||||
}
|
||||
}
|
||||
|
@ -1,261 +1,261 @@
|
||||
package com.songoda.core.nms.v1_14_R1;
|
||||
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import com.songoda.core.nms.methods.AnvilTextChange;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import net.minecraft.server.v1_14_R1.BlockPosition;
|
||||
import net.minecraft.server.v1_14_R1.ChatMessage;
|
||||
import net.minecraft.server.v1_14_R1.Container;
|
||||
import net.minecraft.server.v1_14_R1.ContainerAccess;
|
||||
import net.minecraft.server.v1_14_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_14_R1.ContainerProperty;
|
||||
import net.minecraft.server.v1_14_R1.Containers;
|
||||
import net.minecraft.server.v1_14_R1.EntityHuman;
|
||||
import net.minecraft.server.v1_14_R1.EntityPlayer;
|
||||
import net.minecraft.server.v1_14_R1.IInventory;
|
||||
import net.minecraft.server.v1_14_R1.PacketPlayOutOpenWindow;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_14_R1.inventory.CraftInventoryView;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
|
||||
public class AnvilView extends ContainerAnvil implements CustomAnvil {
|
||||
|
||||
private final EntityPlayer entity;
|
||||
private final Inventory inventory;
|
||||
private String customTitle = "Repairing";
|
||||
private int cost = -1;
|
||||
private boolean canUse = true;
|
||||
private AnvilTextChange textChange = null;
|
||||
|
||||
// used for setting custom inventory
|
||||
static Field mc_ContainerAnvil_repairInventory; // subcontainer with only the result
|
||||
static Field mc_ContainerAnvil_resultInventory; // full inventory
|
||||
static Field mc_ContainerAnvil_bukkitEntity;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_ContainerAnvil_repairInventory = ContainerAnvil.class.getDeclaredField("repairInventory");
|
||||
mc_ContainerAnvil_repairInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_resultInventory = ContainerAnvil.class.getDeclaredField("resultInventory");
|
||||
mc_ContainerAnvil_resultInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_bukkitEntity = ContainerAnvil.class.getDeclaredField("bukkitEntity");
|
||||
mc_ContainerAnvil_bukkitEntity.setAccessible(true);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
// 1.14.3 and 1.14.4 have different fields for levelCost
|
||||
static boolean compat_mode = true;
|
||||
static Method mc_ContainerProperty_set;
|
||||
static Method mc_ContainerProperty_get;
|
||||
// 1.14 also made this field private. Fun.
|
||||
static Field mc_Container_windowId;
|
||||
// 1.14 also introduced a title field, also private, which can only be set once and can't be checked
|
||||
static Field mc_Container_title;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_Container_windowId = Container.class.getDeclaredField("windowId");
|
||||
mc_Container_windowId.setAccessible(true);
|
||||
mc_Container_title = Container.class.getDeclaredField("title");
|
||||
mc_Container_title.setAccessible(true);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
for (Method m : ContainerProperty.class.getMethods()) {
|
||||
if (m.getName().equals("set")) {
|
||||
compat_mode = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (compat_mode) {
|
||||
try {
|
||||
mc_ContainerProperty_set = ContainerProperty.class.getDeclaredMethod("a", int.class);
|
||||
mc_ContainerProperty_get = ContainerProperty.class.getDeclaredMethod("b");
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public AnvilView(int id, EntityPlayer entity, InventoryHolder holder) {
|
||||
super(id, entity.inventory, ContainerAccess.at(entity.world, new BlockPosition(0, 0, 0)));
|
||||
this.setTitle(new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
this.checkReachable = false;
|
||||
this.entity = entity;
|
||||
if(holder != null) {
|
||||
this.inventory = getBukkitView(entity, holder).getTopInventory();
|
||||
} else {
|
||||
this.inventory = getBukkitView().getTopInventory();
|
||||
}
|
||||
}
|
||||
|
||||
public CraftInventoryView getBukkitView(EntityHuman player, InventoryHolder holder) {
|
||||
try {
|
||||
AnvilInventoryCustom craftInventory = new AnvilInventoryCustom(holder,
|
||||
new Location(entity.world.getWorld(), 0, 0, 0),
|
||||
(IInventory) mc_ContainerAnvil_repairInventory.get(this),
|
||||
(IInventory) mc_ContainerAnvil_resultInventory.get(this), this);
|
||||
CraftInventoryView view = new CraftInventoryView(player.getBukkitEntity(), craftInventory, this);
|
||||
mc_ContainerAnvil_bukkitEntity.set(this, view);
|
||||
return view;
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
return getBukkitView();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canUse(EntityHuman entityhuman) {
|
||||
return canUse;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void e() {
|
||||
super.e();
|
||||
if (cost >= 0) {
|
||||
if (compat_mode) {
|
||||
if (mc_ContainerProperty_set != null) {
|
||||
try {
|
||||
mc_ContainerProperty_set.invoke(this.levelCost, 0);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
mc_ContainerProperty_set = null;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
this.levelCost.set(cost);
|
||||
}
|
||||
}
|
||||
textChange.onChange();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update() {
|
||||
e();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getRenameText() {
|
||||
return this.renameText;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRenameText(String text) {
|
||||
this.a(text);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOnChange(AnvilTextChange handler) {
|
||||
textChange = handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getCustomTitle() {
|
||||
return customTitle;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCustomTitle(String title) {
|
||||
this.customTitle = title;
|
||||
try {
|
||||
mc_Container_title.set(this, new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLevelCost(int cost) {
|
||||
this.cost = cost;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLevelCost() {
|
||||
if (cost >= 0) {
|
||||
return cost;
|
||||
} else if (compat_mode) {
|
||||
if (mc_ContainerProperty_get != null) {
|
||||
try {
|
||||
return (int) mc_ContainerProperty_get.invoke(this.levelCost);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
mc_ContainerProperty_get = null;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
return this.levelCost.get();
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCanUse(boolean bool) {
|
||||
this.canUse = bool;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getLeftInput() {
|
||||
return inventory.getItem(0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getRightInput() {
|
||||
return inventory.getItem(1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getOutput() {
|
||||
return inventory.getItem(2);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLeftInput(ItemStack item) {
|
||||
inventory.setItem(0, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRightInput(ItemStack item) {
|
||||
inventory.setItem(1, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOutput(ItemStack item) {
|
||||
inventory.setItem(2, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Inventory getInventory() {
|
||||
return inventory;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void open() {
|
||||
|
||||
// Counter stuff that the game uses to keep track of inventories
|
||||
int id = entity.nextContainerCounter();
|
||||
|
||||
// Send the packet
|
||||
entity.playerConnection.sendPacket(new PacketPlayOutOpenWindow(id, Containers.ANVIL, new ChatMessage(customTitle != null ? customTitle : "")));
|
||||
|
||||
// Set their active container to this anvil
|
||||
entity.activeContainer = this;
|
||||
|
||||
try {
|
||||
// Set their active container window id to that counter stuff
|
||||
mc_Container_windowId.set(this, id);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Create Error", ex);
|
||||
}
|
||||
|
||||
// Add the slot listener
|
||||
entity.activeContainer.addSlotListener(entity);
|
||||
}
|
||||
|
||||
}
|
||||
package com.songoda.core.nms.v1_14_R1;
|
||||
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import com.songoda.core.nms.methods.AnvilTextChange;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import net.minecraft.server.v1_14_R1.BlockPosition;
|
||||
import net.minecraft.server.v1_14_R1.ChatMessage;
|
||||
import net.minecraft.server.v1_14_R1.Container;
|
||||
import net.minecraft.server.v1_14_R1.ContainerAccess;
|
||||
import net.minecraft.server.v1_14_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_14_R1.ContainerProperty;
|
||||
import net.minecraft.server.v1_14_R1.Containers;
|
||||
import net.minecraft.server.v1_14_R1.EntityHuman;
|
||||
import net.minecraft.server.v1_14_R1.EntityPlayer;
|
||||
import net.minecraft.server.v1_14_R1.IInventory;
|
||||
import net.minecraft.server.v1_14_R1.PacketPlayOutOpenWindow;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_14_R1.inventory.CraftInventoryView;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
|
||||
public class AnvilView extends ContainerAnvil implements CustomAnvil {
|
||||
|
||||
private final EntityPlayer entity;
|
||||
private final Inventory inventory;
|
||||
private String customTitle = "Repairing";
|
||||
private int cost = -1;
|
||||
private boolean canUse = true;
|
||||
private AnvilTextChange textChange = null;
|
||||
|
||||
// used for setting custom inventory
|
||||
static Field mc_ContainerAnvil_repairInventory; // subcontainer with only the result
|
||||
static Field mc_ContainerAnvil_resultInventory; // full inventory
|
||||
static Field mc_ContainerAnvil_bukkitEntity;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_ContainerAnvil_repairInventory = ContainerAnvil.class.getDeclaredField("repairInventory");
|
||||
mc_ContainerAnvil_repairInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_resultInventory = ContainerAnvil.class.getDeclaredField("resultInventory");
|
||||
mc_ContainerAnvil_resultInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_bukkitEntity = ContainerAnvil.class.getDeclaredField("bukkitEntity");
|
||||
mc_ContainerAnvil_bukkitEntity.setAccessible(true);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
// 1.14.3 and 1.14.4 have different fields for levelCost
|
||||
static boolean compat_mode = true;
|
||||
static Method mc_ContainerProperty_set;
|
||||
static Method mc_ContainerProperty_get;
|
||||
// 1.14 also made this field private. Fun.
|
||||
static Field mc_Container_windowId;
|
||||
// 1.14 also introduced a title field, also private, which can only be set once and can't be checked
|
||||
static Field mc_Container_title;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_Container_windowId = Container.class.getDeclaredField("windowId");
|
||||
mc_Container_windowId.setAccessible(true);
|
||||
mc_Container_title = Container.class.getDeclaredField("title");
|
||||
mc_Container_title.setAccessible(true);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
for (Method m : ContainerProperty.class.getMethods()) {
|
||||
if (m.getName().equals("set")) {
|
||||
compat_mode = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (compat_mode) {
|
||||
try {
|
||||
mc_ContainerProperty_set = ContainerProperty.class.getDeclaredMethod("a", int.class);
|
||||
mc_ContainerProperty_get = ContainerProperty.class.getDeclaredMethod("b");
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public AnvilView(int id, EntityPlayer entity, InventoryHolder holder) {
|
||||
super(id, entity.inventory, ContainerAccess.at(entity.world, new BlockPosition(0, 0, 0)));
|
||||
this.setTitle(new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
this.checkReachable = false;
|
||||
this.entity = entity;
|
||||
if(holder != null) {
|
||||
this.inventory = getBukkitView(entity, holder).getTopInventory();
|
||||
} else {
|
||||
this.inventory = getBukkitView().getTopInventory();
|
||||
}
|
||||
}
|
||||
|
||||
public CraftInventoryView getBukkitView(EntityHuman player, InventoryHolder holder) {
|
||||
try {
|
||||
AnvilInventoryCustom craftInventory = new AnvilInventoryCustom(holder,
|
||||
new Location(entity.world.getWorld(), 0, 0, 0),
|
||||
(IInventory) mc_ContainerAnvil_repairInventory.get(this),
|
||||
(IInventory) mc_ContainerAnvil_resultInventory.get(this), this);
|
||||
CraftInventoryView view = new CraftInventoryView(player.getBukkitEntity(), craftInventory, this);
|
||||
mc_ContainerAnvil_bukkitEntity.set(this, view);
|
||||
return view;
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
return getBukkitView();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canUse(EntityHuman entityhuman) {
|
||||
return canUse;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void e() {
|
||||
super.e();
|
||||
if (cost >= 0) {
|
||||
if (compat_mode) {
|
||||
if (mc_ContainerProperty_set != null) {
|
||||
try {
|
||||
mc_ContainerProperty_set.invoke(this.levelCost, 0);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
mc_ContainerProperty_set = null;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
this.levelCost.set(cost);
|
||||
}
|
||||
}
|
||||
textChange.onChange();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update() {
|
||||
e();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getRenameText() {
|
||||
return this.renameText;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRenameText(String text) {
|
||||
this.a(text);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOnChange(AnvilTextChange handler) {
|
||||
textChange = handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getCustomTitle() {
|
||||
return customTitle;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCustomTitle(String title) {
|
||||
this.customTitle = title;
|
||||
try {
|
||||
mc_Container_title.set(this, new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLevelCost(int cost) {
|
||||
this.cost = cost;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLevelCost() {
|
||||
if (cost >= 0) {
|
||||
return cost;
|
||||
} else if (compat_mode) {
|
||||
if (mc_ContainerProperty_get != null) {
|
||||
try {
|
||||
return (int) mc_ContainerProperty_get.invoke(this.levelCost);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
mc_ContainerProperty_get = null;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
return this.levelCost.get();
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCanUse(boolean bool) {
|
||||
this.canUse = bool;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getLeftInput() {
|
||||
return inventory.getItem(0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getRightInput() {
|
||||
return inventory.getItem(1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getOutput() {
|
||||
return inventory.getItem(2);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLeftInput(ItemStack item) {
|
||||
inventory.setItem(0, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRightInput(ItemStack item) {
|
||||
inventory.setItem(1, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOutput(ItemStack item) {
|
||||
inventory.setItem(2, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Inventory getInventory() {
|
||||
return inventory;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void open() {
|
||||
|
||||
// Counter stuff that the game uses to keep track of inventories
|
||||
int id = entity.nextContainerCounter();
|
||||
|
||||
// Send the packet
|
||||
entity.playerConnection.sendPacket(new PacketPlayOutOpenWindow(id, Containers.ANVIL, new ChatMessage(customTitle != null ? customTitle : "")));
|
||||
|
||||
// Set their active container to this anvil
|
||||
entity.activeContainer = this;
|
||||
|
||||
try {
|
||||
// Set their active container window id to that counter stuff
|
||||
mc_Container_windowId.set(this, id);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Create Error", ex);
|
||||
}
|
||||
|
||||
// Add the slot listener
|
||||
entity.activeContainer.addSlotListener(entity);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,24 +1,24 @@
|
||||
package com.songoda.core.nms.v1_14_R1;
|
||||
|
||||
import com.songoda.core.nms.CoreNMS;
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import net.minecraft.server.v1_14_R1.EntityPlayer;
|
||||
import org.bukkit.craftbukkit.v1_14_R1.entity.CraftPlayer;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class NMS implements CoreNMS {
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player, InventoryHolder holder) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, holder);
|
||||
}
|
||||
|
||||
}
|
||||
package com.songoda.core.nms.v1_14_R1;
|
||||
|
||||
import com.songoda.core.nms.CoreNMS;
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import net.minecraft.server.v1_14_R1.EntityPlayer;
|
||||
import org.bukkit.craftbukkit.v1_14_R1.entity.CraftPlayer;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class NMS implements CoreNMS {
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player, InventoryHolder holder) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, holder);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,22 +1,22 @@
|
||||
package com.songoda.core.nms.v1_15_R1;
|
||||
|
||||
import net.minecraft.server.v1_15_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_15_R1.IInventory;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_15_R1.inventory.CraftInventoryAnvil;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class AnvilInventoryCustom extends CraftInventoryAnvil {
|
||||
|
||||
final InventoryHolder holder;
|
||||
|
||||
public AnvilInventoryCustom(InventoryHolder holder, Location location, IInventory inventory, IInventory resultInventory, ContainerAnvil container) {
|
||||
super(location, inventory, resultInventory, container);
|
||||
this.holder = holder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public InventoryHolder getHolder() {
|
||||
return holder;
|
||||
}
|
||||
}
|
||||
package com.songoda.core.nms.v1_15_R1;
|
||||
|
||||
import net.minecraft.server.v1_15_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_15_R1.IInventory;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_15_R1.inventory.CraftInventoryAnvil;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class AnvilInventoryCustom extends CraftInventoryAnvil {
|
||||
|
||||
final InventoryHolder holder;
|
||||
|
||||
public AnvilInventoryCustom(InventoryHolder holder, Location location, IInventory inventory, IInventory resultInventory, ContainerAnvil container) {
|
||||
super(location, inventory, resultInventory, container);
|
||||
this.holder = holder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public InventoryHolder getHolder() {
|
||||
return holder;
|
||||
}
|
||||
}
|
||||
|
@ -1,229 +1,229 @@
|
||||
package com.songoda.core.nms.v1_15_R1;
|
||||
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import com.songoda.core.nms.methods.AnvilTextChange;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import net.minecraft.server.v1_15_R1.BlockPosition;
|
||||
import net.minecraft.server.v1_15_R1.ChatMessage;
|
||||
import net.minecraft.server.v1_15_R1.Container;
|
||||
import net.minecraft.server.v1_15_R1.ContainerAccess;
|
||||
import net.minecraft.server.v1_15_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_15_R1.Containers;
|
||||
import net.minecraft.server.v1_15_R1.EntityHuman;
|
||||
import net.minecraft.server.v1_15_R1.EntityPlayer;
|
||||
import net.minecraft.server.v1_15_R1.IInventory;
|
||||
import net.minecraft.server.v1_15_R1.PacketPlayOutOpenWindow;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_15_R1.inventory.CraftInventoryView;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
|
||||
public class AnvilView extends ContainerAnvil implements CustomAnvil {
|
||||
|
||||
private final EntityPlayer entity;
|
||||
private final Inventory inventory;
|
||||
private String customTitle = "Repairing";
|
||||
private int cost = -1;
|
||||
private boolean canUse = true;
|
||||
private AnvilTextChange textChange = null;
|
||||
|
||||
// used for setting custom inventory
|
||||
static Field mc_ContainerAnvil_repairInventory; // subcontainer with only the result
|
||||
static Field mc_ContainerAnvil_resultInventory; // full inventory
|
||||
static Field mc_ContainerAnvil_bukkitEntity;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_ContainerAnvil_repairInventory = ContainerAnvil.class.getDeclaredField("repairInventory");
|
||||
mc_ContainerAnvil_repairInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_resultInventory = ContainerAnvil.class.getDeclaredField("resultInventory");
|
||||
mc_ContainerAnvil_resultInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_bukkitEntity = ContainerAnvil.class.getDeclaredField("bukkitEntity");
|
||||
mc_ContainerAnvil_bukkitEntity.setAccessible(true);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
static Method mc_ContainerProperty_set;
|
||||
static Method mc_ContainerProperty_get;
|
||||
// 1.15 made this field public again, but now it's final. idk.
|
||||
static Field mc_Container_windowId;
|
||||
// 1.14 also introduced a title field, also private, which can only be set once and can't be checked
|
||||
static Field mc_Container_title;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_Container_title = Container.class.getDeclaredField("title");
|
||||
mc_Container_title.setAccessible(true);
|
||||
mc_Container_windowId = Container.class.getDeclaredField("windowId");
|
||||
mc_Container_windowId.setAccessible(true);
|
||||
|
||||
// remove the final modifier
|
||||
Field modifiersField = Field.class.getDeclaredField("modifiers");
|
||||
modifiersField.setAccessible(true);
|
||||
modifiersField.setInt(mc_Container_windowId, mc_Container_windowId.getModifiers() & ~Modifier.FINAL);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
public AnvilView(int id, EntityPlayer entity, InventoryHolder holder) {
|
||||
super(id, entity.inventory, ContainerAccess.at(entity.world, new BlockPosition(0, 0, 0)));
|
||||
this.setTitle(new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
this.checkReachable = false;
|
||||
this.entity = entity;
|
||||
if(holder != null) {
|
||||
this.inventory = getBukkitView(entity, holder).getTopInventory();
|
||||
} else {
|
||||
this.inventory = getBukkitView().getTopInventory();
|
||||
}
|
||||
}
|
||||
|
||||
public CraftInventoryView getBukkitView(EntityHuman player, InventoryHolder holder) {
|
||||
try {
|
||||
AnvilInventoryCustom craftInventory = new AnvilInventoryCustom(holder,
|
||||
new Location(entity.world.getWorld(), 0, 0, 0),
|
||||
(IInventory) mc_ContainerAnvil_repairInventory.get(this),
|
||||
(IInventory) mc_ContainerAnvil_resultInventory.get(this), this);
|
||||
CraftInventoryView view = new CraftInventoryView(player.getBukkitEntity(), craftInventory, this);
|
||||
mc_ContainerAnvil_bukkitEntity.set(this, view);
|
||||
return view;
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
return getBukkitView();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canUse(EntityHuman entityhuman) {
|
||||
return canUse;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void e() {
|
||||
super.e();
|
||||
if (cost >= 0) {
|
||||
this.levelCost.set(cost);
|
||||
}
|
||||
textChange.onChange();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update() {
|
||||
e();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getRenameText() {
|
||||
return this.renameText;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRenameText(String text) {
|
||||
this.a(text);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOnChange(AnvilTextChange handler) {
|
||||
textChange = handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getCustomTitle() {
|
||||
return customTitle;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCustomTitle(String title) {
|
||||
this.customTitle = title;
|
||||
try {
|
||||
mc_Container_title.set(this, new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLevelCost(int cost) {
|
||||
this.cost = cost;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLevelCost() {
|
||||
if (cost >= 0) {
|
||||
return cost;
|
||||
} else {
|
||||
return this.levelCost.get();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCanUse(boolean bool) {
|
||||
this.canUse = bool;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getLeftInput() {
|
||||
return inventory.getItem(0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getRightInput() {
|
||||
return inventory.getItem(1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getOutput() {
|
||||
return inventory.getItem(2);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLeftInput(ItemStack item) {
|
||||
inventory.setItem(0, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRightInput(ItemStack item) {
|
||||
inventory.setItem(1, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOutput(ItemStack item) {
|
||||
inventory.setItem(2, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Inventory getInventory() {
|
||||
return inventory;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void open() {
|
||||
|
||||
// Counter stuff that the game uses to keep track of inventories
|
||||
int id = entity.nextContainerCounter();
|
||||
|
||||
// Send the packet
|
||||
entity.playerConnection.sendPacket(new PacketPlayOutOpenWindow(id, Containers.ANVIL, new ChatMessage(customTitle != null ? customTitle : "")));
|
||||
|
||||
// Set their active container to this anvil
|
||||
entity.activeContainer = this;
|
||||
|
||||
try {
|
||||
// Set their active container window id to that counter stuff
|
||||
mc_Container_windowId.set(this, id);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Create Error", ex);
|
||||
}
|
||||
|
||||
// Add the slot listener
|
||||
entity.activeContainer.addSlotListener(entity);
|
||||
}
|
||||
|
||||
}
|
||||
package com.songoda.core.nms.v1_15_R1;
|
||||
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import com.songoda.core.nms.methods.AnvilTextChange;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
import net.minecraft.server.v1_15_R1.BlockPosition;
|
||||
import net.minecraft.server.v1_15_R1.ChatMessage;
|
||||
import net.minecraft.server.v1_15_R1.Container;
|
||||
import net.minecraft.server.v1_15_R1.ContainerAccess;
|
||||
import net.minecraft.server.v1_15_R1.ContainerAnvil;
|
||||
import net.minecraft.server.v1_15_R1.Containers;
|
||||
import net.minecraft.server.v1_15_R1.EntityHuman;
|
||||
import net.minecraft.server.v1_15_R1.EntityPlayer;
|
||||
import net.minecraft.server.v1_15_R1.IInventory;
|
||||
import net.minecraft.server.v1_15_R1.PacketPlayOutOpenWindow;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_15_R1.inventory.CraftInventoryView;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
|
||||
public class AnvilView extends ContainerAnvil implements CustomAnvil {
|
||||
|
||||
private final EntityPlayer entity;
|
||||
private final Inventory inventory;
|
||||
private String customTitle = "Repairing";
|
||||
private int cost = -1;
|
||||
private boolean canUse = true;
|
||||
private AnvilTextChange textChange = null;
|
||||
|
||||
// used for setting custom inventory
|
||||
static Field mc_ContainerAnvil_repairInventory; // subcontainer with only the result
|
||||
static Field mc_ContainerAnvil_resultInventory; // full inventory
|
||||
static Field mc_ContainerAnvil_bukkitEntity;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_ContainerAnvil_repairInventory = ContainerAnvil.class.getDeclaredField("repairInventory");
|
||||
mc_ContainerAnvil_repairInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_resultInventory = ContainerAnvil.class.getDeclaredField("resultInventory");
|
||||
mc_ContainerAnvil_resultInventory.setAccessible(true);
|
||||
mc_ContainerAnvil_bukkitEntity = ContainerAnvil.class.getDeclaredField("bukkitEntity");
|
||||
mc_ContainerAnvil_bukkitEntity.setAccessible(true);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
static Method mc_ContainerProperty_set;
|
||||
static Method mc_ContainerProperty_get;
|
||||
// 1.15 made this field public again, but now it's final. idk.
|
||||
static Field mc_Container_windowId;
|
||||
// 1.14 also introduced a title field, also private, which can only be set once and can't be checked
|
||||
static Field mc_Container_title;
|
||||
|
||||
static {
|
||||
try {
|
||||
mc_Container_title = Container.class.getDeclaredField("title");
|
||||
mc_Container_title.setAccessible(true);
|
||||
mc_Container_windowId = Container.class.getDeclaredField("windowId");
|
||||
mc_Container_windowId.setAccessible(true);
|
||||
|
||||
// remove the final modifier
|
||||
Field modifiersField = Field.class.getDeclaredField("modifiers");
|
||||
modifiersField.setAccessible(true);
|
||||
modifiersField.setInt(mc_Container_windowId, mc_Container_windowId.getModifiers() & ~Modifier.FINAL);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
public AnvilView(int id, EntityPlayer entity, InventoryHolder holder) {
|
||||
super(id, entity.inventory, ContainerAccess.at(entity.world, new BlockPosition(0, 0, 0)));
|
||||
this.setTitle(new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
this.checkReachable = false;
|
||||
this.entity = entity;
|
||||
if(holder != null) {
|
||||
this.inventory = getBukkitView(entity, holder).getTopInventory();
|
||||
} else {
|
||||
this.inventory = getBukkitView().getTopInventory();
|
||||
}
|
||||
}
|
||||
|
||||
public CraftInventoryView getBukkitView(EntityHuman player, InventoryHolder holder) {
|
||||
try {
|
||||
AnvilInventoryCustom craftInventory = new AnvilInventoryCustom(holder,
|
||||
new Location(entity.world.getWorld(), 0, 0, 0),
|
||||
(IInventory) mc_ContainerAnvil_repairInventory.get(this),
|
||||
(IInventory) mc_ContainerAnvil_resultInventory.get(this), this);
|
||||
CraftInventoryView view = new CraftInventoryView(player.getBukkitEntity(), craftInventory, this);
|
||||
mc_ContainerAnvil_bukkitEntity.set(this, view);
|
||||
return view;
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Setup Error", ex);
|
||||
}
|
||||
return getBukkitView();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canUse(EntityHuman entityhuman) {
|
||||
return canUse;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void e() {
|
||||
super.e();
|
||||
if (cost >= 0) {
|
||||
this.levelCost.set(cost);
|
||||
}
|
||||
textChange.onChange();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update() {
|
||||
e();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getRenameText() {
|
||||
return this.renameText;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRenameText(String text) {
|
||||
this.a(text);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOnChange(AnvilTextChange handler) {
|
||||
textChange = handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getCustomTitle() {
|
||||
return customTitle;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCustomTitle(String title) {
|
||||
this.customTitle = title;
|
||||
try {
|
||||
mc_Container_title.set(this, new ChatMessage(customTitle != null ? customTitle : ""));
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Error", ex);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLevelCost(int cost) {
|
||||
this.cost = cost;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLevelCost() {
|
||||
if (cost >= 0) {
|
||||
return cost;
|
||||
} else {
|
||||
return this.levelCost.get();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCanUse(boolean bool) {
|
||||
this.canUse = bool;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getLeftInput() {
|
||||
return inventory.getItem(0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getRightInput() {
|
||||
return inventory.getItem(1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ItemStack getOutput() {
|
||||
return inventory.getItem(2);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setLeftInput(ItemStack item) {
|
||||
inventory.setItem(0, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setRightInput(ItemStack item) {
|
||||
inventory.setItem(1, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOutput(ItemStack item) {
|
||||
inventory.setItem(2, item);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Inventory getInventory() {
|
||||
return inventory;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void open() {
|
||||
|
||||
// Counter stuff that the game uses to keep track of inventories
|
||||
int id = entity.nextContainerCounter();
|
||||
|
||||
// Send the packet
|
||||
entity.playerConnection.sendPacket(new PacketPlayOutOpenWindow(id, Containers.ANVIL, new ChatMessage(customTitle != null ? customTitle : "")));
|
||||
|
||||
// Set their active container to this anvil
|
||||
entity.activeContainer = this;
|
||||
|
||||
try {
|
||||
// Set their active container window id to that counter stuff
|
||||
mc_Container_windowId.set(this, id);
|
||||
} catch (Exception ex) {
|
||||
Logger.getLogger(AnvilView.class.getName()).log(Level.SEVERE, "Anvil Create Error", ex);
|
||||
}
|
||||
|
||||
// Add the slot listener
|
||||
entity.activeContainer.addSlotListener(entity);
|
||||
}
|
||||
|
||||
}
|
@ -1,24 +1,24 @@
|
||||
package com.songoda.core.nms.v1_15_R1;
|
||||
|
||||
import com.songoda.core.nms.CoreNMS;
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import net.minecraft.server.v1_15_R1.EntityPlayer;
|
||||
import org.bukkit.craftbukkit.v1_15_R1.entity.CraftPlayer;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class NMS implements CoreNMS {
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player, InventoryHolder holder) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, holder);
|
||||
}
|
||||
|
||||
}
|
||||
package com.songoda.core.nms.v1_15_R1;
|
||||
|
||||
import com.songoda.core.nms.CoreNMS;
|
||||
import com.songoda.core.nms.CustomAnvil;
|
||||
import net.minecraft.server.v1_15_R1.EntityPlayer;
|
||||
import org.bukkit.craftbukkit.v1_15_R1.entity.CraftPlayer;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.InventoryHolder;
|
||||
|
||||
public class NMS implements CoreNMS {
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CustomAnvil createAnvil(Player player, InventoryHolder holder) {
|
||||
EntityPlayer p = ((CraftPlayer) player).getHandle();
|
||||
return new AnvilView(p.nextContainerCounter(), p, holder);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,44 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<module org.jetbrains.idea.maven.project.MavenProjectsManager.isMavenModule="true" type="JAVA_MODULE" version="4">
|
||||
<component name="NewModuleRootManager" LANGUAGE_LEVEL="JDK_1_8">
|
||||
<output url="file://$MODULE_DIR$/target/classes" />
|
||||
<output-test url="file://$MODULE_DIR$/target/test-classes" />
|
||||
<content url="file://$MODULE_DIR$">
|
||||
<sourceFolder url="file://$MODULE_DIR$/src/main/java" isTestSource="false" />
|
||||
<excludeFolder url="file://$MODULE_DIR$/target" />
|
||||
</content>
|
||||
<orderEntry type="inheritedJdk" />
|
||||
<orderEntry type="sourceFolder" forTests="false" />
|
||||
<orderEntry type="library" name="Maven: org.spigotmc:spigot:1.14.4" level="project" />
|
||||
<orderEntry type="library" name="Maven: com.gmail.filoghost.holographicdisplays:holographicdisplays-api:2.3.2" level="project" />
|
||||
<orderEntry type="library" name="Maven: com.sainttx.holograms:Holograms:2.9.1" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: net.tnemc:Reserve:0.1.3.0" level="project" />
|
||||
<orderEntry type="library" name="Maven: org.black_ixx:playerpoints:2.1.4" level="project" />
|
||||
<orderEntry type="library" name="Maven: net.milkbowl:vault:1.7.1" level="project" />
|
||||
<orderEntry type="library" name="Maven: org.slf4j:slf4j-api:1.7.25" level="project" />
|
||||
<orderEntry type="library" name="Maven: org.slf4j:slf4j-nop:1.7.25" level="project" />
|
||||
<orderEntry type="library" name="Maven: com.zaxxer:HikariCP:3.2.0" level="project" />
|
||||
<orderEntry type="library" name="Maven: org.xerial:sqlite-jdbc:3.23.1" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q.worldguard:worldguard-bukkit:7.0.1-SNAPSHOT" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: org.bukkit:bukkit:1.14.4-R0.1-SNAPSHOT" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: commons-lang:commons-lang:2.6" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.google.guava:guava:21.0" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.google.code.gson:gson:2.8.0" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: org.yaml:snakeyaml:1.23" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q.worldedit:worldedit-bukkit:7.0.1-SNAPSHOT" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q.worldguard:worldguard-core:7.0.1-SNAPSHOT" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q.worldguard.worldguard-libs:core:7.0.1-SNAPSHOT" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q.worldedit:worldedit-core:7.0.1-SNAPSHOT" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q.worldedit.worldedit-libs:core:7.0.1-SNAPSHOT" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: de.schlichtherle:truezip:6.8.3" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: org.mozilla:rhino:1.7.11" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.google.code.findbugs:jsr305:1.3.9" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: org.flywaydb:flyway-core:3.0" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: io.papermc:paperlib:1.0.2" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: com.sk89q:commandbook:2.3" level="project" />
|
||||
<orderEntry type="library" scope="PROVIDED" name="Maven: org.bstats:bstats-bukkit:1.5" level="project" />
|
||||
<orderEntry type="library" name="Maven: com.songoda:UltimateStacker:1.2.8" level="project" />
|
||||
<orderEntry type="library" name="Maven: com.bgsoftware:WildStacker:2-9-0" level="project" />
|
||||
<orderEntry type="library" name="Maven: uk.antiperson:stackmob:4-0-2" level="project" />
|
||||
</component>
|
||||
</module>
|
Loading…
Reference in New Issue
Block a user