1
mirror of https://github.com/StarWishsama/Slimefun4.git synced 2024-09-20 03:35:51 +00:00
into experimental

Conflicts:
	CHANGELOG.md
This commit is contained in:
TheBusyBiscuit 2020-07-25 14:27:12 +02:00
commit 92ca696140
17 changed files with 509 additions and 383 deletions

View File

@ -7,24 +7,46 @@ assignees: ''
--- ---
## Description (Required) <!-- FILL IN THE FORM BELOW -->
<!-- A clear and detailed description of what exactly the Issue consists of. -->
## Steps to reproduce the Issue (Required) ## Description (REQUIRED)
<!-- A clear and detailed description of what went wrong. -->
<!-- The more information you can provide, the easier we can handle this problem. -->
<!-- Start writing below this line -->
## Steps to reproduce the Issue (REQUIRED)
<!-- Tell us the exact steps to reproduce this issue, the more detailed the easier we can reproduce it. -->
<!-- Youtube Videos and Screenshots are recommended! --> <!-- Youtube Videos and Screenshots are recommended! -->
<!-- Start writing below this line -->
## Expected behavior (Required)
<!-- What did you expect to happen? -->
## Server Log / Error Report ## Expected behavior (REQUIRED)
<!-- Take a look at your Server Log and please provide any error reports you can find via https://pastebin.com/ --> <!-- What were you expecting to happen? -->
<!-- We may discard your Issue if you just post it here, as it's unreadable for us. Please use Pastebin! --> <!-- What do you think would have been the correct behaviour? -->
<!-- Start writing below this line -->
## Environment (Required)
<!-- We may also close your Issue if you are not providing the exact version numbers. --> ## Server Log
<!-- Take a look at your Server Log and post any errors you can find via https://pastebin.com/ -->
<!-- If you are unsure about it, post your full log, you can find it under /logs/latest.log -->
<!-- Start writing below this line -->
## Error Reports
<!-- Check the folder /plugins/Slimefun/error-reports/ and upload all files inside that folder. -->
<!-- You can also post these files via https://pastebin.com/ -->
<!-- Start writing below this line -->
## Environment (REQUIRED)
<!-- Any info without the exact version numbers will be closed! -->
<!-- "latest" IS NOT A VERSION NUMBER. --> <!-- "latest" IS NOT A VERSION NUMBER. -->
<!-- You can also just run "/sf versions" and show us a screenshot of that. --> <!-- We recommend running "/sf versions" and showing us a screenshot of that. -->
<!-- Make sure that the screenshot covers the entire output of that command. -->
<!-- If your issue is related to other plugins, make sure to include the versions of these plugins too! -->
- Server Software (Spigot/Paper):
- Minecraft Version: - Minecraft Version:
- Slimefun Version: - Slimefun Version:
- CS-CoreLib Version: - CS-CoreLib Version:

View File

