diff --git a/.github/workflows/discord-webhook.yml b/.github/workflows/discord-webhook.yml
index f6c11887b..a4845bb6f 100644
--- a/.github/workflows/discord-webhook.yml
+++ b/.github/workflows/discord-webhook.yml
@@ -4,6 +4,7 @@ on:
push:
paths:
- 'src/**'
+ - '!src/main/resources/languages/**'
- 'pom.xml'
jobs:
@@ -15,11 +16,13 @@ jobs:
steps:
- name: Checkout repository
- uses: actions/checkout@v1
- - name: Set up JDK 1.8
- uses: actions/setup-java@master
+ uses: actions/checkout@v2.3.3
+ - name: Set up Java JDK 11
+ uses: actions/setup-java@v1.4.3
with:
- java-version: 1.8
+ java-version: '11'
+ java-package: jdk
+ architecture: x64
- name: Run Discord Webhook
uses: Slimefun/discord-webhook@master
with:
diff --git a/.github/workflows/url-checker.yml b/.github/workflows/url-checker.yml
index e0e150008..523248f00 100644
--- a/.github/workflows/url-checker.yml
+++ b/.github/workflows/url-checker.yml
@@ -4,9 +4,6 @@ on:
push:
branches:
- master
- pull_request:
- branches:
- - master
jobs:
build:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index d06dc74d9..e3f22799e 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -2,7 +2,8 @@
**Table of contents**
-- [Release Candidate 17 (TBD)](#release-candidate-17-tbd)
+- [Release Candidate 18 (TBD)](#release-candidate-18-tbd)
+- [Release Candidate 17 (17 Oct 2020)](#release-candidate-17-17-oct-2020)
- [Release Candidate 16 (07 Sep 2020)](#release-candidate-16-07-sep-2020)
- [Release Candidate 15 (01 Aug 2020)](#release-candidate-15-01-aug-2020)
- [Release Candidate 14 (12 Jul 2020)](#release-candidate-14-12-jul-2020)
@@ -22,7 +23,16 @@
-## Release Candidate 17 (TBD)
+## Release Candidate 18 (TBD)
+
+#### Additions
+
+#### Changes
+* Removed 1.13 support
+
+#### Fixes
+
+## Release Candidate 17 (17 Oct 2020)
#### Additions
* Added /sf charge
@@ -36,11 +46,20 @@
* (API) Added "NotConfigurable" attribute to disable configurability
* Added Elytra Cap
* Added Planks to Sticks recipe to the Table Saw
+* Added "slimefun.gps.bypass" permission to open GPS devices anywhere
+* (API) Added custom tags for developers
+* The range of the Seeker Pickaxe is now configurable
+* Added Energy Connector
+* Blackstone can now be turned into lava using a Crucible
+* Basalt can now be turned into lava using a Crucible
+* Added "Tainted Sheep" (You can dye a Sheep using Strange Nether Goo)
+* Added mcMMO support/integration
#### Changes
* Improved Auto-Updater (Multi-Threading and more)
* General performance improvements
* /sf cheat now shows seasonal categories all year through
+* GPS devices now require chest-access in that area to be used
#### Fixes
* Fixed #2300
@@ -66,6 +85,24 @@
* Fixed #2391
* Fixed #2403
* Fixed #2405
+* Fixed #2412
+* Fixed #2238
+* Fixed #2439
+* Fixed #2420
+* Fixed #2422
+* Fixed #2433
+* Fixed #2455
+* Fixed #2450
+* Fixed Steel Thrusters being used to milk cows
+* Fixed #2424
+* Fixed #2468
+* Fixed #2414
+* Fixed #2454
+* Fixed #2457
+* Fixed #2411
+* Fixed #2423
+* Fixed #2452
+* Fixed a dupe bug with mcMMO
## Release Candidate 16 (07 Sep 2020)
https://thebusybiscuit.github.io/builds/TheBusyBiscuit/Slimefun4/stable/#16
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index e9d1e9120..d80ac5dc6 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -94,3 +94,93 @@ Then you should be able build it via Maven using the goals `clean package`.
If you have any further questions, then please join our [Discord Support Server](https://discord.gg/slimefun) and ask your questions in the `#programming-help` channel.
**Note that we will not accept any bug reports from custom-compiled versions of Slimefun**.
+
+## :black_nib: Code Style guidelines
+The general gist when it comes to code style: **Try to be consistent!**.
+Try to stay inline with the code that surrounds you, having an entire package or even a single file that's filled with plenty of different and inconsistent code styles is just hard to read or maintain. That's why we wanna make sure everyone follows these principles.
+
+*Note that these are just guidelines, we may request changes on your pull request if we think there are changes necessary.
+But we won't reject your Pull Request completely due to a few styling inconsistencies, we can always refactor code later.
+But do try to follow our code style as best as you can.*
+
+#### 1. Imports
+* Don't use wildcard (`*`) imports!
+* Don't import unused classes!
+* Don't use static imports!
+* Always use imports, even in javadocs, don't write out the full location of a class.
+#### 2. Annotations
+* Methods and parameters should be annotated with `@Nullable` (`javax.annotation.Nullable`) or `@Nonnull`(`javax.annotation.Nonnull`)!
+* Methods that override a method must be annotated with `@Override`!
+* Interfaces with only one method should be annotated using `@FunctionalInterface`!
+* If you deprecate a method, add an `@deprecated` section to the javadocs explaining why you did it.
+#### 3. Documentation
+* Every class and every public method should have a Javadocs section assigned to it.
+* New packages should have a `package-info.java` file with documentation about the package.
+* Classes should have an `@author` tag.
+* If there are any other relevant classes related to yours, add them using the `@see` tag.
+#### 4. Unit Tests
+* Try to write Unit Tests where possible.
+* Unit Test classes and methods should have no access modifier, not `public`, `protected` nor `private`.
+* Each Test should have a plain text `@DisplayName` annotation!
+#### 5. General best-practices
+* Do not use `Collection#forEach(x -> ...)`, use a proper `for (...)` loop!
+* Do not create new `Random` objects, use `ThreadLocalRandom.current()` instead!
+* Always declare Maps or Collections using their base type! (e.g. `List list = new ArrayList<>();`)
+* When doing String operations like `String#toUppercase()`, always specify `Locale.ROOT` as an argument!
+* When reading or writing files, always specify the encoding using `StandardCharsets.UTF_8`!
+* Do not declare multiple fields/variables on the same line! (e.g. Don't do this: `int x, y, z;`)
+* Use a Logger, try to avoid `System.out.println(...)` and `Throwable#printStacktrace()`, use `Logger#log` instead!
+* Do not use Exceptions to validate data, empty catch blocks are a very bad practice, use other means like a regular expression to validate data.
+* If a parameter is annotated with `@Nonnull`, you should enforce this behaviour by doing `Validate.notNull(variable, "...");` and give a meaningful message about what went wrong
+* Any `switch/case` should always have a `default:` case at the end.
+* If you are working with a resource that must be closed, use a `try/with-resource`, this will automatically close the resource at the end. (e.g. `try (InputStream stream = ...) {`)
+* Array designators should be placed behind the type, not the variable name. (e.g. `int[] myArray`)
+* Enums must be compared using `==`, not with `.equals()`!
+* Avoid direct string concatenation, use a `StringBuilder` instead!
+* If you need both the key and the value from a Map, use `Map#entrySet()`!
+#### 6. Naming conventions
+* Classes should be in *PascalCase* (e.g. `MyAwesomeClass`)
+* Enum constants should be in *SCREAMING_SNAKE_CASE* (e.g. `MY_ENUM_CONSTANT`)
+* Constants (`static final` fields) should be in *SCREAMING_SNAKE_CASE* (e.g. `MY_CONSTANT_FIELD`)
+* Variables, parameters and fields should be in *camelCase* (e.g. `myVariableOrField`)
+* All methods should be in *camelCase* (e.g. `myMethod`)
+* Packages must be all lowercase, consecutive words should generally be avoided. (e.g. `io.github.thebusybiscuit.slimefun4.core.something`)
+#### 7. Style preferences
+* Use **Spaces**, not Tabs!
+* One class per file! Please don't put multiple classes into one file, this also applies to enums, make a seperate file for new classes or enums.
+* Try to keep ternary operators to a minimum, only in return statements. (e.g. avoid doing this: `int y = x == null ? 1: 2`)
+* Try to keep so-called "guard blocks" to a minimum. One guard block is fine but having multiple guard blocks before getting to the actual code... Well, you might wanna refactor your code there. Example:
+```java
+// guard block
+if (something) {
+ return;
+}
+
+// Actual code...
+```
+* if/else statements should always include a bracket, please avoid one-line statements. (e.g. Avoid doing: `if (x == 0) return;`)
+* We do not enforce any particular width or column limit, just try to prevent your lines from becoming too long. But please avoid line-wrapping.
+* Annotations for methods or fields should never go on the same line, place them on the line above.
+* Comments should never go on the same line as code! Always above or below.
+* Make sure that empty lines are truly empty, they should not contain any whitespace characters.
+* Empty blocks like constructors should not occupy more than one line. (e.g. `private MyClass() {}`)
+* Modifiers for classes and fields must follow this order:
+`(public/protected/private) (abstract) (static) (final)`
+* We recommend using horizontal whitespaces like this:
+ * In variable assignments: `int x = 123;`
+ * In a for-loop: `for (int i = 0; i < 10; i++) {`
+ * Before and after statement parenthesis: `if (x != null) {`
+ * Inbetween array initializers: `int[] array = { 1, 2, 3 };`
+ * After the double slash of a comment: `// This is a comment`
+* Slimefun follows the **1TBS / OTBS** Bracket-Style standard (One true brace style):
+```java
+private void example(int x) {
+ if (x < 0) {
+ // x < 0
+ } else if (x > 0) {
+ // x > 0
+ } else {
+ // x == 0
+ }
+}
+```
diff --git a/README.md b/README.md
index 80f30248b..f531b510d 100644
--- a/README.md
+++ b/README.md
@@ -32,7 +32,7 @@ Here is a full summary of the differences between the two different versions of
| | development (latest) | "stable" |
| ------------------ | -------- | -------- |
-| **Minecraft version(s)** | :video_game: **1.13.\* - 1.16.\*** | :video_game: **1.13.\* - 1.16.\*** |
+| **Minecraft version(s)** | :video_game: **1.14.\* - 1.16.\*** | :video_game: **1.13.\* - 1.16.\*** |
| **automatic updates** | :heavy_check_mark: | :heavy_check_mark: |
| **frequent updates** | :heavy_check_mark: | :x: |
| **latest content** | :heavy_check_mark: | :x: |
diff --git a/pom.xml b/pom.xml
index eba85470d..06d6812a0 100644
--- a/pom.xml
+++ b/pom.xml
@@ -64,6 +64,10 @@
worldedit-repo
https://maven.sk89q.com/repo/
+
+ codemc-repo
+ https://repo.codemc.org/repository/maven-public
+
placeholderapi-repo
https://repo.extendedclip.com/content/repositories/placeholderapi/
@@ -262,6 +266,7 @@
*
+ tags/*
languages/*
@@ -310,7 +315,7 @@
com.github.seeseemelk
MockBukkit-v1.16
- 0.10.2
+ 0.13.0
test
@@ -344,7 +349,7 @@
com.konghq
unirest-java
- 3.11.00
+ 3.11.01
compile
@@ -367,6 +372,32 @@
de.schlichtherle
truezip
+
+ net.java.truevfs
+ truevfs-profile-default_2.13
+
+
+
+
+ com.gmail.nossr50.mcMMO
+ mcMMO
+ 2.1.149
+ provided
+
+
+
+
+ org.jetbrains
+ annotations
+
+
+ com.sk89q.worldguard
+ worldguard-core
+
+
+ com.sk89q.worldguard
+ worldguard-legacy
+
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/ErrorReport.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/ErrorReport.java
index 2abcada1d..7dbffa628 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/ErrorReport.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/ErrorReport.java
@@ -81,7 +81,7 @@ public class ErrorReport {
}
stream.println("Slimefun Data:");
- stream.println(" ID: " + item.getID());
+ stream.println(" ID: " + item.getId());
stream.println(" Inventory: " + BlockStorage.getStorage(l.getWorld()).hasInventory(l));
stream.println(" Data: " + BlockStorage.getBlockInfoAsJson(l));
stream.println();
@@ -92,7 +92,7 @@ public class ErrorReport {
public ErrorReport(T throwable, SlimefunItem item) {
this(throwable, item.getAddon(), stream -> {
stream.println("SlimefunItem:");
- stream.println(" ID: " + item.getID());
+ stream.println(" ID: " + item.getId());
stream.println(" Plugin: " + (item.getAddon() == null ? "Unknown" : item.getAddon().getName()));
stream.println();
});
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/MinecraftVersion.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/MinecraftVersion.java
index c4c8c0dd5..3f49247a9 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/MinecraftVersion.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/MinecraftVersion.java
@@ -14,12 +14,6 @@ import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
*/
public enum MinecraftVersion {
- /**
- * This constant represents Minecraft (Java Edition) Version 1.14
- * (The Update Aquatic)
- */
- MINECRAFT_1_13("1.13.x"),
-
/**
* This constant represents Minecraft (Java Edition) Version 1.14
* (The "Village & Pillage" Update)
@@ -50,7 +44,7 @@ public enum MinecraftVersion {
*/
UNIT_TEST("Unit Test Environment");
- public static final MinecraftVersion[] values = values();
+ public static final MinecraftVersion[] valuesCache = values();
private final String name;
private final String prefix;
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/exceptions/TagMisconfigurationException.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/exceptions/TagMisconfigurationException.java
new file mode 100644
index 000000000..165f5c3be
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/exceptions/TagMisconfigurationException.java
@@ -0,0 +1,48 @@
+package io.github.thebusybiscuit.slimefun4.api.exceptions;
+
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import org.bukkit.NamespacedKey;
+
+import io.github.thebusybiscuit.slimefun4.utils.tags.SlimefunTag;
+
+/**
+ * An {@link TagMisconfigurationException} is thrown whenever a {@link SlimefunTag}
+ * contains illegal, invalid or unknown values.
+ *
+ * @author TheBusyBiscuit
+ *
+ */
+public class TagMisconfigurationException extends Exception {
+
+ private static final long serialVersionUID = 5412127960821774280L;
+
+ /**
+ * This constructs a new {@link TagMisconfigurationException} for the given
+ * {@link SlimefunTag}'s {@link NamespacedKey} with the provided context.
+ *
+ * @param key
+ * The {@link NamespacedKey} of our {@link SlimefunTag}
+ * @param message
+ * The message to display
+ */
+ @ParametersAreNonnullByDefault
+ public TagMisconfigurationException(NamespacedKey key, String message) {
+ super("Tag '" + key + "' has been misconfigured: " + message);
+ }
+
+ /**
+ * This constructs a new {@link TagMisconfigurationException} for the given
+ * {@link SlimefunTag}'s {@link NamespacedKey} with the provided context.
+ *
+ * @param key
+ * The {@link NamespacedKey} of our {@link SlimefunTag}
+ * @param cause
+ * The {@link Throwable} which has caused this to happen
+ */
+ @ParametersAreNonnullByDefault
+ public TagMisconfigurationException(NamespacedKey key, Throwable cause) {
+ super("Tag '" + key + "' has been misconfigured (" + cause.getMessage() + ')', cause);
+ }
+
+}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/geo/ResourceManager.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/geo/ResourceManager.java
index b8fcbc218..81eb79474 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/geo/ResourceManager.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/geo/ResourceManager.java
@@ -201,15 +201,19 @@ public class ResourceManager {
menu.addItem(47, ChestMenuUtils.getPreviousButton(p, page + 1, pages));
menu.addMenuClickHandler(47, (pl, slot, item, action) -> {
- if (page > 0)
+ if (page > 0) {
scan(pl, block, page - 1);
+ }
+
return false;
});
menu.addItem(51, ChestMenuUtils.getNextButton(p, page + 1, pages));
menu.addMenuClickHandler(51, (pl, slot, item, action) -> {
- if (page + 1 < pages)
+ if (page + 1 < pages) {
scan(pl, block, page + 1);
+ }
+
return false;
});
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/GPSNetwork.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/GPSNetwork.java
index 1e7d7e311..649a0ea48 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/GPSNetwork.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/GPSNetwork.java
@@ -148,10 +148,12 @@ public class GPSNetwork {
int index = 0;
for (Location l : getTransmitters(p.getUniqueId())) {
- if (index >= inventory.length)
+ if (index >= inventory.length) {
break;
+ }
SlimefunItem sfi = BlockStorage.check(l);
+
if (sfi instanceof GPSTransmitter) {
int slot = inventory[index];
@@ -216,8 +218,10 @@ public class GPSNetwork {
int index = 0;
for (Waypoint waypoint : profile.getWaypoints()) {
- if (index >= inventory.length)
+ if (index >= inventory.length) {
break;
+ }
+
int slot = inventory[index];
Location l = waypoint.getLocation();
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/TeleportationManager.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/TeleportationManager.java
index e81bcf6a4..eb0ee827a 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/TeleportationManager.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/gps/TeleportationManager.java
@@ -92,8 +92,9 @@ public final class TeleportationManager {
@ParametersAreNonnullByDefault
public int getTeleportationTime(int complexity, Location source, Location destination) {
- if (complexity < 100)
+ if (complexity < 100) {
return 100;
+ }
int speed = 50_000 + complexity * complexity;
return 1 + Math.min(4 * distanceSquared(source, destination) / speed, 40);
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/HashedArmorpiece.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/HashedArmorpiece.java
index 15b25a0bc..f1efceeb6 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/HashedArmorpiece.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/HashedArmorpiece.java
@@ -102,7 +102,7 @@ public final class HashedArmorpiece {
@Override
public String toString() {
- return "HashedArmorpiece {hash=" + hash + ",item=" + item.map(SlimefunItem::getID).orElse("null") + '}';
+ return "HashedArmorpiece {hash=" + hash + ",item=" + item.map(SlimefunItem::getId).orElse("null") + '}';
}
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/ItemSetting.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/ItemSetting.java
index 7eedda655..e51ff0bcb 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/ItemSetting.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/ItemSetting.java
@@ -119,6 +119,17 @@ public class ItemSetting {
return c.isInstance(defaultValue);
}
+ /**
+ * This is an error message which should provide further context on what values
+ * are allowed.
+ *
+ * @return An error message which is displayed when this {@link ItemSetting} is misconfigured.
+ */
+ @Nonnull
+ protected String getErrorMessage() {
+ return "Only '" + defaultValue.getClass().getSimpleName() + "' values are allowed!";
+ }
+
/**
* This method is called by a {@link SlimefunItem} which wants to load its {@link ItemSetting}
* from the {@link Config} file.
@@ -128,20 +139,33 @@ public class ItemSetting {
*/
@SuppressWarnings("unchecked")
public void load(@Nonnull SlimefunItem item) {
- SlimefunPlugin.getItemCfg().setDefaultValue(item.getID() + '.' + getKey(), getDefaultValue());
- Object configuredValue = SlimefunPlugin.getItemCfg().getValue(item.getID() + '.' + getKey());
+ SlimefunPlugin.getItemCfg().setDefaultValue(item.getId() + '.' + getKey(), getDefaultValue());
+ Object configuredValue = SlimefunPlugin.getItemCfg().getValue(item.getId() + '.' + getKey());
if (defaultValue.getClass().isInstance(configuredValue)) {
- this.value = (T) configuredValue;
+ if (validateInput((T) configuredValue)) {
+ this.value = (T) configuredValue;
+ } else {
+ Slimefun.getLogger().log(Level.WARNING, "Slimefun has found an invalid config setting in your Items.yml!");
+ Slimefun.getLogger().log(Level.WARNING, " at \"{0}.{1}\"", new Object[] { item.getId(), getKey() });
+ Slimefun.getLogger().log(Level.WARNING, "{0} is not a valid input!", configuredValue);
+ Slimefun.getLogger().log(Level.WARNING, getErrorMessage());
+ }
} else {
this.value = defaultValue;
String found = configuredValue == null ? "null" : configuredValue.getClass().getSimpleName();
Slimefun.getLogger().log(Level.WARNING, "Slimefun has found an invalid config setting in your Items.yml!");
Slimefun.getLogger().log(Level.WARNING, "Please only use settings that are valid.");
- Slimefun.getLogger().log(Level.WARNING, " at \"{0}.{1}\"", new Object[] { item.getID(), getKey() });
+ Slimefun.getLogger().log(Level.WARNING, " at \"{0}.{1}\"", new Object[] { item.getId(), getKey() });
Slimefun.getLogger().log(Level.WARNING, "Expected \"{0}\" but found: \"{1}\"", new Object[] { defaultValue.getClass().getSimpleName(), found });
}
}
+ @Override
+ public String toString() {
+ T currentValue = this.value != null ? this.value : defaultValue;
+ return getClass().getSimpleName() + " {" + getKey() + " = " + currentValue + " (default: " + getDefaultValue() + ")";
+ }
+
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/DoubleRangeSetting.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/DoubleRangeSetting.java
new file mode 100644
index 000000000..86b02ac05
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/DoubleRangeSetting.java
@@ -0,0 +1,63 @@
+package io.github.thebusybiscuit.slimefun4.api.items.settings;
+
+import javax.annotation.Nonnull;
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import org.apache.commons.lang.Validate;
+
+import io.github.thebusybiscuit.slimefun4.api.items.ItemSetting;
+
+/**
+ * This variation of {@link ItemSetting} allows you to define an {@link Double} range
+ * and enforces this range using the {@link #validateInput(Double)} method.
+ *
+ * @author TheBusyBiscuit
+ *
+ * @see ItemSetting
+ * @see IntRangeSetting
+ *
+ */
+public class DoubleRangeSetting extends ItemSetting {
+
+ private final double min;
+ private final double max;
+
+ @ParametersAreNonnullByDefault
+ public DoubleRangeSetting(String key, double min, double defaultValue, double max) {
+ super(key, defaultValue);
+ Validate.isTrue(defaultValue >= min && defaultValue <= max, "The default value is not in range.");
+
+ this.min = min;
+ this.max = max;
+ }
+
+ @Nonnull
+ @Override
+ protected String getErrorMessage() {
+ return "Only decimal numbers from " + min + '-' + max + "(inclusive) are allowed!";
+ }
+
+ @Override
+ public boolean validateInput(Double input) {
+ return super.validateInput(input) && input >= min && input <= max;
+ }
+
+ /**
+ * This returns the minimum value of this {@link DoubleRangeSetting}.
+ *
+ * @return The minimum value
+ */
+ public final double getMinimum() {
+ return min;
+ }
+
+ /**
+ * This returns the maximum value of this {@link DoubleRangeSetting}.
+ *
+ * @return The maximum value
+ */
+ public final double getMaximum() {
+ return max;
+ }
+
+}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/EnumSetting.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/EnumSetting.java
new file mode 100644
index 000000000..d952286af
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/EnumSetting.java
@@ -0,0 +1,72 @@
+package io.github.thebusybiscuit.slimefun4.api.items.settings;
+
+import java.util.Arrays;
+import java.util.stream.Collectors;
+
+import javax.annotation.Nonnull;
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import io.github.thebusybiscuit.slimefun4.api.items.ItemSetting;
+
+/**
+ * This variation of {@link ItemSetting} allows you to allow {@link Enum} constants to be
+ * used for {@link ItemSetting} validation.
+ *
+ * @author TheBusyBiscuit
+ *
+ * @see ItemSetting
+ *
+ */
+public class EnumSetting> extends ItemSetting {
+
+ private final Class enumClass;
+
+ @ParametersAreNonnullByDefault
+ public EnumSetting(String key, Class enumClass, T defaultValue) {
+ super(key, defaultValue.name());
+
+ this.enumClass = enumClass;
+ }
+
+ @Nonnull
+ @Override
+ protected String getErrorMessage() {
+ String values = Arrays.stream(getAllowedValues()).map(Enum::name).collect(Collectors.joining(", "));
+ return "The following values are valid: " + values;
+ }
+
+ /**
+ * This returns an array of valid {@link Enum} values.
+ * This method may be overridden to further limit the allowed values.
+ *
+ * @return An array of allowed {@link Enum} constants
+ */
+ public T[] getAllowedValues() {
+ return enumClass.getEnumConstants();
+ }
+
+ /**
+ * This will attempt to get the configured value as a constant of the desired {@link Enum}.
+ *
+ * @return The value as an {@link Enum} constant
+ */
+ public T getAsEnumConstant() {
+ return Enum.valueOf(enumClass, getValue());
+ }
+
+ @Override
+ public boolean validateInput(String input) {
+ if (!super.validateInput(input)) {
+ return false;
+ } else {
+ for (Enum value : getAllowedValues()) {
+ if (value.name().equals(input)) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+ }
+
+}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/IntRangeSetting.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/IntRangeSetting.java
new file mode 100644
index 000000000..f4b41ed38
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/IntRangeSetting.java
@@ -0,0 +1,63 @@
+package io.github.thebusybiscuit.slimefun4.api.items.settings;
+
+import javax.annotation.Nonnull;
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import org.apache.commons.lang.Validate;
+
+import io.github.thebusybiscuit.slimefun4.api.items.ItemSetting;
+
+/**
+ * This variation of {@link ItemSetting} allows you to define an {@link Integer} range
+ * and enforces this range using the {@link #validateInput(Integer)} method.
+ *
+ * @author TheBusyBiscuit
+ *
+ * @see ItemSetting
+ * @see DoubleRangeSetting
+ *
+ */
+public class IntRangeSetting extends ItemSetting {
+
+ private final int min;
+ private final int max;
+
+ @ParametersAreNonnullByDefault
+ public IntRangeSetting(String key, int min, int defaultValue, int max) {
+ super(key, defaultValue);
+ Validate.isTrue(defaultValue >= min && defaultValue <= max, "The default value is not in range.");
+
+ this.min = min;
+ this.max = max;
+ }
+
+ @Nonnull
+ @Override
+ protected String getErrorMessage() {
+ return "Only whole numbers from " + min + '-' + max + "(inclusive) are allowed!";
+ }
+
+ @Override
+ public boolean validateInput(Integer input) {
+ return super.validateInput(input) && input >= min && input <= max;
+ }
+
+ /**
+ * This returns the minimum value of this {@link IntRangeSetting}.
+ *
+ * @return The minimum value
+ */
+ public final int getMinimum() {
+ return min;
+ }
+
+ /**
+ * This returns the maximum value of this {@link IntRangeSetting}.
+ *
+ * @return The maximum value
+ */
+ public final int getMaximum() {
+ return max;
+ }
+
+}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/MaterialTagSetting.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/MaterialTagSetting.java
new file mode 100644
index 000000000..b856d5614
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/MaterialTagSetting.java
@@ -0,0 +1,83 @@
+package io.github.thebusybiscuit.slimefun4.api.items.settings;
+
+import java.util.List;
+import java.util.stream.Collectors;
+
+import javax.annotation.Nonnull;
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import org.bukkit.Material;
+import org.bukkit.Tag;
+
+import io.github.thebusybiscuit.slimefun4.api.items.ItemSetting;
+
+/**
+ * This variation of {@link ItemSetting} allows you to define a default {@link Tag}.
+ * The {@link Tag} will be translated into a {@link String} {@link List} which the user
+ * can then configure as they wish.
+ *
+ * It also validates all inputs to be a valid {@link Material}.
+ *
+ * @author TheBusyBiscuit
+ *
+ * @see ItemSetting
+ *
+ */
+public class MaterialTagSetting extends ItemSetting> {
+
+ private final Tag defaultTag;
+
+ @ParametersAreNonnullByDefault
+ public MaterialTagSetting(String key, Tag defaultTag) {
+ super(key, getAsStringList(defaultTag));
+
+ this.defaultTag = defaultTag;
+ }
+
+ /**
+ * This {@link Tag} holds the default values for this {@link MaterialTagSetting}.
+ *
+ * @return The default {@link Tag}
+ */
+ @Nonnull
+ public Tag getDefaultTag() {
+ return defaultTag;
+ }
+
+ @Nonnull
+ @Override
+ protected String getErrorMessage() {
+ return "This List can only contain Materials in the format of e.g. REDSTONE_BLOCK";
+ }
+
+ @Override
+ public boolean validateInput(List input) {
+ if (super.validateInput(input)) {
+ for (String value : input) {
+ Material material = Material.matchMaterial(value);
+
+ // This value is not a valid material, the setting is not valid.
+ if (material == null) {
+ return false;
+ }
+ }
+
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ /**
+ * Internal method to turn a {@link Tag} into a {@link List} of {@link String Strings}.
+ *
+ * @param tag
+ * Our {@link Tag}
+ * @return The {@link String} {@link List}
+ */
+ @Nonnull
+ private static List getAsStringList(@Nonnull Tag tag) {
+ return tag.getValues().stream().map(Material::name).collect(Collectors.toList());
+ }
+
+}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/package-info.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/package-info.java
new file mode 100644
index 000000000..2f6bea34c
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/items/settings/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * This package contains various sub classes of {@link io.github.thebusybiscuit.slimefun4.api.items.ItemSetting}.
+ */
+package io.github.thebusybiscuit.slimefun4.api.items.settings;
\ No newline at end of file
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerBackpack.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerBackpack.java
index e0f2086f2..336a6bfbe 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerBackpack.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerBackpack.java
@@ -28,13 +28,14 @@ import io.github.thebusybiscuit.slimefun4.implementation.listeners.BackpackListe
*/
public class PlayerBackpack {
+ private static final String CONFIG_PREFIX = "backpacks.";
+
private final PlayerProfile profile;
private final int id;
private final Config cfg;
private Inventory inventory;
private int size;
- private static final String CONFIG_PREFIX = "backpacks.";
/**
* This constructor loads an existing Backpack
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/StatusEffect.java b/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/StatusEffect.java
index c108221ce..12a364457 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/StatusEffect.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/StatusEffect.java
@@ -4,6 +4,8 @@ import java.util.Optional;
import java.util.OptionalInt;
import java.util.concurrent.TimeUnit;
+import javax.annotation.Nonnull;
+
import io.github.thebusybiscuit.slimefun4.utils.PatternUtils;
import org.bukkit.Keyed;
import org.bukkit.NamespacedKey;
@@ -27,10 +29,11 @@ public class StatusEffect implements Keyed {
private final NamespacedKey key;
- public StatusEffect(NamespacedKey key) {
+ public StatusEffect(@Nonnull NamespacedKey key) {
this.key = key;
}
+ @Nonnull
@Override
public NamespacedKey getKey() {
return key;
@@ -48,7 +51,7 @@ public class StatusEffect implements Keyed {
* @param unit
* The {@link TimeUnit} for the given duration
*/
- public void add(Player p, int duration, TimeUnit unit) {
+ public void add(@Nonnull Player p, int duration, @Nonnull TimeUnit unit) {
add(p, 1, duration, unit);
}
@@ -64,7 +67,7 @@ public class StatusEffect implements Keyed {
* @param unit
* The {@link TimeUnit} for the given duration
*/
- public void add(Player p, int level, int duration, TimeUnit unit) {
+ public void add(@Nonnull Player p, int level, int duration, @Nonnull TimeUnit unit) {
PersistentDataAPI.setString(p, getKey(), level + ";" + System.currentTimeMillis() + unit.toMillis(duration));
}
@@ -77,7 +80,7 @@ public class StatusEffect implements Keyed {
* @param level
* The level of this effect
*/
- public void addPermanent(Player p, int level) {
+ public void addPermanent(@Nonnull Player p, int level) {
PersistentDataAPI.setString(p, getKey(), level + ";0");
}
@@ -91,7 +94,7 @@ public class StatusEffect implements Keyed {
* The {@link Player} to check for
* @return Whether this {@link StatusEffect} is currently applied
*/
- public boolean isPresent(Player p) {
+ public boolean isPresent(@Nonnull Player p) {
Optional optional = PersistentDataAPI.getOptionalString(p, getKey());
if (optional.isPresent()) {
@@ -104,8 +107,9 @@ public class StatusEffect implements Keyed {
clear(p);
return false;
}
- } else
+ } else {
return false;
+ }
}
/**
@@ -116,15 +120,16 @@ public class StatusEffect implements Keyed {
* The {@link Player} to check for
* @return An {@link OptionalInt} that describes the result
*/
- public OptionalInt getLevel(Player p) {
+ @Nonnull
+ public OptionalInt getLevel(@Nonnull Player p) {
Optional optional = PersistentDataAPI.getOptionalString(p, getKey());
if (optional.isPresent()) {
String[] data = PatternUtils.SEMICOLON.split(optional.get());
return OptionalInt.of(Integer.parseInt(data[0]));
-
- } else
+ } else {
return OptionalInt.empty();
+ }
}
/**
@@ -133,7 +138,7 @@ public class StatusEffect implements Keyed {
* @param p
* The {@link Player} to clear it from
*/
- public void clear(Player p) {
+ public void clear(@Nonnull Player p) {
PersistentDataAPI.remove(p, getKey());
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/SlimefunRegistry.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/SlimefunRegistry.java
index 1b05dbcf1..538a1dc49 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/SlimefunRegistry.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/SlimefunRegistry.java
@@ -11,6 +11,9 @@ import java.util.Set;
import java.util.UUID;
import java.util.concurrent.ConcurrentHashMap;
+import javax.annotation.Nonnull;
+
+import org.apache.commons.lang.Validate;
import org.bukkit.Server;
import org.bukkit.entity.Entity;
import org.bukkit.entity.EntityType;
@@ -19,14 +22,12 @@ import org.bukkit.inventory.ItemStack;
import io.github.thebusybiscuit.cscorelib2.collections.KeyMap;
import io.github.thebusybiscuit.cscorelib2.config.Config;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
import io.github.thebusybiscuit.slimefun4.api.geo.GEOResource;
import io.github.thebusybiscuit.slimefun4.api.player.PlayerProfile;
import io.github.thebusybiscuit.slimefun4.core.guide.SlimefunGuideImplementation;
import io.github.thebusybiscuit.slimefun4.core.guide.SlimefunGuideLayout;
import io.github.thebusybiscuit.slimefun4.core.multiblocks.MultiBlock;
import io.github.thebusybiscuit.slimefun4.core.researching.Research;
-import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import io.github.thebusybiscuit.slimefun4.implementation.guide.BookSlimefunGuide;
import io.github.thebusybiscuit.slimefun4.implementation.guide.CheatSheetSlimefunGuide;
import io.github.thebusybiscuit.slimefun4.implementation.guide.ChestSlimefunGuide;
@@ -47,7 +48,7 @@ import me.mrCookieSlime.Slimefun.api.inventory.UniversalBlockMenu;
* @author TheBusyBiscuit
*
*/
-public class SlimefunRegistry {
+public final class SlimefunRegistry {
private final Map slimefunIds = new HashMap<>();
private final List slimefunItems = new ArrayList<>();
@@ -86,7 +87,9 @@ public class SlimefunRegistry {
private final Map automatedCraftingChamberRecipes = new HashMap<>();
- public void load(Config cfg) {
+ public void load(@Nonnull Config cfg) {
+ Validate.notNull(cfg, "The Config cannot be null!");
+
boolean showVanillaRecipes = cfg.getBoolean("guide.show-vanilla-recipes");
layouts.put(SlimefunGuideLayout.CHEST, new ChestSlimefunGuide(showVanillaRecipes));
@@ -95,7 +98,7 @@ public class SlimefunRegistry {
researchRanks.addAll(cfg.getStringList("research-ranks"));
- backwardsCompatibility = cfg.getBoolean("options.backwards-compatibility") || SlimefunPlugin.getMinecraftVersion().isBefore(MinecraftVersion.MINECRAFT_1_14);
+ backwardsCompatibility = cfg.getBoolean("options.backwards-compatibility");
freeCreativeResearches = cfg.getBoolean("researches.free-in-creative-mode");
researchFireworks = cfg.getBoolean("researches.enable-fireworks");
logDuplicateBlockEntries = cfg.getBoolean("options.log-duplicate-block-entries");
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/EnergyNetComponent.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/EnergyNetComponent.java
index 06123f1e3..6d2e1504d 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/EnergyNetComponent.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/EnergyNetComponent.java
@@ -66,6 +66,12 @@ public interface EnergyNetComponent extends ItemAttribute {
*/
default int getCharge(@Nonnull Location l) {
Validate.notNull(l, "Location was null!");
+
+ // Emergency fallback, this cannot hold a charge, so we'll just return zero
+ if (!isChargeable()) {
+ return 0;
+ }
+
String charge = BlockStorage.getLocationInfo(l, "energy-charge");
if (charge != null) {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/RechargeableHelper.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/RechargeableHelper.java
index f19af55a5..b0e47b1a5 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/RechargeableHelper.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/attributes/RechargeableHelper.java
@@ -13,7 +13,6 @@ import org.bukkit.inventory.meta.ItemMeta;
import org.bukkit.persistence.PersistentDataType;
import io.github.thebusybiscuit.cscorelib2.chat.ChatColors;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import io.github.thebusybiscuit.slimefun4.utils.PatternUtils;
import net.md_5.bungee.api.ChatColor;
@@ -39,9 +38,7 @@ final class RechargeableHelper {
BigDecimal decimal = BigDecimal.valueOf(charge).setScale(2, RoundingMode.HALF_UP);
float value = decimal.floatValue();
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- meta.getPersistentDataContainer().set(CHARGE_KEY, PersistentDataType.FLOAT, value);
- }
+ meta.getPersistentDataContainer().set(CHARGE_KEY, PersistentDataType.FLOAT, value);
List lore = meta.hasLore() ? meta.getLore() : new ArrayList<>();
for (int i = 0; i < lore.size(); i++) {
@@ -59,13 +56,11 @@ final class RechargeableHelper {
}
static float getCharge(@Nonnull ItemMeta meta) {
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- Float value = meta.getPersistentDataContainer().get(CHARGE_KEY, PersistentDataType.FLOAT);
+ Float value = meta.getPersistentDataContainer().get(CHARGE_KEY, PersistentDataType.FLOAT);
- // If persistent data is available, we just return this value
- if (value != null) {
- return value;
- }
+ // If persistent data is available, we just return this value
+ if (value != null) {
+ return value;
}
// If no persistent data exists, we will just fall back to the lore
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/SlimefunTabCompleter.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/SlimefunTabCompleter.java
index b061f475e..e22d222ec 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/SlimefunTabCompleter.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/SlimefunTabCompleter.java
@@ -99,7 +99,7 @@ class SlimefunTabCompleter implements TabCompleter {
List list = new ArrayList<>(items.size());
for (SlimefunItem item : items) {
- list.add(item.getID());
+ list.add(item.getId());
}
return list;
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/ResearchCommand.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/ResearchCommand.java
index dacdb30e2..8bc1d7e2d 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/ResearchCommand.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/ResearchCommand.java
@@ -49,8 +49,9 @@ class ResearchCommand extends SubCommand {
} else {
SlimefunPlugin.getLocalization().sendMessage(sender, "messages.not-online", true, msg -> msg.replace(PLACEHOLDER_PLAYER, args[1]));
}
- } else
+ } else {
SlimefunPlugin.getLocalization().sendMessage(sender, "messages.no-permission", true);
+ }
} else {
SlimefunPlugin.getLocalization().sendMessage(sender, "messages.usage", true, msg -> msg.replace("%usage%", "/sf research "));
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/StatsCommand.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/StatsCommand.java
index 11abe9817..1bb18b3e6 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/StatsCommand.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/commands/subcommands/StatsCommand.java
@@ -29,8 +29,9 @@ class StatsCommand extends SubCommand {
} else {
SlimefunPlugin.getLocalization().sendMessage(sender, "messages.not-online", true, msg -> msg.replace("%player%", args[1]));
}
- } else
+ } else {
SlimefunPlugin.getLocalization().sendMessage(sender, "messages.no-permission", true);
+ }
} else if (sender instanceof Player) {
PlayerProfile.get((Player) sender, profile -> profile.sendStats(sender));
} else {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuide.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuide.java
index 0fd23d500..94970ac43 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuide.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuide.java
@@ -78,15 +78,20 @@ public final class SlimefunGuide {
}
public static void openCategory(PlayerProfile profile, Category category, SlimefunGuideLayout layout, int selectedPage) {
- if (category == null)
+ if (category == null) {
return;
+ }
+
SlimefunPlugin.getRegistry().getGuideLayout(layout).openCategory(profile, category, selectedPage);
}
public static void openSearch(PlayerProfile profile, String input, boolean survival, boolean addToHistory) {
SlimefunGuideImplementation layout = SlimefunPlugin.getRegistry().getGuideLayout(SlimefunGuideLayout.CHEST);
- if (!survival)
+
+ if (!survival) {
layout = SlimefunPlugin.getRegistry().getGuideLayout(SlimefunGuideLayout.CHEAT_SHEET);
+ }
+
layout.openSearch(profile, input, addToHistory);
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuideLayout.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuideLayout.java
index 278352c9d..562fe5981 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuideLayout.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/SlimefunGuideLayout.java
@@ -31,6 +31,6 @@ public enum SlimefunGuideLayout {
*/
CHEAT_SHEET;
- public static final SlimefunGuideLayout[] values = values();
+ public static final SlimefunGuideLayout[] valuesCache = values();
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/GuideLayoutOption.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/GuideLayoutOption.java
index cf19b812d..38564d077 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/GuideLayoutOption.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/GuideLayoutOption.java
@@ -98,7 +98,7 @@ class GuideLayoutOption implements SlimefunGuideOption {
@Override
public Optional getSelectedOption(Player p, ItemStack guide) {
- for (SlimefunGuideLayout layout : SlimefunGuideLayout.values) {
+ for (SlimefunGuideLayout layout : SlimefunGuideLayout.valuesCache) {
if (SlimefunUtils.isItemSimilar(guide, SlimefunGuide.getItem(layout), true, false)) {
return Optional.of(layout);
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/SlimefunGuideSettings.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/SlimefunGuideSettings.java
index 7c132d44f..1ed862a13 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/SlimefunGuideSettings.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/guide/options/SlimefunGuideSettings.java
@@ -12,7 +12,6 @@ import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack;
import io.github.thebusybiscuit.cscorelib2.item.CustomItem;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
import io.github.thebusybiscuit.slimefun4.core.guide.SlimefunGuide;
import io.github.thebusybiscuit.slimefun4.core.guide.SlimefunGuideLayout;
import io.github.thebusybiscuit.slimefun4.core.services.localization.Language;
@@ -41,11 +40,8 @@ public final class SlimefunGuideSettings {
static {
options.add(new GuideLayoutOption());
-
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- options.add(new FireworksOption());
- options.add(new PlayerLanguageOption());
- }
+ options.add(new FireworksOption());
+ options.add(new PlayerLanguageOption());
}
private SlimefunGuideSettings() {}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/handlers/RainbowTickHandler.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/handlers/RainbowTickHandler.java
index 5cd2867ea..4ba7ed63a 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/handlers/RainbowTickHandler.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/handlers/RainbowTickHandler.java
@@ -1,6 +1,9 @@
package io.github.thebusybiscuit.slimefun4.core.handlers;
import java.util.Arrays;
+import java.util.List;
+
+import javax.annotation.Nonnull;
import org.apache.commons.lang.Validate;
import org.bukkit.Material;
@@ -10,7 +13,6 @@ import org.bukkit.block.data.BlockData;
import org.bukkit.block.data.type.GlassPane;
import io.github.thebusybiscuit.cscorelib2.collections.LoopIterator;
-import io.github.thebusybiscuit.cscorelib2.materials.MaterialCollection;
import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import io.github.thebusybiscuit.slimefun4.implementation.items.blocks.RainbowBlock;
@@ -34,18 +36,22 @@ public class RainbowTickHandler extends BlockTicker {
private final boolean glassPanes;
private Material material;
- public RainbowTickHandler(Material... materials) {
+ public RainbowTickHandler(@Nonnull List materials) {
Validate.noNullElements(materials, "A RainbowTicker cannot have a Material that is null!");
- if (materials.length == 0) {
+ if (materials.isEmpty()) {
throw new IllegalArgumentException("A RainbowTicker must have at least one Material associated with it!");
}
glassPanes = containsGlassPanes(materials);
- iterator = new LoopIterator<>(Arrays.asList(materials));
+ iterator = new LoopIterator<>(materials);
material = iterator.next();
}
+ public RainbowTickHandler(Material... materials) {
+ this(Arrays.asList(materials));
+ }
+
/**
* This method checks whether a given {@link Material} array contains any {@link Material}
* that would result in a {@link GlassPane} {@link BlockData}.
@@ -57,7 +63,7 @@ public class RainbowTickHandler extends BlockTicker {
*
* @return Whether the array contained any {@link GlassPane} materials
*/
- private boolean containsGlassPanes(Material[] materials) {
+ private boolean containsGlassPanes(@Nonnull List materials) {
if (SlimefunPlugin.getMinecraftVersion() == MinecraftVersion.UNIT_TEST) {
// BlockData is not available to us during Unit Tests :/
return false;
@@ -75,10 +81,6 @@ public class RainbowTickHandler extends BlockTicker {
return false;
}
- public RainbowTickHandler(MaterialCollection collection) {
- this(collection.getAsArray());
- }
-
@Override
public void tick(Block b, SlimefunItem item, Config data) {
if (b.getType() == Material.AIR) {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/multiblocks/MultiBlock.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/multiblocks/MultiBlock.java
index 83bb966b2..49b80dd9a 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/multiblocks/MultiBlock.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/multiblocks/MultiBlock.java
@@ -41,10 +41,8 @@ public class MultiBlock {
SUPPORTED_TAGS.add(Tag.LOGS);
SUPPORTED_TAGS.add(Tag.WOODEN_TRAPDOORS);
SUPPORTED_TAGS.add(Tag.WOODEN_SLABS);
+ SUPPORTED_TAGS.add(Tag.WOODEN_FENCES);
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- SUPPORTED_TAGS.add(Tag.WOODEN_FENCES);
- }
if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_16)) {
SUPPORTED_TAGS.add(Tag.FIRE);
}
@@ -119,7 +117,7 @@ public class MultiBlock {
@Override
public int hashCode() {
- return Objects.hash(item.getID(), blocks, trigger, isSymmetric);
+ return Objects.hash(item.getId(), blocks, trigger, isSymmetric);
}
private boolean compareBlocks(Material a, @Nullable Material b) {
@@ -161,6 +159,6 @@ public class MultiBlock {
@Override
public String toString() {
- return "MultiBlock (" + item.getID() + ") {" + Arrays.toString(blocks) + "}";
+ return "MultiBlock (" + item.getId() + ") {" + Arrays.toString(blocks) + "}";
}
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/cargo/CargoUtils.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/cargo/CargoUtils.java
index 81c8051c2..b7e5fabab 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/cargo/CargoUtils.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/cargo/CargoUtils.java
@@ -18,10 +18,10 @@ import org.bukkit.inventory.InventoryHolder;
import org.bukkit.inventory.ItemStack;
import io.github.thebusybiscuit.cscorelib2.blocks.BlockPosition;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import io.github.thebusybiscuit.slimefun4.utils.SlimefunUtils;
import io.github.thebusybiscuit.slimefun4.utils.itemstack.ItemStackWrapper;
+import io.github.thebusybiscuit.slimefun4.utils.tags.SlimefunTag;
import io.papermc.lib.PaperLib;
import me.mrCookieSlime.CSCoreLibPlugin.Configuration.Config;
import me.mrCookieSlime.Slimefun.api.BlockStorage;
@@ -54,6 +54,10 @@ final class CargoUtils {
Material type = block.getType();
+ if (SlimefunTag.SHULKER_BOXES.isTagged(type)) {
+ return true;
+ }
+
switch (type) {
case CHEST:
case TRAPPED_CHEST:
@@ -62,28 +66,13 @@ final class CargoUtils {
case DROPPER:
case HOPPER:
case BREWING_STAND:
- case SHULKER_BOX:
+ case BARREL:
+ case BLAST_FURNACE:
+ case SMOKER:
return true;
default:
- break;
+ return false;
}
-
- if (type.name().endsWith("_SHULKER_BOX")) {
- return true;
- }
-
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- switch (type) {
- case BARREL:
- case BLAST_FURNACE:
- case SMOKER:
- return true;
- default:
- break;
- }
- }
-
- return false;
}
static int[] getInputSlotRange(@Nonnull Inventory inv, @Nullable ItemStack item) {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNet.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNet.java
index c009dbab2..02eea2d4b 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNet.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNet.java
@@ -70,6 +70,7 @@ public class EnergyNet extends Network {
return null;
} else {
switch (component.getEnergyComponentType()) {
+ case CONNECTOR:
case CAPACITOR:
return NetworkComponent.CONNECTOR;
case CONSUMER:
@@ -272,6 +273,20 @@ public class EnergyNet extends Network {
return null;
}
+ /**
+ * This attempts to get an {@link EnergyNet} from a given {@link Location}.
+ * If no suitable {@link EnergyNet} could be found, {@code null} will be returned.
+ *
+ * @param l
+ * The target {@link Location}
+ *
+ * @return The {@link EnergyNet} at that {@link Location}, or {@code null}
+ */
+ @Nullable
+ public static EnergyNet getNetworkFromLocation(@Nonnull Location l) {
+ return SlimefunPlugin.getNetworkManager().getNetworkFromLocation(l, EnergyNet.class).orElse(null);
+ }
+
/**
* This attempts to get an {@link EnergyNet} from a given {@link Location}.
* If no suitable {@link EnergyNet} could be found, a new one will be created.
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNetComponentType.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNetComponentType.java
index fe62f19ad..ef05a8466 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNetComponentType.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/networks/energy/EnergyNetComponentType.java
@@ -4,6 +4,7 @@ import org.bukkit.block.Block;
import io.github.thebusybiscuit.slimefun4.core.attributes.EnergyNetComponent;
import io.github.thebusybiscuit.slimefun4.implementation.items.electric.Capacitor;
+import io.github.thebusybiscuit.slimefun4.implementation.items.electric.EnergyConnector;
import io.github.thebusybiscuit.slimefun4.implementation.items.electric.reactors.Reactor;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.abstractItems.AContainer;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.abstractItems.AGenerator;
@@ -13,6 +14,7 @@ import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.abstractItems.AGenerator;
* can have.
*
* @author TheBusyBiscuit
+ * @author Linox
*
* @see EnergyNetComponent
* @see EnergyNet
@@ -38,6 +40,12 @@ public enum EnergyNetComponentType {
*/
CONSUMER,
+ /**
+ * A Connector transmits energy through the network.
+ * Also see: {@link EnergyConnector}
+ */
+ CONNECTOR,
+
/**
* A fallback value to use when a {@link Block} cannot be classified as any of the
* other options.
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/BlockDataService.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/BlockDataService.java
index 9dd1449f8..c9c577681 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/BlockDataService.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/BlockDataService.java
@@ -11,9 +11,6 @@ import org.bukkit.block.TileState;
import org.bukkit.persistence.PersistentDataHolder;
import org.bukkit.plugin.Plugin;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
-import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
-
/**
* The {@link BlockDataService} is similar to the {@link CustomItemDataService},
* it is responsible for storing NBT data inside a {@link TileState}.
@@ -83,9 +80,8 @@ public class BlockDataService implements PersistentDataService, Keyed {
* @return Whether the given {@link Material} is considered a Tile Entity
*/
public boolean isTileEntity(Material type) {
- if (type == null || !SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- // We can only store data on Tile Entities in 1.14+
- // So we will just return false here in that case.
+ if (type == null || type.isAir()) {
+ // Cannot store data on air
return false;
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/CustomTextureService.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/CustomTextureService.java
index d5ce5225b..5587ad8b2 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/CustomTextureService.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/CustomTextureService.java
@@ -10,8 +10,6 @@ import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.ItemMeta;
import io.github.thebusybiscuit.cscorelib2.config.Config;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
-import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.SlimefunItem;
import me.mrCookieSlime.Slimefun.api.SlimefunItemStack;
@@ -64,9 +62,9 @@ public class CustomTextureService {
for (SlimefunItem item : items) {
if (item != null) {
- config.setDefaultValue(item.getID(), 0);
+ config.setDefaultValue(item.getId(), 0);
- if (config.getInt(item.getID()) != 0) {
+ if (config.getInt(item.getId()) != 0) {
modified = true;
}
}
@@ -101,10 +99,7 @@ public class CustomTextureService {
public void setTexture(@Nonnull ItemMeta im, @Nonnull String id) {
int data = getModelData(id);
-
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- im.setCustomModelData(data == 0 ? null : data);
- }
+ im.setCustomModelData(data == 0 ? null : data);
}
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/MetricsService.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/MetricsService.java
index 2da170c23..5835e9f86 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/MetricsService.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/MetricsService.java
@@ -48,12 +48,7 @@ public class MetricsService {
private boolean hasDownloadedUpdate = false;
static {
- Unirest.config()
- .concurrency(2, 1)
- .setDefaultHeader("User-Agent", "MetricsModule Auto-Updater")
- .setDefaultHeader("Accept", "application/vnd.github.v3+json")
- .enableCookieManagement(false)
- .cookieSpec("ignoreCookies");
+ Unirest.config().concurrency(2, 1).setDefaultHeader("User-Agent", "MetricsModule Auto-Updater").setDefaultHeader("Accept", "application/vnd.github.v3+json").enableCookieManagement(false).cookieSpec("ignoreCookies");
}
public MetricsService(@Nonnull SlimefunPlugin plugin) {
@@ -221,7 +216,7 @@ public class MetricsService {
return true;
}
} catch (UnirestException e) {
- plugin.getLogger().log(Level.WARNING, "Failed to fetch the latest jar file from the builds page. Perhaps GitHub is down?");
+ plugin.getLogger().log(Level.WARNING, "Failed to fetch the latest jar file from the builds page. Perhaps GitHub is down? Response: {0}", e.getMessage());
} catch (IOException e) {
plugin.getLogger().log(Level.WARNING, "Failed to replace the old metric file with the new one. Please do this manually! Error: {0}", e.getMessage());
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PerWorldSettingsService.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PerWorldSettingsService.java
index 9c76ef6c7..8e11d9563 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PerWorldSettingsService.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PerWorldSettingsService.java
@@ -85,7 +85,7 @@ public class PerWorldSettingsService {
return false;
}
- return !items.contains(item.getID());
+ return !items.contains(item.getId());
}
/**
@@ -105,9 +105,9 @@ public class PerWorldSettingsService {
Set items = disabledItems.computeIfAbsent(world.getUID(), id -> loadWorldFromConfig(world));
if (enabled) {
- items.remove(item.getID());
+ items.remove(item.getId());
} else {
- items.add(item.getID());
+ items.add(item.getId());
}
}
@@ -178,7 +178,7 @@ public class PerWorldSettingsService {
for (SlimefunItem item : SlimefunPlugin.getRegistry().getEnabledSlimefunItems()) {
if (item != null) {
String addon = item.getAddon().getName().toLowerCase(Locale.ROOT);
- config.setValue(addon + '.' + item.getID(), !items.contains(item.getID()));
+ config.setValue(addon + '.' + item.getId(), !items.contains(item.getId()));
}
}
@@ -222,7 +222,7 @@ public class PerWorldSettingsService {
if (item != null) {
String addon = item.getAddon().getName().toLowerCase(Locale.ROOT);
config.setDefaultValue(addon + ".enabled", true);
- config.setDefaultValue(addon + '.' + item.getID(), true);
+ config.setDefaultValue(addon + '.' + item.getId(), true);
// Whether the entire addon has been disabled
boolean isAddonDisabled = config.getBoolean(addon + ".enabled");
@@ -232,8 +232,8 @@ public class PerWorldSettingsService {
blacklist.add(worldName);
}
- if (!isAddonDisabled || !config.getBoolean(addon + '.' + item.getID())) {
- items.add(item.getID());
+ if (!isAddonDisabled || !config.getBoolean(addon + '.' + item.getId())) {
+ items.add(item.getId());
}
}
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PermissionsService.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PermissionsService.java
index 63b2fbe62..920896ab2 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PermissionsService.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PermissionsService.java
@@ -41,12 +41,12 @@ public class PermissionsService {
public void register(@Nonnull Iterable items, boolean save) {
for (SlimefunItem item : items) {
if (item != null) {
- String path = item.getID() + ".permission";
+ String path = item.getId() + ".permission";
config.setDefaultValue(path, "none");
- config.setDefaultValue(item.getID() + ".lore", new String[] { "&rYou do not have the permission", "&rto access this item." });
+ config.setDefaultValue(item.getId() + ".lore", new String[] { "&rYou do not have the permission", "&rto access this item." });
- permissions.put(item.getID(), config.getString(path));
+ permissions.put(item.getId(), config.getString(path));
}
}
@@ -72,7 +72,7 @@ public class PermissionsService {
return true;
}
- String permission = permissions.get(item.getID());
+ String permission = permissions.get(item.getId());
return permission == null || permission.equals("none") || p.hasPermission(permission);
}
@@ -89,7 +89,7 @@ public class PermissionsService {
@Nonnull
public Optional getPermission(@Nonnull SlimefunItem item) {
Validate.notNull(item, "Cannot get permissions for null");
- String permission = permissions.get(item.getID());
+ String permission = permissions.get(item.getId());
if (permission == null || permission.equals("none")) {
return Optional.empty();
@@ -108,7 +108,7 @@ public class PermissionsService {
*/
public void setPermission(@Nonnull SlimefunItem item, @Nullable String permission) {
Validate.notNull(item, "You cannot set the permission for null");
- permissions.put(item.getID(), permission != null ? permission : "none");
+ permissions.put(item.getId(), permission != null ? permission : "none");
}
/**
@@ -124,7 +124,7 @@ public class PermissionsService {
@Nonnull
public List getLore(@Nonnull SlimefunItem item) {
- List lore = config.getStringList(item.getID() + ".lore");
+ List lore = config.getStringList(item.getId() + ".lore");
return lore == null ? Arrays.asList("LORE NOT FOUND") : lore;
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PersistentDataService.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PersistentDataService.java
index 8a1035d74..b1792f546 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PersistentDataService.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/PersistentDataService.java
@@ -7,32 +7,29 @@ import org.bukkit.persistence.PersistentDataContainer;
import org.bukkit.persistence.PersistentDataHolder;
import org.bukkit.persistence.PersistentDataType;
+import io.github.thebusybiscuit.cscorelib2.data.PersistentDataAPI;
import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
-import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
/**
* This interface is used to defer calls to Persistent Data and make sure they are only called
* if the {@link MinecraftVersion} supports it.
*
* @author TheBusyBiscuit
+ *
+ * @deprecated This is redundant, we can use {@link PersistentDataAPI} instead.
*
*/
+@Deprecated
interface PersistentDataService {
default void setString(Object obj, NamespacedKey key, String value) {
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14) && obj instanceof PersistentDataHolder) {
- PersistentDataContainer container = ((PersistentDataHolder) obj).getPersistentDataContainer();
- container.set(key, PersistentDataType.STRING, value);
- }
+ PersistentDataContainer container = ((PersistentDataHolder) obj).getPersistentDataContainer();
+ container.set(key, PersistentDataType.STRING, value);
}
default Optional getString(Object obj, NamespacedKey key) {
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14) && obj instanceof PersistentDataHolder) {
- PersistentDataContainer container = ((PersistentDataHolder) obj).getPersistentDataContainer();
- return Optional.ofNullable(container.get(key, PersistentDataType.STRING));
- }
-
- return Optional.empty();
+ PersistentDataContainer container = ((PersistentDataHolder) obj).getPersistentDataContainer();
+ return Optional.ofNullable(container.get(key, PersistentDataType.STRING));
}
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubConnector.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubConnector.java
index baa099769..0f9e3e317 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubConnector.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubConnector.java
@@ -94,7 +94,7 @@ abstract class GitHubConnector {
}
} catch (UnirestException e) {
if (github.isLoggingEnabled()) {
- Slimefun.getLogger().log(Level.WARNING, "Could not connect to GitHub in time.");
+ Slimefun.getLogger().log(Level.WARNING, "Could not connect to GitHub in time.", e);
}
// It has the cached file, let's just read that then
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubTask.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubTask.java
index 5401465fb..932bf7060 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubTask.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/github/GitHubTask.java
@@ -88,7 +88,7 @@ class GitHubTask implements Runnable {
} catch (IOException x) {
// Too many requests
Slimefun.getLogger().log(Level.WARNING, "Attempted to connect to mojang.com, got this response: {0}: {1}", new Object[] { x.getClass().getSimpleName(), x.getMessage() });
- Slimefun.getLogger().log(Level.WARNING, "This usually means mojang.com is down or started to rate-limit this connection, this is not an error message!");
+ Slimefun.getLogger().log(Level.WARNING, "This usually means mojang.com is temporarily down or started to rate-limit this connection, this is not an error message!");
// Retry after 5 minutes if it was rate-limiting
if (x.getMessage().contains("429")) {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SlimefunLocalization.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SlimefunLocalization.java
index 390f3a469..dc1bea4b1 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SlimefunLocalization.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SlimefunLocalization.java
@@ -85,7 +85,7 @@ public abstract class SlimefunLocalization extends Localization implements Keyed
protected abstract void addLanguage(@Nonnull String id, @Nonnull String texture);
protected void loadEmbeddedLanguages() {
- for (SupportedLanguage lang : SupportedLanguage.values) {
+ for (SupportedLanguage lang : SupportedLanguage.valuesCache) {
if (lang.isReadyForRelease() || SlimefunPlugin.getUpdater().getBranch() != SlimefunBranch.STABLE) {
addLanguage(lang.getLanguageId(), lang.getTexture());
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SupportedLanguage.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SupportedLanguage.java
index 76287f772..a6381a059 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SupportedLanguage.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/SupportedLanguage.java
@@ -58,7 +58,7 @@ enum SupportedLanguage {
MACEDONIAN("mk", false, "a0e0b0b5d87a855466980a101a757bcdb5f77d9f7287889f3efa998ee0472fc0"),
TAGALOG("tl", true, "9306c0c1ce6a9c61bb42a572c49e6d0ed20e0e6b3d122cc64c339cbf78e9e937");
- public static final SupportedLanguage[] values = values();
+ public static final SupportedLanguage[] valuesCache = values();
private final String id;
private final boolean releaseReady;
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/Translators.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/Translators.java
index 80a235dbe..dd5f95a95 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/Translators.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/localization/Translators.java
@@ -99,6 +99,9 @@ public class Translators {
addTranslator("Dr4gonD", "DragonD", SupportedLanguage.DUTCH, true);
addTranslator("svr333", SupportedLanguage.DUTCH, false);
addTranslator("PabloMarcendo", SupportedLanguage.DUTCH, true);
+ addTranslator("milvantiou", SupportedLanguage.DUTCH, true);
+ addTranslator("Sven313D", SupportedLanguage.DUTCH, true);
+ addTranslator("TypischTeun", SupportedLanguage.DUTCH, true);
// Translators - Danish
addTranslator("Mini-kun", SupportedLanguage.DANISH, true);
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ClearLagHook.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ClearLagIntegration.java
similarity index 75%
rename from src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ClearLagHook.java
rename to src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ClearLagIntegration.java
index 3722fcfd6..212bb1f3f 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ClearLagHook.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ClearLagIntegration.java
@@ -11,11 +11,19 @@ import org.bukkit.event.Listener;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import io.github.thebusybiscuit.slimefun4.utils.SlimefunUtils;
+import me.minebuilders.clearlag.Clearlag;
import me.minebuilders.clearlag.events.EntityRemoveEvent;
-class ClearLagHook implements Listener {
+/**
+ * This handles all integrations with {@link Clearlag}.
+ * We don't want it to clear our altar items.
+ *
+ * @author TheBusyBiscuit
+ *
+ */
+class ClearLagIntegration implements Listener {
- ClearLagHook(@Nonnull SlimefunPlugin plugin) {
+ ClearLagIntegration(@Nonnull SlimefunPlugin plugin) {
plugin.getServer().getPluginManager().registerEvents(this, plugin);
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/EmeraldEnchantsCategory.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/EmeraldEnchantsCategory.java
index ecd2fd7b0..486c59af8 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/EmeraldEnchantsCategory.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/EmeraldEnchantsCategory.java
@@ -12,6 +12,7 @@ import io.github.thebusybiscuit.slimefun4.core.categories.FlexCategory;
import io.github.thebusybiscuit.slimefun4.core.guide.SlimefunGuideLayout;
import me.mrCookieSlime.EmeraldEnchants.EnchantmentGuide;
+@Deprecated
class EmeraldEnchantsCategory extends FlexCategory {
public EmeraldEnchantsCategory(@Nonnull NamespacedKey key) {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/McMMOIntegration.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/McMMOIntegration.java
new file mode 100644
index 000000000..553627469
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/McMMOIntegration.java
@@ -0,0 +1,60 @@
+package io.github.thebusybiscuit.slimefun4.core.services.plugins;
+
+import javax.annotation.Nonnull;
+
+import org.bukkit.event.EventHandler;
+import org.bukkit.event.EventPriority;
+import org.bukkit.event.Listener;
+import org.bukkit.inventory.ItemStack;
+
+import com.gmail.nossr50.mcMMO;
+import com.gmail.nossr50.events.skills.salvage.McMMOPlayerSalvageCheckEvent;
+
+import io.github.thebusybiscuit.slimefun4.api.events.BlockPlacerPlaceEvent;
+import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
+import io.github.thebusybiscuit.slimefun4.implementation.items.VanillaItem;
+import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.SlimefunItem;
+
+/**
+ * This handles all integrations with {@link mcMMO}.
+ *
+ * @author TheBusyBiscuit
+ *
+ */
+class McMMOIntegration implements Listener {
+
+ McMMOIntegration(@Nonnull SlimefunPlugin plugin) {
+ plugin.getServer().getPluginManager().registerEvents(this, plugin);
+ }
+
+ @EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
+ public void onBlockPlacerPlace(BlockPlacerPlaceEvent e) {
+ // This registers blocks placed by the BlockPlacer as "player-placed"
+ mcMMO.getPlaceStore().setTrue(e.getBlock());
+ }
+
+ @EventHandler(ignoreCancelled = true)
+ public void onItemSalvage(McMMOPlayerSalvageCheckEvent e) {
+ // Prevent Slimefun items from being salvaged
+ if (!isSalvageable(e.getSalvageItem())) {
+ e.setCancelled(true);
+ SlimefunPlugin.getLocalization().sendMessage(e.getPlayer(), "anvil.mcmmo-salvaging");
+ }
+ }
+
+ /**
+ * This method checks if an {@link ItemStack} can be salvaged or not.
+ * We basically don't want players to salvage any {@link SlimefunItem} unless
+ * it is a {@link VanillaItem}.
+ *
+ * @param item
+ * The {@link ItemStack} to check
+ *
+ * @return Whether this item can be safely salvaged
+ */
+ private boolean isSalvageable(@Nonnull ItemStack item) {
+ SlimefunItem sfItem = SlimefunItem.getByItem(item);
+ return sfItem == null || sfItem instanceof VanillaItem;
+ }
+
+}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/PlaceholderAPIHook.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/PlaceholderAPIIntegration.java
similarity index 93%
rename from src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/PlaceholderAPIHook.java
rename to src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/PlaceholderAPIIntegration.java
index 892729663..d49426458 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/PlaceholderAPIHook.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/PlaceholderAPIIntegration.java
@@ -13,14 +13,21 @@ import org.bukkit.entity.Player;
import io.github.thebusybiscuit.slimefun4.api.player.PlayerProfile;
import io.github.thebusybiscuit.slimefun4.core.researching.Research;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
+import me.clip.placeholderapi.PlaceholderAPI;
import me.clip.placeholderapi.expansion.PlaceholderExpansion;
-class PlaceholderAPIHook extends PlaceholderExpansion {
+/**
+ * This is our integration for {@link PlaceholderAPI}.
+ *
+ * @author TheBusyBiscuit
+ *
+ */
+class PlaceholderAPIIntegration extends PlaceholderExpansion {
private final String version;
private final String author;
- public PlaceholderAPIHook(@Nonnull SlimefunPlugin plugin) {
+ public PlaceholderAPIIntegration(@Nonnull SlimefunPlugin plugin) {
this.version = plugin.getDescription().getVersion();
this.author = plugin.getDescription().getAuthors().toString();
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ThirdPartyPluginService.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ThirdPartyPluginService.java
index 877aac6b1..4bf85071f 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ThirdPartyPluginService.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/ThirdPartyPluginService.java
@@ -5,12 +5,16 @@ import java.util.function.Function;
import java.util.logging.Level;
import javax.annotation.Nonnull;
+import javax.annotation.ParametersAreNonnullByDefault;
import org.bukkit.NamespacedKey;
import org.bukkit.block.Block;
+import org.bukkit.event.Event;
import org.bukkit.inventory.ItemStack;
import org.bukkit.plugin.Plugin;
+import com.gmail.nossr50.events.fake.FakeBlockBreakEvent;
+
import io.github.thebusybiscuit.slimefun4.api.SlimefunAddon;
import io.github.thebusybiscuit.slimefun4.core.categories.FlexCategory;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
@@ -31,25 +35,41 @@ public class ThirdPartyPluginService {
private final SlimefunPlugin plugin;
+ private boolean initialized = false;
private boolean isExoticGardenInstalled = false;
private boolean isChestTerminalInstalled = false;
private boolean isEmeraldEnchantsInstalled = false;
- private boolean isCoreProtectInstalled = false;
- private boolean isPlaceholderAPIInstalled = false;
+ private boolean isMcMMOInstalled = false;
- // Overridden if ExoticGarden is loaded
+ /**
+ * This gets overridden if ExoticGarden is loaded
+ */
private Function> exoticGardenIntegration = b -> Optional.empty();
+ /**
+ * This initializes the {@link ThirdPartyPluginService}
+ *
+ * @param plugin
+ * Our instance of {@link SlimefunPlugin}
+ */
public ThirdPartyPluginService(@Nonnull SlimefunPlugin plugin) {
this.plugin = plugin;
}
+ /**
+ * This method initializes all third party integrations.
+ */
public void start() {
+ if (initialized) {
+ throw new UnsupportedOperationException("Third Party Integrations have already been initialized!");
+ }
+
+ initialized = true;
+
if (isPluginInstalled("PlaceholderAPI")) {
try {
- PlaceholderAPIHook hook = new PlaceholderAPIHook(plugin);
+ PlaceholderAPIIntegration hook = new PlaceholderAPIIntegration(plugin);
hook.register();
- isPlaceholderAPIInstalled = true;
} catch (Exception | LinkageError x) {
String version = plugin.getServer().getPluginManager().getPlugin("PlaceholderAPI").getDescription().getVersion();
@@ -69,7 +89,7 @@ public class ThirdPartyPluginService {
if (isPluginInstalled("WorldEdit")) {
try {
Class.forName("com.sk89q.worldedit.extent.Extent");
- new WorldEditHook();
+ new WorldEditIntegration();
} catch (Exception | LinkageError x) {
String version = plugin.getServer().getPluginManager().getPlugin("WorldEdit").getDescription().getVersion();
@@ -78,6 +98,21 @@ public class ThirdPartyPluginService {
}
}
+ // mcMMO Integration
+ if (isPluginInstalled("mcMMO")) {
+ try {
+ // This makes sure that the FakeEvent interface is present.
+ // Class.forName("com.gmail.nossr50.events.fake.FakeEvent");
+
+ new McMMOIntegration(plugin);
+ isMcMMOInstalled = true;
+ } catch (Exception | LinkageError x) {
+ String version = plugin.getServer().getPluginManager().getPlugin("mcMMO").getDescription().getVersion();
+ Slimefun.getLogger().log(Level.WARNING, "Maybe consider updating mcMMO or Slimefun?");
+ Slimefun.getLogger().log(Level.WARNING, x, () -> "Failed to hook into mcMMO v" + version);
+ }
+ }
+
/*
* These Items are not marked as soft-dependencies and
* therefore need to be loaded after the Server has finished
@@ -85,7 +120,7 @@ public class ThirdPartyPluginService {
*/
plugin.getServer().getScheduler().scheduleSyncDelayedTask(plugin, () -> {
if (isPluginInstalled("ClearLag")) {
- new ClearLagHook(plugin);
+ new ClearLagIntegration(plugin);
}
isChestTerminalInstalled = isPluginInstalled("ChestTerminal");
@@ -101,6 +136,7 @@ public class ThirdPartyPluginService {
}
}
+ @ParametersAreNonnullByDefault
public void loadExoticGarden(Plugin plugin, Function> method) {
if (plugin.getName().equals("ExoticGarden")) {
isExoticGardenInstalled = true;
@@ -120,16 +156,22 @@ public class ThirdPartyPluginService {
return isEmeraldEnchantsInstalled;
}
- public boolean isCoreProtectInstalled() {
- return isCoreProtectInstalled;
- }
-
- public boolean isPlaceholderAPIInstalled() {
- return isPlaceholderAPIInstalled;
- }
-
public Optional harvestExoticGardenPlant(Block block) {
return exoticGardenIntegration.apply(block);
}
+ /**
+ * This checks if one of our third party integrations faked an {@link Event}.
+ * Faked {@link Event Events} should be ignored in our logic.
+ *
+ * @param event
+ * The {@link Event} to test
+ *
+ * @return Whether this is a fake event
+ */
+ public boolean isEventFaked(@Nonnull Event event) {
+ // TODO: Change this to FakeEvent once the new mcMMO build was released
+ return isMcMMOInstalled && event instanceof FakeBlockBreakEvent;
+ }
+
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/WorldEditHook.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/WorldEditIntegration.java
similarity index 86%
rename from src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/WorldEditHook.java
rename to src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/WorldEditIntegration.java
index 3b134df92..38af34726 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/WorldEditHook.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/plugins/WorldEditIntegration.java
@@ -14,9 +14,16 @@ import com.sk89q.worldedit.world.block.BlockStateHolder;
import me.mrCookieSlime.Slimefun.api.BlockStorage;
-class WorldEditHook {
+/**
+ * This handles all integrations with {@link WorldEdit}.
+ * If an are is cleared, we also wanna clear all Slimefun-related block data.
+ *
+ * @author TheBusyBiscuit
+ *
+ */
+class WorldEditIntegration {
- WorldEditHook() {
+ WorldEditIntegration() {
WorldEdit.getInstance().getEventBus().register(this);
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/PerformanceRating.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/PerformanceRating.java
index b03191c6c..b1417b523 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/PerformanceRating.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/PerformanceRating.java
@@ -31,7 +31,7 @@ public enum PerformanceRating implements Predicate {
HURTFUL(ChatColor.DARK_RED, 500),
BAD(ChatColor.DARK_RED, Float.MAX_VALUE);
- public static final PerformanceRating[] values = values();
+ public static final PerformanceRating[] valuesCache = values();
private final ChatColor color;
private final float threshold;
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/ProfiledBlock.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/ProfiledBlock.java
index c89707a9b..8a4e68d0d 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/ProfiledBlock.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/ProfiledBlock.java
@@ -46,7 +46,7 @@ class ProfiledBlock {
}
public String getId() {
- return item.getID();
+ return item.getId();
}
public SlimefunAddon getAddon() {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/SlimefunProfiler.java b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/SlimefunProfiler.java
index d123c37c4..5a0d92d9a 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/SlimefunProfiler.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/core/services/profiler/SlimefunProfiler.java
@@ -296,7 +296,7 @@ public class SlimefunProfiler {
public PerformanceRating getPerformance() {
float percentage = getPercentageOfTick();
- for (PerformanceRating rating : PerformanceRating.values) {
+ for (PerformanceRating rating : PerformanceRating.valuesCache) {
if (rating.test(percentage)) {
return rating;
}
@@ -344,7 +344,7 @@ public class SlimefunProfiler {
public String getTime(@Nonnull SlimefunItem item) {
Validate.notNull("Cannot get timings for a null SlimefunItem");
- long time = getByItem().getOrDefault(item.getID(), 0L);
+ long time = getByItem().getOrDefault(item.getId(), 0L);
return NumberUtils.getAsMillis(time);
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunItems.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunItems.java
index 6c4cd245e..68c8b2d88 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunItems.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunItems.java
@@ -581,14 +581,14 @@ public final class SlimefunItems {
public static final SlimefunItemStack ENHANCED_CRAFTING_TABLE = new SlimefunItemStack("ENHANCED_CRAFTING_TABLE", Material.CRAFTING_TABLE, "&eEnhanced Crafting Table", "", "&aA regular Crafting Table cannot", "&ahold this massive Amount of Power...");
public static final SlimefunItemStack GRIND_STONE = new SlimefunItemStack("GRIND_STONE", Material.DISPENSER, "&bGrind Stone", "", "&aGrinds items down into other items");
public static final SlimefunItemStack ARMOR_FORGE = new SlimefunItemStack("ARMOR_FORGE", Material.ANVIL, "&6Armor Forge", "", "&aGives you the ability to create powerful armor");
- public static final SlimefunItemStack MAKESHIFT_SMELTERY;
+ public static final SlimefunItemStack MAKESHIFT_SMELTERY = new SlimefunItemStack("MAKESHIFT_SMELTERY", Material.BLAST_FURNACE, "&eMakeshift Smeltery", "", "&fImprovised version of the Smeltery", "&fthat only allows you to", "&fsmelt dusts into ingots");
public static final SlimefunItemStack SMELTERY = new SlimefunItemStack("SMELTERY", Material.FURNACE, "&6Smeltery", "", "&fA high-temperature furnace", "&fthat allows you to smelt dusts", "&finto ingots and create alloys.");
public static final SlimefunItemStack ORE_CRUSHER = new SlimefunItemStack("ORE_CRUSHER", Material.DISPENSER, "&bOre Crusher", "", "&aCrushes ores to double them");
public static final SlimefunItemStack COMPRESSOR = new SlimefunItemStack("COMPRESSOR", Material.PISTON, "&bCompressor", "", "&aCompresses Items");
public static final SlimefunItemStack PRESSURE_CHAMBER = new SlimefunItemStack("PRESSURE_CHAMBER", Material.GLASS, "&bPressure Chamber", "", "&aCompresses Items even further");
public static final SlimefunItemStack MAGIC_WORKBENCH = new SlimefunItemStack("MAGIC_WORKBENCH", Material.CRAFTING_TABLE, "&6Magic Workbench", "", "&dInfuses Items with magical Energy");
public static final SlimefunItemStack ORE_WASHER = new SlimefunItemStack("ORE_WASHER", Material.CAULDRON, "&6Ore Washer", "", "&aWashes Sifted Ore to filter Ores", "&aand gives you small Stone Chunks");
- public static final SlimefunItemStack TABLE_SAW;
+ public static final SlimefunItemStack TABLE_SAW = new SlimefunItemStack("TABLE_SAW", Material.STONECUTTER, "&6Table Saw", "", "&aAllows you to get 8 planks from 1 Log", "&a(Works with all log types)");
public static final SlimefunItemStack JUICER = new SlimefunItemStack("JUICER", Material.GLASS_BOTTLE, "&aJuicer", "", "&aAllows you to create delicious Juice");
public static final SlimefunItemStack AUTOMATED_PANNING_MACHINE = new SlimefunItemStack("AUTOMATED_PANNING_MACHINE", Material.BOWL, "&eAutomated Panning Machine", "", "&fA MultiBlock Version of the Gold Pan", "&fand Nether Gold Pan combined in one machine.");
@@ -676,22 +676,22 @@ public final class SlimefunItems {
public static final SlimefunItemStack ELECTRIC_ORE_GRINDER = new SlimefunItemStack("ELECTRIC_ORE_GRINDER", Material.FURNACE, "&cElectric Ore Grinder", "", "&fWorks as an Ore Crusher and Grind Stone", "", LoreBuilder.machine(MachineTier.ADVANCED, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(12));
public static final SlimefunItemStack ELECTRIC_ORE_GRINDER_2 = new SlimefunItemStack("ELECTRIC_ORE_GRINDER_2", Material.FURNACE, "&cElectric Ore Grinder &7(&eII&7)", "", "&fWorks as an Ore Crusher and Grind Stone", "", LoreBuilder.machine(MachineTier.END_GAME, MachineType.MACHINE), LoreBuilder.speed(4), LoreBuilder.powerPerSecond(30));
public static final SlimefunItemStack ELECTRIC_INGOT_PULVERIZER = new SlimefunItemStack("ELECTRIC_INGOT_PULVERIZER", Material.FURNACE, "&cElectric Ingot Pulverizer", "", "&fPulverizes Ingots into Dust", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(14));
- public static final SlimefunItemStack AUTO_DRIER;
+ public static final SlimefunItemStack AUTO_DRIER = new SlimefunItemStack("AUTO_DRIER", Material.SMOKER, "&6Auto Drier", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(10));
public static final SlimefunItemStack AUTO_ENCHANTER = new SlimefunItemStack("AUTO_ENCHANTER", Material.ENCHANTING_TABLE, "&5Auto Enchanter", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(18));
public static final SlimefunItemStack AUTO_DISENCHANTER = new SlimefunItemStack("AUTO_DISENCHANTER", Material.ENCHANTING_TABLE, "&5Auto Disenchanter", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(18));
public static final SlimefunItemStack AUTO_ANVIL = new SlimefunItemStack("AUTO_ANVIL", Material.IRON_BLOCK, "&7Auto Anvil", "", LoreBuilder.machine(MachineTier.ADVANCED, MachineType.MACHINE), "&8\u21E8 &7Repair Factor: 10%", LoreBuilder.powerPerSecond(24));
public static final SlimefunItemStack AUTO_ANVIL_2 = new SlimefunItemStack("AUTO_ANVIL_2", Material.IRON_BLOCK, "&7Auto Anvil Mk.II", "", LoreBuilder.machine(MachineTier.END_GAME, MachineType.MACHINE), "&8\u21E8 &7Repair Factor: 25%", LoreBuilder.powerPerSecond(32));
- public static final SlimefunItemStack AUTO_BREWER;
+ public static final SlimefunItemStack AUTO_BREWER = new SlimefunItemStack("AUTO_BREWER", Material.SMOKER, "&6Auto Brewer", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(12));
public static final SlimefunItemStack BIO_REACTOR = new SlimefunItemStack("BIO_REACTOR", Material.LIME_TERRACOTTA, "&2Bio Reactor", "", LoreBuilder.machine(MachineTier.AVERAGE, MachineType.GENERATOR), LoreBuilder.powerBuffer(128), LoreBuilder.powerPerSecond(8));
public static final SlimefunItemStack MULTIMETER = new SlimefunItemStack("MULTIMETER", Material.CLOCK, "&eMultimeter", "", "&fMeasures the Amount of stored", "&fEnergy in a Block");
- public static final SlimefunItemStack SMALL_CAPACITOR = new SlimefunItemStack("SMALL_CAPACITOR", HeadTexture.CAPACITOR_25, "&aSmall Energy Capacitor", "", LoreBuilder.machine(MachineTier.BASIC, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &7128 J Capacity");
- public static final SlimefunItemStack MEDIUM_CAPACITOR = new SlimefunItemStack("MEDIUM_CAPACITOR", HeadTexture.CAPACITOR_25, "&aMedium Energy Capacitor", "", LoreBuilder.machine(MachineTier.AVERAGE, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &7512 J Capacity");
- public static final SlimefunItemStack BIG_CAPACITOR = new SlimefunItemStack("BIG_CAPACITOR", HeadTexture.CAPACITOR_25, "&aBig Energy Capacitor", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &71024 J Capacity");
- public static final SlimefunItemStack LARGE_CAPACITOR = new SlimefunItemStack("LARGE_CAPACITOR", HeadTexture.CAPACITOR_25, "&aLarge Energy Capacitor", "", LoreBuilder.machine(MachineTier.GOOD, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &78192 J Capacity");
- public static final SlimefunItemStack CARBONADO_EDGED_CAPACITOR = new SlimefunItemStack("CARBONADO_EDGED_CAPACITOR", HeadTexture.CAPACITOR_25, "&aCarbonado Edged Energy Capacitor", "", LoreBuilder.machine(MachineTier.END_GAME, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &765536 J Capacity");
- public static final SlimefunItemStack ENERGIZED_CAPACITOR = new SlimefunItemStack("ENERGIZED_CAPACITOR", HeadTexture.CAPACITOR_25, "&aEnergized Energy Capacitor", "", LoreBuilder.machine(MachineTier.END_GAME, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &7524288 J Capacity");
+ public static final SlimefunItemStack SMALL_CAPACITOR = new SlimefunItemStack("SMALL_CAPACITOR", HeadTexture.CAPACITOR_25, "&aSmall Energy Capacitor", LoreBuilder.range(6), "", LoreBuilder.machine(MachineTier.BASIC, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &7128 J Capacity");
+ public static final SlimefunItemStack MEDIUM_CAPACITOR = new SlimefunItemStack("MEDIUM_CAPACITOR", HeadTexture.CAPACITOR_25, "&aMedium Energy Capacitor", LoreBuilder.range(6), "", LoreBuilder.machine(MachineTier.AVERAGE, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &7512 J Capacity");
+ public static final SlimefunItemStack BIG_CAPACITOR = new SlimefunItemStack("BIG_CAPACITOR", HeadTexture.CAPACITOR_25, "&aBig Energy Capacitor", LoreBuilder.range(6), "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &71024 J Capacity");
+ public static final SlimefunItemStack LARGE_CAPACITOR = new SlimefunItemStack("LARGE_CAPACITOR", HeadTexture.CAPACITOR_25, "&aLarge Energy Capacitor", LoreBuilder.range(6), "", LoreBuilder.machine(MachineTier.GOOD, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &78192 J Capacity");
+ public static final SlimefunItemStack CARBONADO_EDGED_CAPACITOR = new SlimefunItemStack("CARBONADO_EDGED_CAPACITOR", HeadTexture.CAPACITOR_25, "&aCarbonado Edged Energy Capacitor", LoreBuilder.range(6), "", LoreBuilder.machine(MachineTier.END_GAME, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &765536 J Capacity");
+ public static final SlimefunItemStack ENERGIZED_CAPACITOR = new SlimefunItemStack("ENERGIZED_CAPACITOR", HeadTexture.CAPACITOR_25, "&aEnergized Energy Capacitor", LoreBuilder.range(6), "", LoreBuilder.machine(MachineTier.END_GAME, MachineType.CAPACITOR), "&8\u21E8 &e\u26A1 &7524288 J Capacity");
/* Robots */
public static final SlimefunItemStack PROGRAMMABLE_ANDROID = new SlimefunItemStack("PROGRAMMABLE_ANDROID", HeadTexture.PROGRAMMABLE_ANDROID, "&cProgrammable Android &7(Normal)", "", "&8\u21E8 &7Function: None", "&8\u21E8 &7Fuel Efficiency: 1.0x");
@@ -764,6 +764,7 @@ public final class SlimefunItems {
public static final SlimefunItemStack BLISTERING_INGOT_3 = new SlimefunItemStack("BLISTERING_INGOT_3", Material.GOLD_INGOT, "&6Blistering Ingot", "", LoreBuilder.radioactive(Radioactivity.VERY_HIGH), LoreBuilder.HAZMAT_SUIT_REQUIRED);
public static final SlimefunItemStack ENERGY_REGULATOR = new SlimefunItemStack("ENERGY_REGULATOR", HeadTexture.ENERGY_REGULATOR, "&6Energy Regulator", "", "&fCore Component of an Energy Network");
+ public static final SlimefunItemStack ENERGY_CONNECTOR = new SlimefunItemStack("ENERGY_CONNECTOR", HeadTexture.ENERGY_CONNECTOR, "&eEnergy Connector", LoreBuilder.range(6), "", "&fPlace this between machines", "&fand generators to connect them", "&fto your regulator.");
public static final SlimefunItemStack DEBUG_FISH = new SlimefunItemStack("DEBUG_FISH", Material.SALMON, "&3How much is the Fish?", "", "&eRight Click &fany Block to view it's BlockData", "&eLeft Click &fto break a Block", "&eShift + Left Click &fany Block to erase it's BlockData", "&eShift + Right Click &fto place a Placeholder Block");
public static final SlimefunItemStack NETHER_ICE = new SlimefunItemStack("NETHER_ICE", HeadTexture.NETHER_ICE, "&eNether Ice", "", LoreBuilder.radioactive(Radioactivity.MODERATE), LoreBuilder.HAZMAT_SUIT_REQUIRED);
@@ -854,17 +855,5 @@ public final class SlimefunItems {
static {
INFUSED_ELYTRA.addUnsafeEnchantment(Enchantment.MENDING, 1);
-
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- TABLE_SAW = new SlimefunItemStack("TABLE_SAW", Material.STONECUTTER, "&6Table Saw", "", "&aAllows you to get 8 planks from 1 Log", "&a(Works with all log types)");
- MAKESHIFT_SMELTERY = new SlimefunItemStack("MAKESHIFT_SMELTERY", Material.BLAST_FURNACE, "&eMakeshift Smeltery", "", "&fImprovised version of the Smeltery", "&fthat only allows you to", "&fsmelt dusts into ingots");
- AUTO_DRIER = new SlimefunItemStack("AUTO_DRIER", Material.SMOKER, "&6Auto Drier", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(10));
- AUTO_BREWER = new SlimefunItemStack("AUTO_BREWER", Material.SMOKER, "&6Auto Brewer", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(12));
- } else {
- TABLE_SAW = null;
- MAKESHIFT_SMELTERY = new SlimefunItemStack("MAKESHIFT_SMELTERY", Material.FURNACE, "&eMakeshift Smeltery", "", "&fImprovised version of the Smeltery", "&fthat only allows you to", "&fsmelt dusts into ingots");
- AUTO_DRIER = new SlimefunItemStack("AUTO_DRIER", Material.FURNACE, "&6Auto Drier", "", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(10));
- AUTO_BREWER = new SlimefunItemStack("AUTO_BREWER", Material.BREWING_STAND, "&6Auto Brewer", LoreBuilder.machine(MachineTier.MEDIUM, MachineType.MACHINE), LoreBuilder.speed(1), LoreBuilder.powerPerSecond(12));
- }
}
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunPlugin.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunPlugin.java
index 517135ba1..23bfb15fb 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunPlugin.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/SlimefunPlugin.java
@@ -30,6 +30,7 @@ import io.github.thebusybiscuit.cscorelib2.protection.ProtectionManager;
import io.github.thebusybiscuit.cscorelib2.reflection.ReflectionUtils;
import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
import io.github.thebusybiscuit.slimefun4.api.SlimefunAddon;
+import io.github.thebusybiscuit.slimefun4.api.exceptions.TagMisconfigurationException;
import io.github.thebusybiscuit.slimefun4.api.gps.GPSNetwork;
import io.github.thebusybiscuit.slimefun4.api.player.PlayerProfile;
import io.github.thebusybiscuit.slimefun4.core.SlimefunRegistry;
@@ -89,10 +90,15 @@ import io.github.thebusybiscuit.slimefun4.implementation.listeners.SlimefunItemL
import io.github.thebusybiscuit.slimefun4.implementation.listeners.SoulboundListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.TalismanListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.VampireBladeListener;
-import io.github.thebusybiscuit.slimefun4.implementation.listeners.VanillaMachinesListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.VillagerTradingListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.WitherListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.WorldListener;
+import io.github.thebusybiscuit.slimefun4.implementation.listeners.crafting.AnvilListener;
+import io.github.thebusybiscuit.slimefun4.implementation.listeners.crafting.BrewingStandListener;
+import io.github.thebusybiscuit.slimefun4.implementation.listeners.crafting.CartographyTableListener;
+import io.github.thebusybiscuit.slimefun4.implementation.listeners.crafting.CauldronListener;
+import io.github.thebusybiscuit.slimefun4.implementation.listeners.crafting.CraftingTableListener;
+import io.github.thebusybiscuit.slimefun4.implementation.listeners.crafting.GrindstoneListener;
import io.github.thebusybiscuit.slimefun4.implementation.resources.GEOResourcesSetup;
import io.github.thebusybiscuit.slimefun4.implementation.setup.PostSetup;
import io.github.thebusybiscuit.slimefun4.implementation.setup.ResearchSetup;
@@ -100,6 +106,7 @@ import io.github.thebusybiscuit.slimefun4.implementation.setup.SlimefunItemSetup
import io.github.thebusybiscuit.slimefun4.implementation.tasks.ArmorTask;
import io.github.thebusybiscuit.slimefun4.implementation.tasks.SlimefunStartupTask;
import io.github.thebusybiscuit.slimefun4.implementation.tasks.TickerTask;
+import io.github.thebusybiscuit.slimefun4.utils.tags.SlimefunTag;
import io.papermc.lib.PaperLib;
import me.mrCookieSlime.CSCoreLibPlugin.CSCoreLib;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.abstractItems.AContainer;
@@ -175,10 +182,14 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
command.register();
registry.load(config);
} else if (getServer().getPluginManager().isPluginEnabled("CS-CoreLib")) {
+ getLogger().log(Level.INFO, "CS-CoreLib was detected!");
long timestamp = System.nanoTime();
-
PaperLib.suggestPaper(this);
+ if (PaperLib.isPaper()) {
+ getLogger().log(Level.INFO, "Paper was detected! Performance optimizations have been applied.");
+ }
+
// We wanna ensure that the Server uses a compatible version of Minecraft
if (isVersionUnsupported()) {
getServer().getPluginManager().disablePlugin(this);
@@ -229,6 +240,9 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
getLogger().log(Level.INFO, "Loading GEO-Resources...");
GEOResourcesSetup.setup();
+ getLogger().log(Level.INFO, "Loading Tags...");
+ loadTags();
+
getLogger().log(Level.INFO, "Loading items...");
loadItems();
@@ -267,7 +281,10 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
autoSavingService.start(this, config.getInt("options.auto-save-delay-in-minutes"));
ticker.start(this);
+
+ getLogger().log(Level.INFO, "Loading Third-Party plugin integrations...");
thirdPartySupportService.start();
+
gitHubService.start(this);
// Hooray!
@@ -311,7 +328,7 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
String currentVersion = ReflectionUtils.getVersion();
if (currentVersion.startsWith("v")) {
- for (MinecraftVersion version : MinecraftVersion.values) {
+ for (MinecraftVersion version : MinecraftVersion.valuesCache) {
if (version.matches(currentVersion)) {
minecraftVersion = version;
return false;
@@ -338,7 +355,7 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
private Collection getSupportedVersions() {
List list = new ArrayList<>();
- for (MinecraftVersion version : MinecraftVersion.values) {
+ for (MinecraftVersion version : MinecraftVersion.valuesCache) {
if (version != MinecraftVersion.UNKNOWN) {
list.add(version.getName());
}
@@ -442,7 +459,6 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
new DeathpointListener(this);
new ExplosionsListener(this);
new DebugFishListener(this);
- new VanillaMachinesListener(this);
new FireworksListener(this);
new WitherListener(this);
new IronGolemListener(this);
@@ -450,6 +466,12 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
new MobDropListener(this);
new VillagerTradingListener(this);
new ElytraCrashListener(this);
+ new CraftingTableListener(this);
+ new AnvilListener(this);
+ new BrewingStandListener(this);
+ new CauldronListener(this);
+ new GrindstoneListener(this);
+ new CartographyTableListener(this);
if (minecraftVersion.isAtLeast(MinecraftVersion.MINECRAFT_1_15)) {
new BeeListener(this);
@@ -491,6 +513,16 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
new PlayerProfileListener(this);
}
+ private void loadTags() {
+ for (SlimefunTag tag : SlimefunTag.valuesCache) {
+ try {
+ tag.reload();
+ } catch (TagMisconfigurationException e) {
+ getLogger().log(Level.SEVERE, e, () -> "Failed to load Tag: " + tag.name());
+ }
+ }
+ }
+
private void loadItems() {
try {
SlimefunItemSetup.setup(this);
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/BookSlimefunGuide.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/BookSlimefunGuide.java
index 0a26c0a7f..59b081e82 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/BookSlimefunGuide.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/BookSlimefunGuide.java
@@ -208,7 +208,7 @@ public class BookSlimefunGuide implements SlimefunGuideImplementation {
}
private void addSlimefunItem(Category category, int page, Player p, PlayerProfile profile, SlimefunItem item, List items) {
- NamespacedKey key = new NamespacedKey(SlimefunPlugin.instance(), item.getID().toLowerCase(Locale.ROOT));
+ NamespacedKey key = new NamespacedKey(SlimefunPlugin.instance(), item.getId().toLowerCase(Locale.ROOT));
if (!Slimefun.hasUnlocked(p, item, false) && item.getResearch() != null) {
Research research = item.getResearch();
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/ChestSlimefunGuide.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/ChestSlimefunGuide.java
index 5ca33706b..cbab11d87 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/ChestSlimefunGuide.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/guide/ChestSlimefunGuide.java
@@ -1,7 +1,5 @@
package io.github.thebusybiscuit.slimefun4.implementation.guide;
-import javax.annotation.Nonnull;
-
import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedList;
@@ -10,6 +8,8 @@ import java.util.Locale;
import java.util.Optional;
import java.util.logging.Level;
+import javax.annotation.Nonnull;
+
import org.bukkit.ChatColor;
import org.bukkit.Material;
import org.bukkit.Sound;
@@ -26,7 +26,6 @@ import io.github.thebusybiscuit.cscorelib2.chat.ChatInput;
import io.github.thebusybiscuit.cscorelib2.inventory.ItemUtils;
import io.github.thebusybiscuit.cscorelib2.item.CustomItem;
import io.github.thebusybiscuit.cscorelib2.recipes.MinecraftRecipe;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
import io.github.thebusybiscuit.slimefun4.api.player.PlayerProfile;
import io.github.thebusybiscuit.slimefun4.core.attributes.RecipeDisplayItem;
import io.github.thebusybiscuit.slimefun4.core.categories.FlexCategory;
@@ -68,18 +67,12 @@ public class ChestSlimefunGuide implements SlimefunGuideImplementation {
private final ItemStack item;
private final int[] recipeSlots = { 3, 4, 5, 12, 13, 14, 21, 22, 23 };
- private final Sound sound;
+ private final Sound sound = Sound.ITEM_BOOK_PAGE_TURN;
private final boolean showVanillaRecipes;
public ChestSlimefunGuide(boolean vanillaRecipes) {
showVanillaRecipes = vanillaRecipes;
item = new SlimefunGuideItem(this, "&aSlimefun Guide &7(Chest GUI)");
-
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- sound = Sound.ITEM_BOOK_PAGE_TURN;
- } else {
- sound = Sound.ENTITY_BAT_TAKEOFF;
- }
}
@Override
@@ -233,16 +226,22 @@ public class ChestSlimefunGuide implements SlimefunGuideImplementation {
menu.addItem(46, ChestMenuUtils.getPreviousButton(p, page, pages));
menu.addMenuClickHandler(46, (pl, slot, item, action) -> {
int next = page - 1;
- if (next != page && next > 0)
+
+ if (next != page && next > 0) {
openCategory(profile, category, next);
+ }
+
return false;
});
menu.addItem(52, ChestMenuUtils.getNextButton(p, page, pages));
menu.addMenuClickHandler(52, (pl, slot, item, action) -> {
int next = page + 1;
- if (next != page && next <= pages)
+
+ if (next != page && next <= pages) {
openCategory(profile, category, next);
+ }
+
return false;
});
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/altar/AncientPedestal.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/altar/AncientPedestal.java
index 62a0d6318..80cc207cd 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/altar/AncientPedestal.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/altar/AncientPedestal.java
@@ -2,6 +2,10 @@ package io.github.thebusybiscuit.slimefun4.implementation.items.altar;
import java.util.Optional;
+import javax.annotation.Nonnull;
+import javax.annotation.Nullable;
+import javax.annotation.ParametersAreNonnullByDefault;
+
import org.bukkit.ChatColor;
import org.bukkit.GameMode;
import org.bukkit.Location;
@@ -17,7 +21,9 @@ import org.bukkit.util.Vector;
import io.github.thebusybiscuit.cscorelib2.chat.ChatColors;
import io.github.thebusybiscuit.cscorelib2.inventory.ItemUtils;
import io.github.thebusybiscuit.cscorelib2.item.CustomItem;
+import io.github.thebusybiscuit.slimefun4.core.handlers.BlockDispenseHandler;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
+import io.github.thebusybiscuit.slimefun4.implementation.items.SimpleSlimefunItem;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.AncientAltarListener;
import io.github.thebusybiscuit.slimefun4.implementation.tasks.AncientAltarTask;
import io.github.thebusybiscuit.slimefun4.utils.SlimefunUtils;
@@ -39,14 +45,15 @@ import me.mrCookieSlime.Slimefun.api.SlimefunItemStack;
* @see AncientAltarTask
*
*/
-public class AncientPedestal extends SlimefunItem {
+public class AncientPedestal extends SimpleSlimefunItem {
public static final String ITEM_PREFIX = ChatColors.color("&dALTAR &3Probe - &e");
+ @ParametersAreNonnullByDefault
public AncientPedestal(Category category, SlimefunItemStack item, RecipeType recipeType, ItemStack[] recipe, ItemStack recipeOutput) {
super(category, item, recipeType, recipe, recipeOutput);
- SlimefunItem.registerBlockHandler(getID(), (p, b, tool, reason) -> {
+ SlimefunItem.registerBlockHandler(getId(), (p, b, tool, reason) -> {
Optional- entity = getPlacedItem(b);
if (entity.isPresent()) {
@@ -63,7 +70,13 @@ public class AncientPedestal extends SlimefunItem {
});
}
- public Optional
- getPlacedItem(Block pedestal) {
+ @Override
+ public BlockDispenseHandler getItemHandler() {
+ return (e, d, block, machine) -> e.setCancelled(true);
+ }
+
+ @Nonnull
+ public Optional
- getPlacedItem(@Nonnull Block pedestal) {
Location l = pedestal.getLocation().add(0.5, 1.2, 0.5);
for (Entity n : l.getWorld().getNearbyEntities(l, 0.5, 0.5, 0.5, this::testItem)) {
@@ -75,7 +88,7 @@ public class AncientPedestal extends SlimefunItem {
return Optional.empty();
}
- private boolean testItem(Entity n) {
+ private boolean testItem(@Nullable Entity n) {
if (n instanceof Item && n.isValid()) {
Item item = (Item) n;
ItemMeta meta = item.getItemStack().getItemMeta();
@@ -86,7 +99,8 @@ public class AncientPedestal extends SlimefunItem {
}
}
- public ItemStack getOriginalItemStack(Item item) {
+ @Nonnull
+ public ItemStack getOriginalItemStack(@Nonnull Item item) {
ItemStack stack = item.getItemStack().clone();
String customName = item.getCustomName();
@@ -108,7 +122,7 @@ public class AncientPedestal extends SlimefunItem {
return stack;
}
- public void placeItem(Player p, Block b) {
+ public void placeItem(@Nonnull Player p, @Nonnull Block b) {
ItemStack hand = p.getInventory().getItemInMainHand();
ItemStack displayItem = new CustomItem(hand, ITEM_PREFIX + System.nanoTime());
displayItem.setAmount(1);
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/AndroidInterface.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/AndroidInterface.java
new file mode 100644
index 000000000..2e745be60
--- /dev/null
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/AndroidInterface.java
@@ -0,0 +1,34 @@
+package io.github.thebusybiscuit.slimefun4.implementation.items.androids;
+
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import org.bukkit.inventory.ItemStack;
+
+import io.github.thebusybiscuit.slimefun4.core.handlers.BlockDispenseHandler;
+import io.github.thebusybiscuit.slimefun4.implementation.items.SimpleSlimefunItem;
+import me.mrCookieSlime.Slimefun.Lists.RecipeType;
+import me.mrCookieSlime.Slimefun.Objects.Category;
+import me.mrCookieSlime.Slimefun.api.SlimefunItemStack;
+
+/**
+ * The {@link AndroidInterface} are inventories used to interact with a {@link ProgrammableAndroid}.
+ * There are two variants of interfaces, fuel and items.
+ *
+ * @author TheBusyBiscuit
+ *
+ * @see ProgrammableAndroid
+ *
+ */
+public class AndroidInterface extends SimpleSlimefunItem {
+
+ @ParametersAreNonnullByDefault
+ public AndroidInterface(Category category, SlimefunItemStack item, RecipeType recipeType, ItemStack[] recipe) {
+ super(category, item, recipeType, recipe);
+ }
+
+ @Override
+ public BlockDispenseHandler getItemHandler() {
+ return (e, d, block, machine) -> e.setCancelled(true);
+ }
+
+}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FarmerAndroid.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FarmerAndroid.java
index 060bb6b81..e46721c84 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FarmerAndroid.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FarmerAndroid.java
@@ -10,8 +10,6 @@ import org.bukkit.block.data.Ageable;
import org.bukkit.block.data.BlockData;
import org.bukkit.inventory.ItemStack;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
-import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import me.mrCookieSlime.Slimefun.Lists.RecipeType;
import me.mrCookieSlime.Slimefun.Objects.Category;
import me.mrCookieSlime.Slimefun.api.SlimefunItemStack;
@@ -57,10 +55,6 @@ public class FarmerAndroid extends ProgrammableAndroid {
private ItemStack getDropFromCrop(Material crop) {
Random random = ThreadLocalRandom.current();
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14) && crop == Material.SWEET_BERRY_BUSH) {
- return new ItemStack(Material.SWEET_BERRIES, random.nextInt(3) + 1);
- }
-
switch (crop) {
case WHEAT:
return new ItemStack(Material.WHEAT, random.nextInt(2) + 1);
@@ -74,6 +68,8 @@ public class FarmerAndroid extends ProgrammableAndroid {
return new ItemStack(Material.COCOA_BEANS, random.nextInt(3) + 1);
case NETHER_WART:
return new ItemStack(Material.NETHER_WART, random.nextInt(3) + 1);
+ case SWEET_BERRY_BUSH:
+ return new ItemStack(Material.SWEET_BERRIES, random.nextInt(3) + 1);
default:
return null;
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FisherAndroid.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FisherAndroid.java
index 085895521..de83525a7 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FisherAndroid.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/FisherAndroid.java
@@ -4,14 +4,12 @@ import java.util.concurrent.ThreadLocalRandom;
import org.bukkit.Material;
import org.bukkit.Sound;
+import org.bukkit.Tag;
import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.inventory.ItemStack;
import io.github.thebusybiscuit.cscorelib2.collections.RandomizedSet;
-import io.github.thebusybiscuit.cscorelib2.materials.MaterialCollections;
-import io.github.thebusybiscuit.slimefun4.api.MinecraftVersion;
-import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import me.mrCookieSlime.Slimefun.Lists.RecipeType;
import me.mrCookieSlime.Slimefun.Objects.Category;
import me.mrCookieSlime.Slimefun.api.SlimefunItemStack;
@@ -25,7 +23,7 @@ public class FisherAndroid extends ProgrammableAndroid {
super(category, tier, item, recipeType, recipe);
// Fish
- for (Material fish : MaterialCollections.getAllFishItems()) {
+ for (Material fish : Tag.ITEMS_FISHES.getValues()) {
fishingLoot.add(new ItemStack(fish), 25);
}
@@ -37,10 +35,7 @@ public class FisherAndroid extends ProgrammableAndroid {
fishingLoot.add(new ItemStack(Material.STICK), 5);
fishingLoot.add(new ItemStack(Material.ROTTEN_FLESH), 3);
fishingLoot.add(new ItemStack(Material.LEATHER), 2);
-
- if (SlimefunPlugin.getMinecraftVersion().isAtLeast(MinecraftVersion.MINECRAFT_1_14)) {
- fishingLoot.add(new ItemStack(Material.BAMBOO), 3);
- }
+ fishingLoot.add(new ItemStack(Material.BAMBOO), 3);
// "loot"
fishingLoot.add(new ItemStack(Material.SADDLE), 1);
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Instruction.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Instruction.java
index e80029472..4a2083b05 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Instruction.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Instruction.java
@@ -146,18 +146,18 @@ enum Instruction {
});
private static final Map nameLookup = new HashMap<>();
- public static final Instruction[] values = values();
+ public static final Instruction[] valuesCache = values();
+
+ static {
+ for (Instruction instruction : valuesCache) {
+ nameLookup.put(instruction.name(), instruction);
+ }
+ }
private final ItemStack item;
private final AndroidType type;
private final AndroidAction method;
- static {
- for (Instruction instruction : values) {
- nameLookup.put(instruction.name(), instruction);
- }
- }
-
@ParametersAreNonnullByDefault
Instruction(AndroidType type, HeadTexture head, @Nullable AndroidAction method) {
this.type = type;
@@ -198,7 +198,7 @@ enum Instruction {
* @return The {@link Instruction} or null if it does not exist.
*/
@Nullable
- public static Instruction getFromCache(@Nonnull String value) {
+ public static Instruction getInstruction(@Nonnull String value) {
Validate.notNull(value, "An Instruction cannot be null!");
return nameLookup.get(value);
}
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/MinerAndroid.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/MinerAndroid.java
index f082b68f5..4328e6c0e 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/MinerAndroid.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/MinerAndroid.java
@@ -11,10 +11,10 @@ import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.inventory.ItemStack;
-import io.github.thebusybiscuit.cscorelib2.materials.MaterialCollections;
import io.github.thebusybiscuit.cscorelib2.protection.ProtectableAction;
import io.github.thebusybiscuit.slimefun4.api.events.AndroidMineEvent;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
+import io.github.thebusybiscuit.slimefun4.utils.tags.SlimefunTag;
import me.mrCookieSlime.Slimefun.Lists.RecipeType;
import me.mrCookieSlime.Slimefun.Objects.Category;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.SlimefunItem;
@@ -40,7 +40,7 @@ public class MinerAndroid extends ProgrammableAndroid {
protected void dig(Block b, BlockMenu menu, Block block) {
Collection drops = block.getDrops(effectivePickaxe);
- if (!MaterialCollections.getAllUnbreakableBlocks().contains(block.getType()) && !drops.isEmpty()) {
+ if (!SlimefunTag.UNBREAKABLE_MATERIALS.isTagged(block.getType()) && !drops.isEmpty()) {
OfflinePlayer owner = Bukkit.getOfflinePlayer(UUID.fromString(BlockStorage.getLocationInfo(b.getLocation(), "owner")));
if (SlimefunPlugin.getProtectionManager().hasPermission(owner, block.getLocation(), ProtectableAction.BREAK_BLOCK)) {
@@ -71,7 +71,7 @@ public class MinerAndroid extends ProgrammableAndroid {
protected void moveAndDig(Block b, BlockMenu menu, BlockFace face, Block block) {
Collection drops = block.getDrops(effectivePickaxe);
- if (!MaterialCollections.getAllUnbreakableBlocks().contains(block.getType()) && !drops.isEmpty()) {
+ if (!SlimefunTag.UNBREAKABLE_MATERIALS.isTagged(block.getType()) && !drops.isEmpty()) {
OfflinePlayer owner = Bukkit.getOfflinePlayer(UUID.fromString(BlockStorage.getLocationInfo(b.getLocation(), "owner")));
if (SlimefunPlugin.getProtectionManager().hasPermission(owner, block.getLocation(), ProtectableAction.BREAK_BLOCK)) {
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/ProgrammableAndroid.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/ProgrammableAndroid.java
index be15a49e3..b57b449e4 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/ProgrammableAndroid.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/ProgrammableAndroid.java
@@ -81,7 +81,7 @@ public class ProgrammableAndroid extends SlimefunItem implements InventoryBlock,
texture = item.getSkullTexture().orElse(null);
registerDefaultFuelTypes();
- new BlockMenuPreset(getID(), "Programmable Android") {
+ new BlockMenuPreset(getId(), "Programmable Android") {
@Override
public void init() {
@@ -131,7 +131,7 @@ public class ProgrammableAndroid extends SlimefunItem implements InventoryBlock,
}
};
- registerBlockHandler(getID(), (p, b, stack, reason) -> {
+ registerBlockHandler(getId(), (p, b, stack, reason) -> {
boolean allow = reason == UnregisterReason.PLAYER_BREAK && (BlockStorage.getLocationInfo(b.getLocation(), "owner").equals(p.getUniqueId().toString()) || p.hasPermission("slimefun.android.bypass"));
if (allow) {
@@ -257,7 +257,7 @@ public class ProgrammableAndroid extends SlimefunItem implements InventoryBlock,
return false;
});
} else {
- Instruction instruction = Instruction.getFromCache(script[i]);
+ Instruction instruction = Instruction.getInstruction(script[i]);
if (instruction == null) {
SlimefunPlugin.instance().getLogger().log(Level.WARNING, "Failed to parse Android instruction: {0}, maybe your server is out of date?", script[i]);
@@ -493,7 +493,7 @@ public class ProgrammableAndroid extends SlimefunItem implements InventoryBlock,
protected List getValidScriptInstructions() {
List list = new ArrayList<>();
- for (Instruction part : Instruction.values) {
+ for (Instruction part : Instruction.valuesCache) {
if (part == Instruction.START || part == Instruction.REPEAT) {
continue;
}
@@ -646,7 +646,7 @@ public class ProgrammableAndroid extends SlimefunItem implements InventoryBlock,
}
BlockStorage.addBlockInfo(b, "fuel", String.valueOf(fuel - 1));
- Instruction instruction = Instruction.getFromCache(script[index]);
+ Instruction instruction = Instruction.getInstruction(script[index]);
if (instruction == null) {
SlimefunPlugin.instance().getLogger().log(Level.WARNING, "Failed to parse Android instruction: {0}, maybe your server is out of date?", script[index]);
diff --git a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Script.java b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Script.java
index 2b623dbc5..5d97975f7 100644
--- a/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Script.java
+++ b/src/main/java/io/github/thebusybiscuit/slimefun4/implementation/items/androids/Script.java
@@ -9,6 +9,9 @@ import java.util.List;
import java.util.UUID;
import java.util.logging.Level;
+import javax.annotation.Nonnull;
+import javax.annotation.ParametersAreNonnullByDefault;
+
import org.apache.commons.lang.Validate;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
@@ -22,6 +25,12 @@ import io.github.thebusybiscuit.slimefun4.utils.ChatUtils;
import io.github.thebusybiscuit.slimefun4.utils.NumberUtils;
import me.mrCookieSlime.Slimefun.api.Slimefun;
+/**
+ * A {@link Script} represents runnable code for a {@link ProgrammableAndroid}.
+ *
+ * @author TheBusyBiscuit
+ *
+ */
public final class Script {
private final Config config;
@@ -29,7 +38,13 @@ public final class Script {
private final String author;
private final String code;
- private Script(Config config) {
+ /**
+ * This constructs a new {@link Script} from the given {@link Config}.
+ *
+ * @param config
+ * The {@link Config}
+ */
+ private Script(@Nonnull Config config) {
Validate.notNull(config);
this.config = config;
@@ -52,6 +67,7 @@ public final class Script {
*
* @return The name
*/
+ @Nonnull
public String getName() {
return name;
}
@@ -62,6 +78,7 @@ public final class Script {
*
* @return The author of this {@link Script}
*/
+ @Nonnull
public String getAuthor() {
return author;
}
@@ -73,6 +90,7 @@ public final class Script {
*
* @return The code for this {@link Script}
*/
+ @Nonnull
public String getSourceCode() {
return code;
}
@@ -86,7 +104,7 @@ public final class Script {
*
* @return Whether the given {@link OfflinePlayer} is the author of this {@link Script}.
*/
- public boolean isAuthor(OfflinePlayer p) {
+ public boolean isAuthor(@Nonnull OfflinePlayer p) {
return p.getUniqueId().equals(config.getUUID("author"));
}
@@ -99,7 +117,7 @@ public final class Script {
*
* @return Whether the given {@link Player} is able to rate this {@link Script}
*/
- public boolean canRate(Player p) {
+ public boolean canRate(@Nonnull Player p) {
if (isAuthor(p)) {
return false;
}
@@ -109,7 +127,8 @@ public final class Script {
return !upvoters.contains(p.getUniqueId().toString()) && !downvoters.contains(p.getUniqueId().toString());
}
- ItemStack getAsItemStack(ProgrammableAndroid android, Player p) {
+ @Nonnull
+ ItemStack getAsItemStack(@Nonnull ProgrammableAndroid android, @Nonnull Player p) {
List lore = new LinkedList<>();
lore.add("&7by &r" + getAuthor());
lore.add("");
@@ -128,6 +147,7 @@ public final class Script {
return new CustomItem(android.getItem(), "&b" + getName(), lore.toArray(new String[0]));
}
+ @Nonnull
private String getScriptRatingPercentage() {
float percentage = getRating();
return NumberUtils.getColorFromPercentage(percentage) + String.valueOf(percentage) + ChatColor.RESET + "% ";
@@ -181,7 +201,7 @@ public final class Script {
config.save();
}
- public void rate(Player p, boolean positive) {
+ public void rate(@Nonnull Player p, boolean positive) {
config.reload();
String path = "rating." + (positive ? "positive" : "negative");
@@ -192,7 +212,8 @@ public final class Script {
config.save();
}
- public static List