@ -27,6 +27,7 @@
* Added a [Metrics module](https://github.com/Slimefun/MetricsModule) which allows us to release updates to metrics (bStats) independently from the main plugin * Added a [Metrics module](https://github.com/Slimefun/MetricsModule) which allows us to release updates to metrics (bStats) independently from the main plugin
* Added "Compressed Carbon -> Carbon" recipe to the Ore Crusher * Added "Compressed Carbon -> Carbon" recipe to the Ore Crusher
* Added "Carbon -> Coal" recipe to the Ore Crusher * Added "Carbon -> Coal" recipe to the Ore Crusher
* Added an option to disable the message "Ignoring duplicate block"
* Added Iron Golem Assembler * Added Iron Golem Assembler
* Added Reinforced Cloth * Added Reinforced Cloth
* Added Bee protection to Hazmat Suit * Added Bee protection to Hazmat Suit
@ -51,6 +52,7 @@
* Fixed #2093 * Fixed #2093
* Fixed #2086 * Fixed #2086
* Fixed #1894 * Fixed #1894
* Fixed #2097
## Release Candidate 14 (12 Jul 2020) ## Release Candidate 14 (12 Jul 2020)

View File

@ -64,10 +64,11 @@ public class SlimefunRegistry {
private boolean enableResearches; private boolean enableResearches;
private boolean freeCreativeResearches; private boolean freeCreativeResearches;
private boolean researchFireworks; private boolean researchFireworks;
private boolean logDuplicateBlockEntries;
private final Set<String> tickers = new HashSet<>(); private final Set<String> tickers = new HashSet<>();
private final Set<SlimefunItem> radioactive = new HashSet<>(); private final Set<SlimefunItem> radioactive = new HashSet<>();
private final Set<String> activeChunks = new HashSet<>(); private final Set<String> activeChunks = ConcurrentHashMap.newKeySet();
private final KeyMap<GEOResource> geoResources = new KeyMap<>(); private final KeyMap<GEOResource> geoResources = new KeyMap<>();
@ -82,7 +83,7 @@ public class SlimefunRegistry {
private final Map<Class<? extends ItemHandler>, Set<ItemHandler>> globalItemHandlers = new HashMap<>(); private final Map<Class<? extends ItemHandler>, Set<ItemHandler>> globalItemHandlers = new HashMap<>();
private final Map<String, SlimefunBlockHandler> blockHandlers = new HashMap<>(); private final Map<String, SlimefunBlockHandler> blockHandlers = new HashMap<>();
private final Map<String, Set<Location>> activeTickers = new HashMap<>(); private final Map<String, Set<Location>> activeTickers = new ConcurrentHashMap<>();
private final Map<String, ItemStack> automatedCraftingChamberRecipes = new HashMap<>(); private final Map<String, ItemStack> automatedCraftingChamberRecipes = new HashMap<>();
@ -98,6 +99,7 @@ public class SlimefunRegistry {
backwardsCompatibility = cfg.getBoolean("options.backwards-compatibility") || SlimefunPlugin.getMinecraftVersion().isBefore(MinecraftVersion.MINECRAFT_1_14); backwardsCompatibility = cfg.getBoolean("options.backwards-compatibility") || SlimefunPlugin.getMinecraftVersion().isBefore(MinecraftVersion.MINECRAFT_1_14);
freeCreativeResearches = cfg.getBoolean("researches.free-in-creative-mode"); freeCreativeResearches = cfg.getBoolean("researches.free-in-creative-mode");
researchFireworks = cfg.getBoolean("researches.enable-fireworks"); researchFireworks = cfg.getBoolean("researches.enable-fireworks");
logDuplicateBlockEntries = cfg.getBoolean("options.log-duplicate-block-entries");
} }
/** /**
@ -265,4 +267,8 @@ public class SlimefunRegistry {
return automatedCraftingChamberRecipes; return automatedCraftingChamberRecipes;
} }
public boolean logDuplicateBlockEntries() {
return logDuplicateBlockEntries;
}
} }

View File

@ -36,13 +36,15 @@ class VersionsCommand extends SubCommand {
// After all these years... Spigot still displays as "CraftBukkit" // After all these years... Spigot still displays as "CraftBukkit"
// so we will just fix this inconsistency for them :) // so we will just fix this inconsistency for them :)
String serverSoftware = PaperLib.isSpigot() && !PaperLib.isPaper() ? "Spigot" : Bukkit.getName(); String serverSoftware = PaperLib.isSpigot() && !PaperLib.isPaper() ? "Spigot" : Bukkit.getName();
sender.sendMessage(ChatColors.color("&a" + serverSoftware + " &2" + ReflectionUtils.getVersion())); sender.sendMessage(ChatColors.color("&a" + serverSoftware + " &2" + ReflectionUtils.getVersion()));
sender.sendMessage(""); sender.sendMessage("");
sender.sendMessage(ChatColors.color("&aCS-CoreLib &2v" + SlimefunPlugin.getCSCoreLibVersion())); sender.sendMessage(ChatColors.color("&aCS-CoreLib &2v" + SlimefunPlugin.getCSCoreLibVersion()));
sender.sendMessage(ChatColors.color("&aSlimefun &2v" + SlimefunPlugin.getVersion())); sender.sendMessage(ChatColors.color("&aSlimefun &2v" + SlimefunPlugin.getVersion()));
if (SlimefunPlugin.getMetricsService().getVersion() != null) if (SlimefunPlugin.getMetricsService().getVersion() != null) {
sender.sendMessage(ChatColors.color("&aMetrics: &2#" + SlimefunPlugin.getMetricsService().getVersion() + ')')); sender.sendMessage(ChatColors.color("&aMetrics build: &2#" + SlimefunPlugin.getMetricsService().getVersion()));
}
if (SlimefunPlugin.getRegistry().isBackwardsCompatible()) { if (SlimefunPlugin.getRegistry().isBackwardsCompatible()) {
sender.sendMessage(ChatColor.YELLOW + "Backwards compatibility enabled!"); sender.sendMessage(ChatColor.YELLOW + "Backwards compatibility enabled!");

View File

@ -13,6 +13,7 @@ import java.util.logging.Level;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin; import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import io.github.thebusybiscuit.slimefun4.utils.PatternUtils; import io.github.thebusybiscuit.slimefun4.utils.PatternUtils;
import kong.unirest.GetRequest;
import kong.unirest.HttpResponse; import kong.unirest.HttpResponse;
import kong.unirest.JsonNode; import kong.unirest.JsonNode;
import kong.unirest.Unirest; import kong.unirest.Unirest;
@ -79,16 +80,14 @@ public class MetricsService {
try { try {
// Load the jar file into a child class loader using the SF PluginClassLoader // Load the jar file into a child class loader using the SF PluginClassLoader
// as a parent. // as a parent.
moduleClassLoader = URLClassLoader.newInstance(new URL[] { metricsModuleFile.toURI().toURL() }, moduleClassLoader = URLClassLoader.newInstance(new URL[] { metricsModuleFile.toURI().toURL() }, plugin.getClass().getClassLoader());
plugin.getClass().getClassLoader()); Class<?> metricsClass = moduleClassLoader.loadClass("dev.walshy.sfmetrics.MetricsModule");
Class<?> cl = moduleClassLoader.loadClass("dev.walshy.sfmetrics.MetricsModule");
metricVersion = cl.getPackage().getImplementationVersion(); metricVersion = metricsClass.getPackage().getImplementationVersion();
// If it has not been newly downloaded, auto-updates are on AND there's a new version // If it has not been newly downloaded, auto-updates are on AND there's a new version
// then cleanup, download and start // then cleanup, download and start
if (!hasDownloadedUpdate && hasAutoUpdates() && checkForUpdate(metricVersion) if (!hasDownloadedUpdate && hasAutoUpdates() && checkForUpdate(metricVersion)) {
) {
plugin.getLogger().info("Cleaning up and re-loading Metrics."); plugin.getLogger().info("Cleaning up and re-loading Metrics.");
cleanUp(); cleanUp();
start(); start();
@ -96,21 +95,22 @@ public class MetricsService {
} }
// Finally, we're good to start this. // Finally, we're good to start this.
Method start = cl.getDeclaredMethod("start"); Method start = metricsClass.getDeclaredMethod("start");
String version = cl.getPackage().getImplementationVersion(); String version = metricsClass.getPackage().getImplementationVersion();
// This is required to be sync due to bStats. // This is required to be sync due to bStats.
Slimefun.runSync(() -> { Slimefun.runSync(() -> {
try { try {
start.invoke(null); start.invoke(null);
plugin.getLogger().info("Metrics build #" + version + " started."); plugin.getLogger().info("Metrics build #" + version + " started.");
} catch (Exception e) { }
catch (Exception | LinkageError e) {
plugin.getLogger().log(Level.WARNING, "Failed to start metrics.", e); plugin.getLogger().log(Level.WARNING, "Failed to start metrics.", e);
} }
}); });
} catch (Exception e) { }
plugin.getLogger().log(Level.WARNING, catch (Exception | LinkageError e) {
"Failed to load the metrics module. Maybe the jar is corrupt?", e); plugin.getLogger().log(Level.WARNING, "Failed to load the metrics module. Maybe the jar is corrupt?", e);
} }
} }
@ -123,9 +123,9 @@ public class MetricsService {
if (this.moduleClassLoader != null) { if (this.moduleClassLoader != null) {
this.moduleClassLoader.close(); this.moduleClassLoader.close();
} }
} catch (IOException e) { }
plugin.getLogger().log(Level.WARNING, catch (IOException e) {
"Could not clean up module class loader. Some memory may have been leaked."); plugin.getLogger().log(Level.WARNING, "Could not clean up module class loader. Some memory may have been leaked.");
} }
} }
@ -133,7 +133,8 @@ public class MetricsService {
* Checks for a new update and compares it against the current version. * Checks for a new update and compares it against the current version.
* If there is a new version available then this returns true. * If there is a new version available then this returns true.
* *
* @param currentVersion The current version which is being used. * @param currentVersion
* The current version which is being used.
* @return True if there is an update available. * @return True if there is an update available.
*/ */
public boolean checkForUpdate(String currentVersion) { public boolean checkForUpdate(String currentVersion) {
@ -160,16 +161,21 @@ public class MetricsService {
*/ */
private int getLatestVersion() { private int getLatestVersion() {
try { try {
HttpResponse<JsonNode> response = Unirest.get(GH_API + "/releases/latest") HttpResponse<JsonNode> response = Unirest.get(GH_API + "/releases/latest").asJson();
.asJson();
if (!response.isSuccess()) return -1; if (!response.isSuccess()) {
return -1;
}
JsonNode node = response.getBody(); JsonNode node = response.getBody();
if (node == null) return -1; if (node == null) {
return -1;
}
return node.getObject().getInt("tag_name"); return node.getObject().getInt("tag_name");
} catch (UnirestException e) { }
catch (UnirestException e) {
plugin.getLogger().log(Level.SEVERE, "Failed to fetch latest builds for SFMetrics"); plugin.getLogger().log(Level.SEVERE, "Failed to fetch latest builds for SFMetrics");
return -1; return -1;
} }
@ -178,7 +184,8 @@ public class MetricsService {
/** /**
* Downloads the version specified to Slimefun's data folder. * Downloads the version specified to Slimefun's data folder.
* *
* @param version The version to download. * @param version
* The version to download.
*/ */
private boolean download(int version) { private boolean download(int version) {
File f = new File(parentFolder, "Metrics-" + version + ".jar"); File f = new File(parentFolder, "Metrics-" + version + ".jar");
@ -187,18 +194,17 @@ public class MetricsService {
plugin.getLogger().log(Level.INFO, "# Starting download of MetricsModule build: #{0}", version); plugin.getLogger().log(Level.INFO, "# Starting download of MetricsModule build: #{0}", version);
AtomicInteger lastPercentPosted = new AtomicInteger(); AtomicInteger lastPercentPosted = new AtomicInteger();
HttpResponse<File> response = Unirest.get(GH_RELEASES + "/" + version GetRequest request = Unirest.get(GH_RELEASES + "/" + version + "/" + REPO_NAME + ".jar");
+ "/" + REPO_NAME + ".jar")
.downloadMonitor((b, fileName, bytesWritten, totalBytes) -> { HttpResponse<File> response = request.downloadMonitor((b, fileName, bytesWritten, totalBytes) -> {
int percent = (int) (20 * (Math.round((((double) bytesWritten / totalBytes) * 100) / 20))); int percent = (int) (20 * (Math.round((((double) bytesWritten / totalBytes) * 100) / 20)));
if (percent != 0 && percent != lastPercentPosted.get()) { if (percent != 0 && percent != lastPercentPosted.get()) {
plugin.getLogger().info("# Downloading... " + percent + "% " + plugin.getLogger().info("# Downloading... " + percent + "% " + "(" + bytesWritten + "/" + totalBytes + " bytes)");
"(" + bytesWritten + "/" + totalBytes + " bytes)");
lastPercentPosted.set(percent); lastPercentPosted.set(percent);
} }
}) }).asFile(f.getPath());
.asFile(f.getPath());
if (response.isSuccess()) { if (response.isSuccess()) {
plugin.getLogger().log(Level.INFO, "Successfully downloaded {0} build: #{1}", new Object[] { REPO_NAME, version }); plugin.getLogger().log(Level.INFO, "Successfully downloaded {0} build: #{1}", new Object[] { REPO_NAME, version });
@ -209,12 +215,12 @@ public class MetricsService {
hasDownloadedUpdate = true; hasDownloadedUpdate = true;
return true; return true;
} }
} catch (UnirestException e) { }
plugin.getLogger().log(Level.WARNING, "Failed to fetch the latest jar file from the" + catch (UnirestException e) {
" 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.");
} catch (IOException e) { }
plugin.getLogger().log(Level.WARNING, "Failed to replace the old metric file with the " + catch (IOException e) {
"new one. Please do this manually! Error: {0}", e.getMessage()); plugin.getLogger().log(Level.WARNING, "Failed to replace the old metric file with the " + "new one. Please do this manually! Error: {0}", e.getMessage());
} }
return false; return false;
} }

View File

@ -54,7 +54,7 @@ abstract class GitHubConnector {
writeCacheFile(resp.getBody()); writeCacheFile(resp.getBody());
} }
else { else {
Slimefun.getLogger().log(Level.WARNING, "Failed to fetch {0}", repository + getURLSuffix()); Slimefun.getLogger().log(Level.WARNING, "Failed to fetch {0}: {1} - {2}", new Object[] {repository + getURLSuffix(), resp.getStatus(), resp.getBody()});
} }
} }
catch (UnirestException e) { catch (UnirestException e) {
@ -78,21 +78,21 @@ abstract class GitHubConnector {
} }
private JsonNode readCacheFile() { private JsonNode readCacheFile() {
try (BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(file), StandardCharsets.UTF_8))) { try (BufferedReader reader = new BufferedReader(new InputStreamReader(new FileInputStream(file), StandardCharsets.UTF_8))) {
return new JsonNode(br.readLine()); return new JsonNode(reader.readLine());
} }
catch (IOException | JSONException e) { catch (IOException | JSONException e) {
Slimefun.getLogger().log(Level.WARNING, "Failed to read Github cache file: {0}", file.getName()); Slimefun.getLogger().log(Level.WARNING, "Failed to read Github cache file: {0} - {1}: {2}", new Object[] {file.getName(), e.getClass().getSimpleName(), e.getMessage()});
return null; return null;
} }
} }
private void writeCacheFile(JsonNode node) { private void writeCacheFile(JsonNode node) {
try (FileOutputStream fos = new FileOutputStream(file)) { try (FileOutputStream output = new FileOutputStream(file)) {
fos.write(node.toString().getBytes(StandardCharsets.UTF_8)); output.write(node.toString().getBytes(StandardCharsets.UTF_8));
} }
catch (IOException e) { catch (IOException e) {
Slimefun.getLogger().log(Level.WARNING, "Failed to populate GitHub cache"); Slimefun.getLogger().log(Level.WARNING, "Failed to populate GitHub cache: {0} - {1}", new Object[] {e.getClass().getSimpleName(), e.getMessage()});
} }
} }
} }

View File

@ -36,12 +36,12 @@ import io.github.thebusybiscuit.slimefun4.core.services.BlockDataService;
import io.github.thebusybiscuit.slimefun4.core.services.CustomItemDataService; import io.github.thebusybiscuit.slimefun4.core.services.CustomItemDataService;
import io.github.thebusybiscuit.slimefun4.core.services.CustomTextureService; import io.github.thebusybiscuit.slimefun4.core.services.CustomTextureService;
import io.github.thebusybiscuit.slimefun4.core.services.LocalizationService; import io.github.thebusybiscuit.slimefun4.core.services.LocalizationService;
import io.github.thebusybiscuit.slimefun4.core.services.MetricsService;
import io.github.thebusybiscuit.slimefun4.core.services.MinecraftRecipeService; import io.github.thebusybiscuit.slimefun4.core.services.MinecraftRecipeService;
import io.github.thebusybiscuit.slimefun4.core.services.PerWorldSettingsService; import io.github.thebusybiscuit.slimefun4.core.services.PerWorldSettingsService;
import io.github.thebusybiscuit.slimefun4.core.services.PermissionsService; import io.github.thebusybiscuit.slimefun4.core.services.PermissionsService;
import io.github.thebusybiscuit.slimefun4.core.services.UpdaterService; import io.github.thebusybiscuit.slimefun4.core.services.UpdaterService;
import io.github.thebusybiscuit.slimefun4.core.services.github.GitHubService; import io.github.thebusybiscuit.slimefun4.core.services.github.GitHubService;
import io.github.thebusybiscuit.slimefun4.core.services.MetricsService;
import io.github.thebusybiscuit.slimefun4.core.services.plugins.ThirdPartyPluginService; import io.github.thebusybiscuit.slimefun4.core.services.plugins.ThirdPartyPluginService;
import io.github.thebusybiscuit.slimefun4.core.services.profiler.SlimefunProfiler; import io.github.thebusybiscuit.slimefun4.core.services.profiler.SlimefunProfiler;
import io.github.thebusybiscuit.slimefun4.implementation.items.altar.AncientAltar; import io.github.thebusybiscuit.slimefun4.implementation.items.altar.AncientAltar;
@ -69,6 +69,7 @@ import io.github.thebusybiscuit.slimefun4.implementation.listeners.IronGolemList
import io.github.thebusybiscuit.slimefun4.implementation.listeners.ItemPickupListener; import io.github.thebusybiscuit.slimefun4.implementation.listeners.ItemPickupListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.MobDropListener; import io.github.thebusybiscuit.slimefun4.implementation.listeners.MobDropListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.MultiBlockListener; import io.github.thebusybiscuit.slimefun4.implementation.listeners.MultiBlockListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.PiglinListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.PlayerInteractEntityListener; import io.github.thebusybiscuit.slimefun4.implementation.listeners.PlayerInteractEntityListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.PlayerProfileListener; import io.github.thebusybiscuit.slimefun4.implementation.listeners.PlayerProfileListener;
import io.github.thebusybiscuit.slimefun4.implementation.listeners.SeismicAxeListener; import io.github.thebusybiscuit.slimefun4.implementation.listeners.SeismicAxeListener;
@ -431,12 +432,15 @@ public final class SlimefunPlugin extends JavaPlugin implements SlimefunAddon {
new WitherListener(this); new WitherListener(this);
new IronGolemListener(this); new IronGolemListener(this);
new PlayerInteractEntityListener(this); new PlayerInteractEntityListener(this);
new MobDropListener(this);
if (minecraftVersion.isAtLeast(MinecraftVersion.MINECRAFT_1_15)) { if (minecraftVersion.isAtLeast(MinecraftVersion.MINECRAFT_1_15)) {
new BeeListener(this); new BeeListener(this);
} }
new MobDropListener(this); if (minecraftVersion.isAtLeast(MinecraftVersion.MINECRAFT_1_16)) {
new PiglinListener(this);
}
// Item-specific Listeners // Item-specific Listeners
new VampireBladeListener(this, (VampireBlade) SlimefunItems.BLADE_OF_VAMPIRES.getItem()); new VampireBladeListener(this, (VampireBlade) SlimefunItems.BLADE_OF_VAMPIRES.getItem());

View File

@ -21,9 +21,9 @@ import org.bukkit.inventory.ItemStack;
import io.github.thebusybiscuit.slimefun4.core.handlers.ItemDropHandler; import io.github.thebusybiscuit.slimefun4.core.handlers.ItemDropHandler;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin; import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import io.github.thebusybiscuit.slimefun4.implementation.items.SimpleSlimefunItem;
import me.mrCookieSlime.Slimefun.Lists.RecipeType; import me.mrCookieSlime.Slimefun.Lists.RecipeType;
import me.mrCookieSlime.Slimefun.Objects.Category; import me.mrCookieSlime.Slimefun.Objects.Category;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.SimpleSlimefunItem;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.SlimefunItem; import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.SlimefunItem;
import me.mrCookieSlime.Slimefun.api.Slimefun; import me.mrCookieSlime.Slimefun.api.Slimefun;
import me.mrCookieSlime.Slimefun.api.SlimefunItemStack; import me.mrCookieSlime.Slimefun.api.SlimefunItemStack;

View File

@ -0,0 +1,62 @@
package io.github.thebusybiscuit.slimefun4.implementation.listeners;
import io.github.thebusybiscuit.slimefun4.implementation.SlimefunPlugin;
import me.mrCookieSlime.Slimefun.Objects.SlimefunItem.SlimefunItem;
import org.bukkit.Material;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.Item;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.entity.EntityPickupItemEvent;
import org.bukkit.event.entity.EntityTargetEvent;
import org.bukkit.event.player.PlayerInteractAtEntityEvent;
import org.bukkit.event.player.PlayerInteractEntityEvent;
import org.bukkit.inventory.EquipmentSlot;
import org.bukkit.inventory.ItemStack;
/**
* Listens to "Piglin trading events" to prevent trading with Slimefun items.
*
* @author poma123
*/
public class PiglinListener implements Listener {
public PiglinListener(SlimefunPlugin plugin) {
plugin.getServer().getPluginManager().registerEvents(this, plugin);
}
@EventHandler
public void onEntityPickup(EntityPickupItemEvent e) {
if (e.getEntityType() == EntityType.PIGLIN) {
if (SlimefunItem.getByItem(e.getItem().getItemStack()) != null) {
e.setCancelled(true);
}
}
}
@EventHandler
public void onInteractEntity(PlayerInteractEntityEvent e) {
if (!e.getRightClicked().isValid() || e.getRightClicked().getType() != EntityType.PIGLIN) {
return;
}
ItemStack itemStack;
if (e.getHand() == EquipmentSlot.OFF_HAND) {
itemStack = e.getPlayer().getInventory().getItemInOffHand();
} else {
itemStack = e.getPlayer().getInventory().getItemInMainHand();
}
if (itemStack.getType() != Material.GOLD_INGOT) {
return;
}
SlimefunItem sfItem = SlimefunItem.getByItem(itemStack);
if (sfItem != null) {
SlimefunPlugin.getLocalization().sendMessage(e.getPlayer(), "messages.piglin-barter", true);
e.setCancelled(true);
}
}
}

View File

@ -16,7 +16,6 @@ import java.util.logging.Level;
import java.util.logging.Logger; import java.util.logging.Logger;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.Chunk;
import org.bukkit.Location; import org.bukkit.Location;
import org.bukkit.World; import org.bukkit.World;
import org.bukkit.block.Block; import org.bukkit.block.Block;
@ -151,11 +150,35 @@ public class BlockStorage {
FileConfiguration cfg = YamlConfiguration.loadConfiguration(file); FileConfiguration cfg = YamlConfiguration.loadConfiguration(file);
for (String key : cfg.getKeys(false)) { for (String key : cfg.getKeys(false)) {
loadBlock(file, cfg, key);
totalBlocks++;
}
done++;
}
}
}
finally {
long time = (System.currentTimeMillis() - start);
Slimefun.getLogger().log(Level.INFO, "Loading Blocks... 100% (FINISHED - {0}ms)", time);
Slimefun.getLogger().log(Level.INFO, "Loaded a total of {0} Blocks for World \"{1}\"", new Object[] { totalBlocks, world.getName() });
if (totalBlocks > 0) {
Slimefun.getLogger().log(Level.INFO, "Avg: {0}ms/Block", DoubleHandler.fixDouble((double) time / (double) totalBlocks, 3));
}
}
}
private void loadBlock(File file, FileConfiguration cfg, String key) {
Location l = deserializeLocation(key); Location l = deserializeLocation(key);
String chunkString = locationToChunkString(l);
if (l == null) {
// That location was malformed, we will skip this one
return;
}
try { try {
totalBlocks++; String chunkString = locationToChunkString(l);
String json = cfg.getString(key); String json = cfg.getString(key);
Config blockInfo = parseBlockInfo(l, json); Config blockInfo = parseBlockInfo(l, json);
@ -163,10 +186,11 @@ public class BlockStorage {
if (storage.containsKey(l)) { if (storage.containsKey(l)) {
// It should not be possible to have two blocks on the same location. Ignore the // It should not be possible to have two blocks on the same location. Ignore the
// new entry if a block is already present and print an error to the console. // new entry if a block is already present and print an error to the console.
if (SlimefunPlugin.getRegistry().logDuplicateBlockEntries()) {
Slimefun.getLogger().log(Level.INFO, "Ignoring duplicate block @ {0}, {1}, {2} ({3} -> {4})", new Object[] { l.getBlockX(), l.getBlockY(), l.getBlockZ(), blockInfo.getString("id"), storage.get(l).getString("id") });
}
Slimefun.getLogger().log(Level.INFO, "Ignoring duplicate block @ {0}, {1}, {2}", new Object[] { l.getBlockX(), l.getBlockY(), l.getBlockZ() }); return;
Slimefun.getLogger().log(Level.INFO, "New: {0} | Old: {1}", new Object[] { key, serializeBlockInfo(storage.get(l)) });
continue;
} }
storage.put(l, blockInfo); storage.put(l, blockInfo);
@ -187,21 +211,6 @@ public class BlockStorage {
} }
} }
done++;
}
}
}
finally {
long time = (System.currentTimeMillis() - start);
Slimefun.getLogger().log(Level.INFO, "Loading Blocks... 100% (FINISHED - {0}ms)", time);
Slimefun.getLogger().log(Level.INFO, "Loaded a total of {0} Blocks for World \"{1}\"", new Object[] { totalBlocks, world.getName() });
if (totalBlocks > 0) {
Slimefun.getLogger().log(Level.INFO, "Avg: {0}ms/Block", DoubleHandler.fixDouble((double) time / (double) totalBlocks, 3));
}
}
}
private void loadChunks() { private void loadChunks() {
File chunks = new File(PATH_CHUNKS + "chunks.sfc"); File chunks = new File(PATH_CHUNKS + "chunks.sfc");
@ -211,7 +220,8 @@ public class BlockStorage {
for (String key : cfg.getKeys(false)) { for (String key : cfg.getKeys(false)) {
try { try {
if (world.getName().equals(PatternUtils.SEMICOLON.split(key)[0])) { if (world.getName().equals(PatternUtils.SEMICOLON.split(key)[0])) {
SlimefunPlugin.getRegistry().getChunks().put(key, new BlockInfoConfig(parseJSON(cfg.getString(key)))); BlockInfoConfig data = new BlockInfoConfig(parseJSON(cfg.getString(key)));
SlimefunPlugin.getRegistry().getChunks().put(key, data);
} }
} }
catch (Exception x) { catch (Exception x) {
@ -381,6 +391,7 @@ public class BlockStorage {
* *
* @param block * @param block
* the block to retrieve the ItemStack from * the block to retrieve the ItemStack from
*
* @return the SlimefunItem's ItemStack corresponding to the block if it has one, otherwise null * @return the SlimefunItem's ItemStack corresponding to the block if it has one, otherwise null
* *
* @since 4.0 * @since 4.0
@ -424,6 +435,7 @@ public class BlockStorage {
map.put(entry.getKey(), entry.getValue().getAsString()); map.put(entry.getKey(), entry.getValue().getAsString());
} }
} }
return map; return map;
} }
@ -530,12 +542,14 @@ public class BlockStorage {
} }
else if (!storage.hasInventory(l)) { else if (!storage.hasInventory(l)) {
File file = new File(PATH_INVENTORIES + serializeLocation(l) + ".sfi"); File file = new File(PATH_INVENTORIES + serializeLocation(l) + ".sfi");
BlockMenuPreset preset = BlockMenuPreset.getPreset(id);
if (file.exists()) { if (file.exists()) {
storage.inventories.put(l, new BlockMenu(BlockMenuPreset.getPreset(id), l, new io.github.thebusybiscuit.cscorelib2.config.Config(file))); BlockMenu inventory = new BlockMenu(preset, l, new io.github.thebusybiscuit.cscorelib2.config.Config(file));
storage.inventories.put(l, inventory);
} }
else { else {
storage.loadInventory(l, BlockMenuPreset.getPreset(id)); storage.loadInventory(l, preset);
} }
} }
} }
@ -732,15 +746,11 @@ public class BlockStorage {
} }
public static Set<String> getTickingChunks() { public static Set<String> getTickingChunks() {
return new HashSet<>(SlimefunPlugin.getRegistry().getActiveChunks()); return SlimefunPlugin.getRegistry().getActiveChunks();
}
public static Set<Location> getTickingLocations(Chunk chunk) {
return getTickingLocations(chunk.toString());
} }
public static Set<Location> getTickingLocations(String chunk) { public static Set<Location> getTickingLocations(String chunk) {
return new HashSet<>(SlimefunPlugin.getRegistry().getActiveTickers().get(chunk)); return SlimefunPlugin.getRegistry().getActiveTickers().getOrDefault(chunk, new HashSet<>());
} }
public BlockMenu loadInventory(Location l, BlockMenuPreset preset) { public BlockMenu loadInventory(Location l, BlockMenuPreset preset) {
@ -769,7 +779,8 @@ public class BlockStorage {
} }
public void loadUniversalInventory(BlockMenuPreset preset) { public void loadUniversalInventory(BlockMenuPreset preset) {
SlimefunPlugin.getRegistry().getUniversalInventories().put(preset.getID(), new UniversalBlockMenu(preset)); UniversalBlockMenu inventory = new UniversalBlockMenu(preset);
SlimefunPlugin.getRegistry().getUniversalInventories().put(preset.getID(), inventory);
} }
public void clearInventory(Location l) { public void clearInventory(Location l) {

View File

@ -16,6 +16,7 @@ options:
legacy-ore-grinder: true legacy-ore-grinder: true
language: en language: en
enable-translations: true enable-translations: true
log-duplicate-block-entries: true
guide: guide:
default-view-book: false default-view-book: false

View File

@ -1,66 +1,19 @@
--- ---
android:
scripts:
already-uploaded: "&4Dieses Skript wurde bereits hochgeladen."
editor: Skripteditor
enter-name:
-
- "&eBitte gebe einen Namen für dein Skript ins Chatfenster ein"
instructions:
ATTACK_ANIMALS: "&4Angreifen &c(Nur Tiere)"
ATTACK_ANIMALS_ADULT: "&4Angreifen &c(Nur ausgewachsene Tiere)"
ATTACK_MOBS: "&4Angreifen &c(Nur Monster)"
ATTACK_MOBS_ANIMALS: "&4Angreifen &c(Monster & Tiere)"
CATCH_FISH: "&bAngeln"
CHOP_TREE: "&cBaum fällen und nachpflanzen"
DIG_DOWN: "&bGrabe nach unten"
DIG_FORWARD: "&bGrabe vorwärts"
DIG_UP: "&bGrabe nach oben"
FARM_DOWN: "&bErnten und Nachpflanzen &7(Unterer Block)"
FARM_EXOTIC_DOWN: "&bErnten und Nachpflanzen (Fortgeschritten und unterer Block)"
FARM_EXOTIC_FORWARD: "&bErnten und Nachpflanzen (Fortgeschritten)"
FARM_FORWARD: "&bErnten und Nachpflanzen"
GO_DOWN: "&7Gehe nach unten"
GO_FORWARD: "&7Gehe vorwärts"
GO_UP: "&7Gehe nach oben"
INTERFACE_FUEL: "&cTreibstoff aus dem vorliegenden Interface nehmen"
INTERFACE_ITEMS: "&9Items ins vorliegende Interface bewegen"
MOVE_AND_DIG_DOWN: "&bGehe & Grabe nach unten"
MOVE_AND_DIG_FORWARD: "&bGehe & Grabe vorwärts"
MOVE_AND_DIG_UP: "&bGehe & Grabe nach oben"
REPEAT: "&9Neubeginn des Skripts"
START: "&2Start des Skripts"
TURN_LEFT: "&7Drehung nach links"
TURN_RIGHT: "&7Drehung nach rechts"
WAIT: "&eWarte 0.5 Sekunden"
rating:
already: "&4Du hast dieses Skript bereits bewertet!"
own: "&4Du kannst nicht dein eigenes Skript bewerten!"
uploaded:
- "&bLade dein Skript hoch..."
- "&aDein Skript wurde erfolgreich hochgeladen!"
started: "&7Dein Android hat sein Skript fortgesetzt"
stopped: "&7Dein Android hat sein Skript pausiert"
anvil:
not-working: "&4Items von Slimefun können nicht in einem Amboss verwendet werden!"
backpack:
already-open: "&cDieser Rucksack wird derzeit von jemand anderem benutzt!"
no-stack: "&cRucksäcke dürfen nicht gestapelt werden"
commands: commands:
help: Zeigt diesen Infotext an
cheat: Ermöglicht das Cheaten von Items cheat: Ermöglicht das Cheaten von Items
give: Gibt jemandem ein bestimmtes Item give: Gibt jemandem ein bestimmtes Item
guide: Gibt dir das Slimefun-Handbuch guide: Gibt dir das Slimefun-Handbuch
help: Zeigt diesen Infotext an timings: Zeigt einige Informationen über die Performance
teleporter: Erlaubt es dir Wegpunkte anderer Spieler anzusehen
versions: Eine Liste aller installierter Addons
search: Durchsucht dein Slimefun-Handbuch nach einem Begriff
open_guide: Öffnet das Slimefun-Handbuch open_guide: Öffnet das Slimefun-Handbuch
stats: Zeigt einige Statistiken über einen Spieler
research: research:
description: Verändert den Erfahrungsgrad eines Spielers description: Verändert den Erfahrungsgrad eines Spielers
reset: "&cDu hast soeben %player%'s Erfahrungsgrad zurückgesetzt" reset: "&cDu hast soeben %player%'s Erfahrungsgrad zurückgesetzt"
reset-target: "&cDein Erfahrungsgrad wurde zurückgesetzt" reset-target: "&cDein Erfahrungsgrad wurde zurückgesetzt"
search: Durchsucht dein Slimefun-Handbuch nach einem Begriff
stats: Zeigt einige Statistiken über einen Spieler
teleporter: Erlaubt es dir Wegpunkte anderer Spieler anzusehen
timings: Zeigt einige Informationen über die Performance
versions: Eine Liste aller installierter Addons
backpack: backpack:
description: Gibt eine Kopie eines existierenden Rucksacks description: Gibt eine Kopie eines existierenden Rucksacks
invalid-id: "&4Die id muss eine nicht-negative ganze Zahl sein!" invalid-id: "&4Die id muss eine nicht-negative ganze Zahl sein!"
@ -68,184 +21,120 @@ commands:
backpack-does-not-exist: "&4Der angegebene Rucksack konnte nicht gefunden werden!" backpack-does-not-exist: "&4Der angegebene Rucksack konnte nicht gefunden werden!"
restored-backpack-given: "&aDein Rucksack wurde erfolgreich wiederhergestellt restored-backpack-given: "&aDein Rucksack wurde erfolgreich wiederhergestellt
und deinem Inventar hinzugefügt!" und deinem Inventar hinzugefügt!"
gps:
deathpoint: "&4Todespunkt &7%date%"
geo:
scan-required: "&4GEO-Scan benötigt! &cScanne diesen Chunk mit einem GEO-Scanner!"
insufficient-complexity:
- "&4Unzureichende Komplexität deines GPS-Netzwerkes! Folgende Komplexität wird
benötigt: &c%complexity%"
- "&4a) Vielleicht hast du gar kein GPS-Netzwerk"
- "&4b) Oder dein GPS-Netzwerk ist nicht komplex genug"
waypoint:
added: "&aEin neuer Wegpunkt wurde hinzugefügt"
max: "&4Du hast die maximale Anzahl an Wegpunkten erreicht"
new: "&eBitte gebe ins Chatfenser einen Namen für deinen Wegpunkt ein. &7(Farbcodes
werden unterstützt!)"
guide: guide:
back: search:
guide: Gehe zurück zum Slimefun-Handbuch message: "&bWonach möchtest du suchen?"
settings: Gehe zurück zu den Einstellungen name: "&7Suche..."
title: Zurück tooltip: "&bKlicke um die Suche zu starten"
inventory: 'Suche nach: %item%'
lore:
- "&bWonach möchtest du suchen?"
- "&7Gib den Begriff, nach dem du suchen willst, in das Chatfenster ein"
cheat: cheat:
no-multiblocks: "&4Multiblöcke müssen gebaut werden! Du kannst dir diese nicht no-multiblocks: "&4Multiblöcke müssen gebaut werden! Du kannst dir diese nicht
geben." geben."
credits:
commit: Beitrag
commits: Beiträge
profile-link: Klick um mich auf GitHub zu sehen
roles:
developer: "&6Entwickler"
resourcepack: "&cRessourcenpaket-Designer"
translator: "&9Übersetzer"
wiki: "&3Wiki-Editor"
languages: languages:
updated: "&aFolgende Sprache wurde ausgewählt: &b%lang%"
translations:
name: "&aFehlt etwas?"
lore: Klicke um eine Übersetzung hinzuzufügen
select: Klicke hier um diese Sprache auszuwählen select: Klicke hier um diese Sprache auszuwählen
select-default: Klicke hier um die Standardsprache auszuwählen select-default: Klicke hier um die Standardsprache auszuwählen
selected-language: 'Aktuell ausgewählt:' selected-language: 'Aktuell ausgewählt:'
translations: title:
lore: Klicke um eine Übersetzung hinzuzufügen main: Slimefun-Handbuch
name: "&aFehlt etwas?" settings: Einstellungen & Infos
updated: "&aFolgende Sprache wurde ausgewählt: &b%lang%" languages: Wähle deine bevorzugte Sprache
credits: 'Slimefun4: Mitwirkende'
wiki: Slimefun4-Wiki
addons: Addons für Slimefun4
bugs: Fehlermeldungen
source: Quellcode
credits:
commit: Beitrag
commits: Beiträge
roles:
developer: "&6Entwickler"
wiki: "&3Wiki-Editor"
resourcepack: "&cRessourcenpaket-Designer"
translator: "&9Übersetzer"
profile-link: Klick um mich auf GitHub zu sehen
pages:
previous: Vorherige Seite
next: Nächste Seite
tooltips:
open-category: Klicke zum Öffnen
versions-notice: Dies ist sehr wichtig bei Fehlermeldungen!
wiki: Besuche das offizielle Slimefun-Wiki
recipes:
machine: Rezepte dieser Maschine
miner: Ressourcen, die mit dieser Maschine gewonnen werden können
generator: Mögliche Treibstoffquellen
gold-pan: Ressourcen, die hiermit gewonnen werden können
back:
title: Zurück
guide: Gehe zurück zum Slimefun-Handbuch
settings: Gehe zurück zu den Einstellungen
locked: GESPERRT locked: GESPERRT
locked-category: locked-category:
- Um diese Kategorie freizuschalten, - Um diese Kategorie freizuschalten,
- müssen zuerst sämtliche Items der - müssen zuerst sämtliche Items der
- folgenden Kategorien freigeschaltet werden - folgenden Kategorien freigeschaltet werden
pages:
next: Nächste Seite
previous: Vorherige Seite
search:
inventory: 'Suche nach: %item%'
lore:
- "&bWonach möchtest du suchen?"
- "&7Gib den Begriff, nach dem du suchen willst, in das Chatfenster ein"
message: "&bWonach möchtest du suchen?"
name: "&7Suche..."
tooltip: "&bKlicke um die Suche zu starten"
title:
addons: Addons für Slimefun4
bugs: Fehlermeldungen
credits: 'Slimefun4: Mitwirkende'
languages: Wähle deine bevorzugte Sprache
main: Slimefun-Handbuch
settings: Einstellungen & Infos
source: Quellcode
wiki: Slimefun4-Wiki
tooltips:
open-category: Klicke zum Öffnen
recipes:
generator: Mögliche Treibstoffquellen
gold-pan: Ressourcen, die hiermit gewonnen werden können
machine: Rezepte dieser Maschine
miner: Ressourcen, die mit dieser Maschine gewonnen werden können
versions-notice: Dies ist sehr wichtig bei Fehlermeldungen!
wiki: Besuche das offizielle Slimefun-Wiki
inventory:
no-access: "&4Du kannst nicht auf diesen Block zugreifen"
languages:
af: Afrikaans
ar: Arabisch
be: Belarusisch
bg: Bulgarisch
cs: Tschechisch
da: Dänisch
de: Deutsch
default: Server-Standard
el: Griechisch
en: Englisch
es: Spanisch
fa: Persisch
fi: Finnisch
fr: Französisch
he: Hebräisch
hr: Kroatisch
hu: Ungarisch
id: Indonesisch
it: Italienisch
ja: Japanisch
ko: Koreanisch
lv: Lettisch
mk: Mazedonisch
ms: Malaiisch
nl: Niederländisch
'no': Norwegisch
pl: Polnisch
pt: Portugiesisch (Portugal)
pt-BR: Portugiesisch (Brasilien)
ro: Rumänisch
ru: Russisch
sk: Slowakisch
sr: Serbisch
sv: Schwedisch
th: Thailändisch
tr: Türkisch
uk: Ukrainisch
vi: Vietnamesisch
zh-CN: Chinesisch (China)
zh-TW: Chinesisch (Taiwan)
machines:
ANCIENT_ALTAR:
not-enough-pedestals: "&4Es fehlen einige Sockel des Altars &c(%pedestals% / 8)"
unknown-catalyst: "&4Unbekannter Katalysator!"
unknown-recipe: "&4Unbekanntes Rezept!"
ANCIENT_PEDESTAL:
obstructed: "&4Der Sockel wurde blockiert! &cBitte entferne den Block über jedem
jedem Sockel!"
CARGO_NODES:
must-be-placed: "&4Dieser Block muss an die Seite einer Maschine oder Kiste platziert
werden!"
ELEVATOR:
click-to-teleport: "&eKlicke hier &7um zu dieser Etage zu teleportieren:"
current-floor: "&eDeine aktuelle Etage:"
enter-name: "&7Bitte gebe ins Chatfenser einen Namen für diese Etage ein. &r(Farbcodes
werden unterstützt!)"
named: '&2Diese Etage wurde erfolgreich &r"%floor%&r" &2genannt'
no-destinations: "&4Es konnten keine weiteren Etagen gefunden werden"
pick-a-floor: "&3- Wähle eine Etage -"
full-inventory: "&eDieses Inventar ist bereits voll!"
GPS_CONTROL_PANEL:
title: GPS - Kontrolltafel
transmitters: Satelliten-Übersicht
waypoints: Wegpunkte-Übersicht
HOLOGRAM_PROJECTOR:
enter-text: "&7Bitte gebe ins Chatfenser einen Text für dieses Hologram ein. &r(Farbcodes
werden unterstützt!)"
inventory-title: Hologrammeditor
ignition-chamber-no-flint: "&cAlle Feuerzeuge wurden aufgebraucht!"
in-use: "&cDiese Maschine wird derzeit von einem anderen Spieler verwendet."
pattern-not-found: "&eEs tut mir leid, aber ich konnte kein passendes Rezept finden."
TELEPORTER:
cancelled: "&4Teleportation abgebrochen!"
gui:
time: Voraussichtliche Dauer
title: Deine Wegpunkte
tooltip: Klicke zum teleportieren
invulnerability: "&b&lDu bist nun für 30 Sekunden unverwundbar!"
teleported: "&3Erfolgreich teleportiert!"
teleporting: "&3Du wirst teleportiert..."
unknown-material: "&eEs tut mir leid, aber ich erkenne das Item in meinem Werfer
nicht, probier ein anderes Item aus."
wrong-item: "&eEs tut mir leid, aber ich erkenne das Item in deiner Hand nicht,
probier ein anderes Item aus."
INDUSTRIAL_MINER:
no-fuel: "&cDein Industrial Miner hat keinen Treibstoff mehr! Platziere den benötigten
Treibstoff in die Kiste."
piston-facing: "&cEinIndustrial Miner erfordert Kolben, die nach oben zeigen!"
piston-space: "&cDie Blöcke über den Kolben müssen leer bleiben!"
destroyed: "&cDein Industrial Miner scheint zerstört worden zu sein."
already-running: "&cDieser Industrial Miner wird bereits verwendet!"
full-chest: "&cDie Kiste deines Industrial Miner ist vollgelaufen!"
no-permission: "&4Du scheinst nicht die benötigten Rechte zu haben, um in diesem
Gebiet einen Industrial Miner zu verwenden."
finished: "&eDein Industrial Miner ist fertig! Es wurde(n) insgesamt %ores% Erz(e)
gefunden!"
messages: messages:
cannot-place: "&cDu kannst hier keine Blöcke platzieren!" not-researched: "&4Du hast diesen Gegenstand noch nicht freigeschaltet!"
diet-cookie: "&eDu beginnst dich sehr leicht zu fühlen..." not-enough-xp: "&4Du hast nicht genügend Erfahrungspunkte, um dies freizuschalten"
unlocked: '&bDu hast folgenden Erfahrungsgrad gewonnen: &7"%research%"'
only-players: "&4Dieser Befehl ist nur für Spieler"
unknown-player: "&4Unbekannter Spieler: &c%player%"
no-permission: "&4Du hast nicht die benötigten Rechte hierfür"
usage: "&4Korrekte Schreibweise: &c%usage%"
not-online: "&4%player% &cist derzeit nicht online!"
not-valid-item: "&4%item% &cist kein gültiges Item!"
not-valid-amount: "&4%amount% &cist keine gültige Anzahl! Sie muss höher als 0 sein!"
given-item: '&bDir wurde &a%amount% &7mal "%item%&7" gegeben'
give-item: '&bDu hast %player% &a%amount% &7"%item%&7" gegeben'
not-valid-research: "&4%research% &cist kein gültiger Erfahrungsgrad!"
give-research: '&bDu hast %player% den Erfahrungsgrad &7"%research%&7" vergeben'
hungry: "&cDu bist zu hungrig, um dies zu tun!"
mode-change: "&bDer Modus von deinem %device% wurde geändert zu: &9%mode%"
disabled-in-world: "&4&lDieses Item wurde in dieser Welt deaktiviert!" disabled-in-world: "&4&lDieses Item wurde in dieser Welt deaktiviert!"
disabled-item: "&4&lDieses Item wurde von einem Server-Administrator deaktiviert!" disabled-item: "&4&lDieses Item wurde von einem Server-Administrator deaktiviert!"
no-tome-yourself: "&cDu kannst dieses Item nicht an dir selbst anwenden..."
multimeter: "&bGespeicherte Energie: &3%stored% &b/ &3%capacity%"
talisman:
anvil: "&a&oDein Talisman hat dein Werkzeug vor dem Zerfall gerettet"
miner: "&a&oDein Talisman hat soeben die Drops verdoppelt"
hunter: "&a&oDein Talisman hat soeben die Drops verdoppelt"
lava: "&a&oDein Talisman hat dich vor dem Verbrennen gerettet"
water: "&a&oDein Talisman hat dich vor dem Ertrinken gerettet"
angel: "&a&oDein Talisman hat dich davor bewahrt Fallschaden zu erleiden"
fire: "&a&oDein Talisman hat dich vor dem Verbrennen gerettet"
magician: "&a&oDein Talisman hat dir eine zusätzliche Verzauberung verliehen"
traveller: "&a&oDein Talisman hat dir einen Geschwindigkeitsboost gegeben"
warrior: "&a&oDein Talisman hat dir einen temporären Stärkebonus gegeben"
knight: "&a&oDein Talisman hat dir 5 Sekunden Regeneration gegeben"
whirlwind: "&a&oDein Talisman hat soeben ein Projektil reflektiert"
wizard: "&a&oDein Talisman hat dein Glück-Level erhöht aber möglicherweise das
Level einer anderen Verzauberung vermindert"
soulbound-rune:
fail: "&cDu kannst nicht mehrere Items auf einmal an deine Seele binden"
success: "&aDu hast dieses Item erfolgreich an deine Seele gebunden! Solltest
du sterben, wirst du es nun behalten."
research:
start: "&7Mysteriöse Worte flüstert man dir in dein Ohr!"
progress: "&7Du beginnst über &b%research% &7nachzudenken &e(%progress%)"
fire-extinguish: "&7Das Feuer wurde erfolgreich gelöscht" fire-extinguish: "&7Das Feuer wurde erfolgreich gelöscht"
cannot-place: "&cDu kannst hier keine Blöcke platzieren!"
no-pvp: "&cDu kannst andere Spieler hier nicht verletzen!"
radiation: "&4Du wurdest radioaktiver Strahlung ausgesetzt! &cZiehe einen vollständigen
Hazmat Suit an oder werde das radioaktive Item schnleunigst los!"
opening-guide: "&bÖffne dein Handbuch, dies kann eventuell ein paar Sekunden dauern..."
opening-backpack: "&bÖffne deinen Rucksack, dies kann eventuell ein paar Sekunden
dauern..."
no-iron-golem-heal: "&cDas ist kein Eisenbarren. Du kannst dieses Item nicht verwenden
um Eisengolems zu reparieren!"
link-prompt: "&eKlicke hier:"
diet-cookie: "&eDu beginnst dich sehr leicht zu fühlen..."
fortune-cookie: fortune-cookie:
- "&7Hilfe, ich bin in einer Glückskeks-Fabrik gefangen!" - "&7Hilfe, ich bin in einer Glückskeks-Fabrik gefangen!"
- "&7Morgen könntest du sterben... durch einen Creeper" - "&7Morgen könntest du sterben... durch einen Creeper"
@ -259,56 +148,173 @@ messages:
- "&742. Die Antwort ist 42." - "&742. Die Antwort ist 42."
- "&7Ein Walshy am Tag, hält die Sorgen fern. (Insiderwitz)" - "&7Ein Walshy am Tag, hält die Sorgen fern. (Insiderwitz)"
- "&7Grabe niemals direkt nach unten!" - "&7Grabe niemals direkt nach unten!"
give-item: '&bDu hast %player% &a%amount% &7"%item%&7" gegeben' - "&7Das ist nur ein Kratzer!"
given-item: '&bDir wurde &a%amount% &7mal "%item%&7" gegeben' - "&7Always look on the bright side of life!"
give-research: '&bDu hast %player% den Erfahrungsgrad &7"%research%&7" vergeben' - "&7Ist das jetzt ein Keks, Cookie oder ein Biscuit?"
hungry: "&cDu bist zu hungrig, um dies zu tun!" - "&7Jetzt auch zuckerfrei!"
link-prompt: "&eKlicke hier:" piglin-barter: "&4Du kannst Piglins keine Slimefun-Gegenständen anbieten!"
mode-change: "&bDer Modus von deinem %device% wurde geändert zu: &9%mode%" machines:
multimeter: "&bGespeicherte Energie: &3%stored% &b/ &3%capacity%" pattern-not-found: "&eEs tut mir leid, aber ich konnte kein passendes Rezept finden."
no-iron-golem-heal: "&cDas ist kein Eisenbarren. Du kannst dieses Item nicht verwenden unknown-material: "&eEs tut mir leid, aber ich erkenne das Item in meinem Werfer
um Eisengolems zu reparieren!" nicht, probier ein anderes Item aus."
no-permission: "&4Du hast nicht die benötigten Rechte hierfür" wrong-item: "&eEs tut mir leid, aber ich erkenne das Item in deiner Hand nicht,
no-pvp: "&cDu kannst andere Spieler hier nicht verletzen!" probier ein anderes Item aus."
not-enough-xp: "&4Du hast nicht genügend Erfahrungspunkte, um dies freizuschalten" full-inventory: "&eDieses Inventar ist bereits voll!"
no-tome-yourself: "&cDu kannst dieses Item nicht an dir selbst anwenden..." in-use: "&cDiese Maschine wird derzeit von einem anderen Spieler verwendet."
not-online: "&4%player% &cist derzeit nicht online!" ignition-chamber-no-flint: "&cAlle Feuerzeuge wurden aufgebraucht!"
not-researched: "&4Du hast diesen Gegenstand noch nicht freigeschaltet!" ANCIENT_ALTAR:
not-valid-amount: "&4%amount% &cist keine gültige Anzahl! Sie muss höher als 0 sein!" not-enough-pedestals: "&4Es fehlen einige Sockel des Altars &c(%pedestals% / 8)"
not-valid-item: "&4%item% &cist kein gültiges Item!" unknown-catalyst: "&4Unbekannter Katalysator!"
not-valid-research: "&4%research% &cist kein gültiger Erfahrungsgrad!" unknown-recipe: "&4Unbekanntes Rezept!"
only-players: "&4Dieser Befehl ist nur für Spieler" ANCIENT_PEDESTAL:
opening-backpack: "&bÖffne deinen Rucksack, dies kann eventuell ein paar Sekunden obstructed: "&4Der Sockel wurde blockiert! &cBitte entferne den Block über jedem
dauern..." jedem Sockel!"
opening-guide: "&bÖffne dein Handbuch, dies kann eventuell ein paar Sekunden dauern..." HOLOGRAM_PROJECTOR:
radiation: "&4Du wurdest radioaktiver Strahlung ausgesetzt! &cZiehe einen vollständigen enter-text: "&7Bitte gebe ins Chatfenser einen Text für dieses Hologram ein. &r(Farbcodes
Hazmat Suit an oder werde das radioaktive Item schnleunigst los!" werden unterstützt!)"
research: inventory-title: Hologrammeditor
progress: "&7Du beginnst über &b%research% &7nachzudenken &e(%progress%)" ELEVATOR:
start: "&7Mysteriöse Worte flüstert man dir in dein Ohr!" no-destinations: "&4Es konnten keine weiteren Etagen gefunden werden"
soulbound-rune: pick-a-floor: "&3- Wähle eine Etage -"
fail: "&cDu kannst nicht mehrere Items auf einmal an deine Seele binden" current-floor: "&eDeine aktuelle Etage:"
success: "&aDu hast dieses Item erfolgreich an deine Seele gebunden! Solltest click-to-teleport: "&eKlicke hier &7um zu dieser Etage zu teleportieren:"
du sterben, wirst du es nun behalten." enter-name: "&7Bitte gebe ins Chatfenser einen Namen für diese Etage ein. &r(Farbcodes
talisman: werden unterstützt!)"
angel: "&a&oDein Talisman hat dich davor bewahrt Fallschaden zu erleiden" named: '&2Diese Etage wurde erfolgreich &r"%floor%&r" &2genannt'
anvil: "&a&oDein Talisman hat dein Werkzeug vor dem Zerfall gerettet" TELEPORTER:
fire: "&a&oDein Talisman hat dich vor dem Verbrennen gerettet" teleporting: "&3Du wirst teleportiert..."
hunter: "&a&oDein Talisman hat soeben die Drops verdoppelt" teleported: "&3Erfolgreich teleportiert!"
knight: "&a&oDein Talisman hat dir 5 Sekunden Regeneration gegeben" cancelled: "&4Teleportation abgebrochen!"
lava: "&a&oDein Talisman hat dich vor dem Verbrennen gerettet" invulnerability: "&b&lDu bist nun für 30 Sekunden unverwundbar!"
magician: "&a&oDein Talisman hat dir eine zusätzliche Verzauberung verliehen" gui:
miner: "&a&oDein Talisman hat soeben die Drops verdoppelt" title: Deine Wegpunkte
traveller: "&a&oDein Talisman hat dir einen Geschwindigkeitsboost gegeben" tooltip: Klicke zum teleportieren
warrior: "&a&oDein Talisman hat dir einen temporären Stärkebonus gegeben" time: Voraussichtliche Dauer
water: "&a&oDein Talisman hat dich vor dem Ertrinken gerettet" CARGO_NODES:
whirlwind: "&a&oDein Talisman hat soeben ein Projektil reflektiert" must-be-placed: "&4Dieser Block muss an die Seite einer Maschine oder Kiste platziert
wizard: "&a&oDein Talisman hat dein Glück-Level erhöht aber möglicherweise das werden!"
Level einer anderen Verzauberung vermindert" GPS_CONTROL_PANEL:
unknown-player: "&4Unbekannter Spieler: &c%player%" title: GPS - Kontrolltafel
unlocked: '&bDu hast folgenden Erfahrungsgrad gewonnen: &7"%research%"' transmitters: Satelliten-Übersicht
usage: "&4Korrekte Schreibweise: &c%usage%" waypoints: Wegpunkte-Übersicht
miner: INDUSTRIAL_MINER:
no-ores: "&eIch konnte leider keine Erze in der Nähe finden!" no-fuel: "&cDein Industrial Miner hat keinen Treibstoff mehr! Platziere den benötigten
Treibstoff in die Kiste."
piston-facing: "&cEinIndustrial Miner erfordert Kolben, die nach oben zeigen!"
piston-space: "&cDie Blöcke über den Kolben müssen leer bleiben!"
destroyed: "&cDein Industrial Miner scheint zerstört worden zu sein."
already-running: "&cDieser Industrial Miner wird bereits verwendet!"
full-chest: "&cDie Kiste deines Industrial Miner ist vollgelaufen!"
no-permission: "&4Du scheinst nicht die benötigten Rechte zu haben, um in diesem
Gebiet einen Industrial Miner zu verwenden."
finished: "&eDein Industrial Miner ist fertig! Es wurde(n) insgesamt %ores% Erz(e)
gefunden!"
anvil:
not-working: "&4Items von Slimefun können nicht in einem Amboss verwendet werden!"
backpack:
already-open: "&cDieser Rucksack wird derzeit von jemand anderem benutzt!"
no-stack: "&cRucksäcke dürfen nicht gestapelt werden"
workbench: workbench:
not-enhanced: "&4Dieses Item kann nicht in einer normalen Werkbank genutzt werden" not-enhanced: "&4Dieses Item kann nicht in einer normalen Werkbank genutzt werden"
gps:
deathpoint: "&4Todespunkt &7%date%"
waypoint:
new: "&eBitte gebe ins Chatfenser einen Namen für deinen Wegpunkt ein. &7(Farbcodes
werden unterstützt!)"
added: "&aEin neuer Wegpunkt wurde hinzugefügt"
max: "&4Du hast die maximale Anzahl an Wegpunkten erreicht"
insufficient-complexity:
- "&4Unzureichende Komplexität deines GPS-Netzwerkes! Folgende Komplexität wird
benötigt: &c%complexity%"
- "&4a) Vielleicht hast du gar kein GPS-Netzwerk"
- "&4b) Oder dein GPS-Netzwerk ist nicht komplex genug"
geo:
scan-required: "&4GEO-Scan benötigt! &cScanne diesen Chunk mit einem GEO-Scanner!"
inventory:
no-access: "&4Du kannst nicht auf diesen Block zugreifen"
android:
started: "&7Dein Android hat sein Skript fortgesetzt"
stopped: "&7Dein Android hat sein Skript pausiert"
scripts:
already-uploaded: "&4Dieses Skript wurde bereits hochgeladen."
instructions:
START: "&2Start des Skripts"
REPEAT: "&9Neubeginn des Skripts"
WAIT: "&eWarte 0.5 Sekunden"
GO_FORWARD: "&7Gehe vorwärts"
GO_UP: "&7Gehe nach oben"
GO_DOWN: "&7Gehe nach unten"
TURN_LEFT: "&7Drehung nach links"
TURN_RIGHT: "&7Drehung nach rechts"
DIG_UP: "&bGrabe nach oben"
DIG_FORWARD: "&bGrabe vorwärts"
DIG_DOWN: "&bGrabe nach unten"
MOVE_AND_DIG_UP: "&bGehe & Grabe nach oben"
MOVE_AND_DIG_FORWARD: "&bGehe & Grabe vorwärts"
MOVE_AND_DIG_DOWN: "&bGehe & Grabe nach unten"
ATTACK_MOBS_ANIMALS: "&4Angreifen &c(Monster & Tiere)"
ATTACK_MOBS: "&4Angreifen &c(Nur Monster)"
ATTACK_ANIMALS: "&4Angreifen &c(Nur Tiere)"
ATTACK_ANIMALS_ADULT: "&4Angreifen &c(Nur ausgewachsene Tiere)"
CHOP_TREE: "&cBaum fällen und nachpflanzen"
CATCH_FISH: "&bAngeln"
FARM_FORWARD: "&bErnten und Nachpflanzen"
FARM_DOWN: "&bErnten und Nachpflanzen &7(Unterer Block)"
FARM_EXOTIC_FORWARD: "&bErnten und Nachpflanzen (Fortgeschritten)"
FARM_EXOTIC_DOWN: "&bErnten und Nachpflanzen (Fortgeschritten und unterer Block)"
INTERFACE_ITEMS: "&9Items ins vorliegende Interface bewegen"
INTERFACE_FUEL: "&cTreibstoff aus dem vorliegenden Interface nehmen"
enter-name:
-
- "&eBitte gebe einen Namen für dein Skript ins Chatfenster ein"
uploaded:
- "&bLade dein Skript hoch..."
- "&aDein Skript wurde erfolgreich hochgeladen!"
rating:
own: "&4Du kannst nicht dein eigenes Skript bewerten!"
already: "&4Du hast dieses Skript bereits bewertet!"
editor: Skripteditor
languages:
default: Server-Standard
en: Englisch
de: Deutsch
fr: Französisch
it: Italienisch
es: Spanisch
pl: Polnisch
sv: Schwedisch
nl: Niederländisch
cs: Tschechisch
hu: Ungarisch
lv: Lettisch
ru: Russisch
sk: Slowakisch
zh-TW: Chinesisch (Taiwan)
vi: Vietnamesisch
id: Indonesisch
zh-CN: Chinesisch (China)
el: Griechisch
he: Hebräisch
pt: Portugiesisch (Portugal)
ar: Arabisch
af: Afrikaans
da: Dänisch
fi: Finnisch
uk: Ukrainisch
ms: Malaiisch
'no': Norwegisch
ja: Japanisch
fa: Persisch
th: Thailändisch
ro: Rumänisch
pt-BR: Portugiesisch (Brasilien)
bg: Bulgarisch
ko: Koreanisch
tr: Türkisch
hr: Kroatisch
mk: Mazedonisch
sr: Serbisch
be: Belarusisch
tl: Tagalog
miner:
no-ores: "&eIch konnte leider keine Erze in der Nähe finden!"

View File

@ -110,6 +110,7 @@ messages:
disabled-item: '&4&lThis Item has been disabled! How did you even get that?' disabled-item: '&4&lThis Item has been disabled! How did you even get that?'
no-tome-yourself: '&cYou cannot use the &4Tome of Knowledge &con yourself...' no-tome-yourself: '&cYou cannot use the &4Tome of Knowledge &con yourself...'
multimeter: '&bStored Energy: &3%stored% &b/ &3%capacity%' multimeter: '&bStored Energy: &3%stored% &b/ &3%capacity%'
piglin-barter: '&4You cannot barter with piglins using Slimefun items'
talisman: talisman:
anvil: '&a&oYour Talisman saved your tool from breaking' anvil: '&a&oYour Talisman saved your tool from breaking'

View File

@ -151,6 +151,7 @@ messages:
- "&7Всегда смотрите на светлую сторону жизни!" - "&7Всегда смотрите на светлую сторону жизни!"
- "&7Вы съели странное печенье, до жути напоминающее бисквит" - "&7Вы съели странное печенье, до жути напоминающее бисквит"
- "&7Неоновые таблички просто ШИК!" - "&7Неоновые таблички просто ШИК!"
piglin-barter: "&4Вы не можете торговать с пиглинами, используя Slimefun предметы"
machines: machines:
pattern-not-found: "&eК сожалению, не удалось распознать этот рецепт. Пожалуйста, pattern-not-found: "&eК сожалению, не удалось распознать этот рецепт. Пожалуйста,
разложите предметы в верной последовательности в раздатчик." разложите предметы в верной последовательности в раздатчик."
@ -292,6 +293,8 @@ languages:
zh-CN: Китайский (Китай) zh-CN: Китайский (Китай)
el: Греческий el: Греческий
he: Иврит he: Иврит
pt: Португальский (Португалия)
pt-BR: Португальский (Бразилия)
ar: Арабский ar: Арабский
af: Бурский af: Бурский
da: Датский da: Датский
@ -303,8 +306,6 @@ languages:
fa: Персидский fa: Персидский
th: Тайский th: Тайский
ro: Румынский ro: Румынский
pt: Португальский (Португалия)
pt-BR: Португальский (Бразилия)
bg: Болгарский bg: Болгарский
ko: Корейский ko: Корейский
tr: Турецкий tr: Турецкий

View File

@ -149,6 +149,7 @@ messages:
- "&7Daima hayatın parlak tarafından bak!" - "&7Daima hayatın parlak tarafından bak!"
- "&7Bu aslında bir Bisküvi idi, Kurabiye değil." - "&7Bu aslında bir Bisküvi idi, Kurabiye değil."
- "&7Neon levhalar ışık yayar!" - "&7Neon levhalar ışık yayar!"
piglin-barter: "&4Slimefun eşyalarıyla, piglinlerle ticaret yapamazsın"
machines: machines:
pattern-not-found: "&eÜzgünüm, bu tarifi tanıyamadım. Lütfen Eşyaları Dağıtıcıya pattern-not-found: "&eÜzgünüm, bu tarifi tanıyamadım. Lütfen Eşyaları Dağıtıcıya
doğru şekilde yerleştirin." doğru şekilde yerleştirin."

View File

@ -147,6 +147,7 @@ messages:
- "&7Завжди дивіться на світлу сторону життя!" - "&7Завжди дивіться на світлу сторону життя!"
- "&7Цього разу попався бісквіт, а не печиво" - "&7Цього разу попався бісквіт, а не печиво"
- "&7Неонові таблички просто ШИК!" - "&7Неонові таблички просто ШИК!"
piglin-barter: "&4Ви не можете торгувати з піґлінами, використовуючи Slimefun предмети"
machines: machines:
pattern-not-found: "&eНа жаль, не вдалось розпізнати цей рецепт. Будь ласка, розмістіть pattern-not-found: "&eНа жаль, не вдалось розпізнати цей рецепт. Будь ласка, розмістіть
предмети у правильній послідовності у роздавач." предмети у правильній послідовності у роздавач."
@ -287,7 +288,6 @@ languages:
zh-CN: Китайська (Китай) zh-CN: Китайська (Китай)
el: Грецька el: Грецька
he: Іврит he: Іврит
pt: Португальська (Португалія)
pt-BR: Португальська (Бразилія) pt-BR: Португальська (Бразилія)
ar: Арабська ar: Арабська
af: Бурська af: Бурська
@ -300,6 +300,7 @@ languages:
fa: Перська fa: Перська
th: Тайська th: Тайська
ro: Румунська ro: Румунська
pt: Португальська (Португалія)
bg: Болгарська bg: Болгарська
ko: Корейська ko: Корейська
tr: Турецька tr: Турецька