Removed lombok dependency

This commit is contained in:
themode 2020-11-16 03:10:51 +01:00
parent e3793ed093
commit 3db53a798f
22 changed files with 841 additions and 375 deletions

View File

@ -8,6 +8,10 @@ plugins {
id 'org.jetbrains.kotlin.jvm' version '1.4.10'
}
group 'net.minestom.server'
version '1.0'
sourceCompatibility = 1.11
project.ext.lwjglVersion = "3.2.3"
switch (OperatingSystem.current()) {
@ -43,11 +47,6 @@ allprojects {
}
}
group 'net.minestom.server'
version '1.0'
sourceCompatibility = 1.11
sourceSets {
main {
java {
@ -126,9 +125,6 @@ dependencies {
api 'com.mojang:authlib:1.5.21'
api 'org.projectlombok:lombok:1.18.12'
annotationProcessor 'org.projectlombok:lombok:1.18.12'
// Code modification
api "org.ow2.asm:asm:${asmVersion}"
api "org.ow2.asm:asm-tree:${asmVersion}"

View File

@ -1,23 +1,21 @@
package net.minestom.codegen;
import lombok.Getter;
import java.io.File;
public class PrismarinePaths {
@Getter private String blocks;
@Getter private String biomes;
@Getter private String effects;
@Getter private String items;
@Getter private String recipes;
@Getter private String instruments;
@Getter private String materials;
@Getter private String entities;
@Getter private String protocol;
@Getter private String windows;
@Getter private String version;
@Getter private String language;
private String blocks;
private String biomes;
private String effects;
private String items;
private String recipes;
private String instruments;
private String materials;
private String entities;
private String protocol;
private String windows;
private String version;
private String language;
public File getBlockFile() {
return getFile(blocks, "blocks");
@ -32,6 +30,6 @@ public class PrismarinePaths {
}
public File getFile(String path, String type) {
return new File("prismarine-minecraft-data/data/"+path+"/"+type+".json");
return new File("prismarine-minecraft-data/data/" + path + "/" + type + ".json");
}
}

View File

@ -1,10 +1,5 @@
package net.minestom.server;
import com.mojang.authlib.AuthenticationService;
import com.mojang.authlib.minecraft.MinecraftSessionService;
import com.mojang.authlib.yggdrasil.YggdrasilAuthenticationService;
import lombok.Getter;
import lombok.Setter;
import net.minestom.server.advancements.AdvancementManager;
import net.minestom.server.benchmark.BenchmarkManager;
import net.minestom.server.command.CommandManager;
@ -16,7 +11,6 @@ import net.minestom.server.entity.EntityType;
import net.minestom.server.entity.Player;
import net.minestom.server.extensions.Extension;
import net.minestom.server.extensions.ExtensionManager;
import net.minestom.server.extras.mojangAuth.MojangCrypt;
import net.minestom.server.fluids.Fluid;
import net.minestom.server.gamedata.loottables.LootTableManager;
import net.minestom.server.gamedata.tags.TagManager;
@ -60,8 +54,6 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.net.Proxy;
import java.security.KeyPair;
import java.util.Collection;
/**
@ -72,8 +64,7 @@ import java.util.Collection;
*/
public final class MinecraftServer {
@Getter
private final static Logger LOGGER = LoggerFactory.getLogger(MinecraftServer.class);
public final static Logger LOGGER = LoggerFactory.getLogger(MinecraftServer.class);
public static final String VERSION_NAME = "1.16.4";
public static final int PROTOCOL_VERSION = 754;
@ -100,15 +91,6 @@ public final class MinecraftServer {
private static final int MS_TO_SEC = 1000;
public static final int TICK_MS = MS_TO_SEC / TICK_PER_SECOND;
@Getter
@Setter
private static boolean hardcoreLook = false;
// Extras
@Getter
@Setter
private static boolean fixLighting = true;
// Network monitoring
private static int rateLimit = 300;
private static int maxPacketSize = 30_000;
@ -151,14 +133,6 @@ public final class MinecraftServer {
private static LootTableManager lootTableManager;
private static TagManager tagManager;
//Mojang Auth
@Getter
private static final KeyPair keyPair = MojangCrypt.generateKeyPair();
@Getter
private static final AuthenticationService authService = new YggdrasilAuthenticationService(Proxy.NO_PROXY, "");
@Getter
private static final MinecraftSessionService sessionService = authService.createMinecraftSessionService();
public static MinecraftServer init() {
if (minecraftServer != null) // don't init twice
return minecraftServer;

View File

@ -1,11 +1,11 @@
package net.minestom.server.extensions;
import com.google.gson.*;
import lombok.extern.slf4j.Slf4j;
import net.minestom.server.extras.selfmodification.MinestomOverwriteClassLoader;
import net.minestom.server.utils.validate.Check;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.spongepowered.asm.mixin.Mixins;
@ -19,9 +19,10 @@ import java.net.URLClassLoader;
import java.util.*;
import java.util.zip.ZipFile;
@Slf4j
public final class ExtensionManager {
public final static Logger LOGGER = LoggerFactory.getLogger(ExtensionManager.class);
private final static String INDEV_CLASSES_FOLDER = "minestom.extension.indevfolder.classes";
private final static String INDEV_RESOURCES_FOLDER = "minestom.extension.indevfolder.resources";
private final static Gson GSON = new Gson();
@ -40,7 +41,7 @@ public final class ExtensionManager {
if (!extensionFolder.exists()) {
if (!extensionFolder.mkdirs()) {
log.error("Could not find or create the extension folder, extensions will not be loaded!");
LOGGER.error("Could not find or create the extension folder, extensions will not be loaded!");
return;
}
}
@ -57,7 +58,7 @@ public final class ExtensionManager {
}
loader = newClassLoader(urls);
} catch (MalformedURLException e) {
log.error("Failed to get URL.", e);
LOGGER.error("Failed to get URL.", e);
continue;
}
// TODO: Can't we use discoveredExtension.description here? Someone should test that.
@ -71,7 +72,7 @@ public final class ExtensionManager {
}
urlsString.append("'").append(url.toString()).append("'");
}
log.error("Failed to find extension.json in the urls '{}'.", urlsString);
LOGGER.error("Failed to find extension.json in the urls '{}'.", urlsString);
continue;
}
JsonObject extensionDescriptionJson = JsonParser.parseReader(new InputStreamReader(extensionInputStream)).getAsJsonObject();
@ -80,8 +81,8 @@ public final class ExtensionManager {
final String extensionName = extensionDescriptionJson.get("name").getAsString();
// Check the validity of the extension's name.
if (!extensionName.matches("[A-Za-z]+")) {
log.error("Extension '{}' specified an invalid name.", extensionName);
log.error("Extension '{}' will not be loaded.", extensionName);
LOGGER.error("Extension '{}' specified an invalid name.", extensionName);
LOGGER.error("Extension '{}' will not be loaded.", extensionName);
continue;
}
@ -90,8 +91,8 @@ public final class ExtensionManager {
{
String version;
if (!extensionDescriptionJson.has("version")) {
log.warn("Extension '{}' did not specify a version.", extensionName);
log.warn("Extension '{}' will continue to load but should specify a plugin version.", extensionName);
LOGGER.warn("Extension '{}' did not specify a version.", extensionName);
LOGGER.warn("Extension '{}' will continue to load but should specify a plugin version.", extensionName);
version = "Not Specified";
} else {
version = extensionDescriptionJson.get("version").getAsString();
@ -109,7 +110,7 @@ public final class ExtensionManager {
extensionLoaders.put(extensionName.toLowerCase(), loader);
if (extensions.containsKey(extensionName.toLowerCase())) {
log.error("An extension called '{}' has already been registered.", extensionName);
LOGGER.error("An extension called '{}' has already been registered.", extensionName);
continue;
}
@ -117,7 +118,7 @@ public final class ExtensionManager {
try {
jarClass = Class.forName(mainClass, true, loader);
} catch (ClassNotFoundException e) {
log.error("Could not find main class '{}' in extension '{}'.", mainClass, extensionName, e);
LOGGER.error("Could not find main class '{}' in extension '{}'.", mainClass, extensionName, e);
continue;
}
@ -125,7 +126,7 @@ public final class ExtensionManager {
try {
extensionClass = jarClass.asSubclass(Extension.class);
} catch (ClassCastException e) {
log.error("Main class '{}' in '{}' does not extend the 'Extension' superclass.", mainClass, extensionName, e);
LOGGER.error("Main class '{}' in '{}' does not extend the 'Extension' superclass.", mainClass, extensionName, e);
continue;
}
@ -135,19 +136,19 @@ public final class ExtensionManager {
// Let's just make it accessible, plugin creators don't have to make this public.
constructor.setAccessible(true);
} catch (NoSuchMethodException e) {
log.error("Main class '{}' in '{}' does not define a no-args constructor.", mainClass, extensionName, e);
LOGGER.error("Main class '{}' in '{}' does not define a no-args constructor.", mainClass, extensionName, e);
continue;
}
Extension extension = null;
try {
extension = constructor.newInstance();
} catch (InstantiationException e) {
log.error("Main class '{}' in '{}' cannot be an abstract class.", mainClass, extensionName, e);
LOGGER.error("Main class '{}' in '{}' cannot be an abstract class.", mainClass, extensionName, e);
continue;
} catch (IllegalAccessException ignored) {
// We made it accessible, should not occur
} catch (InvocationTargetException e) {
log.error(
LOGGER.error(
"While instantiating the main class '{}' in '{}' an exception was thrown.",
mainClass,
extensionName,
@ -164,7 +165,7 @@ public final class ExtensionManager {
} catch (IllegalAccessException e) {
// We made it accessible, should not occur
} catch (NoSuchFieldException e) {
log.error("Main class '{}' in '{}' has no description field.", mainClass, extensionName, e);
LOGGER.error("Main class '{}' in '{}' has no description field.", mainClass, extensionName, e);
continue;
}
@ -178,7 +179,7 @@ public final class ExtensionManager {
e.printStackTrace();
} catch (NoSuchFieldException e) {
// This should also not occur (unless someone changed the logger in Extension superclass).
log.error("Main class '{}' in '{}' has no logger field.", mainClass, extensionName, e);
LOGGER.error("Main class '{}' in '{}' has no logger field.", mainClass, extensionName, e);
}
extensions.put(extensionName.toLowerCase(), extension);
@ -209,7 +210,7 @@ public final class ExtensionManager {
// this allows developers to have their extension discovered while working on it, without having to build a jar and put in the extension folder
if (System.getProperty(INDEV_CLASSES_FOLDER) != null && System.getProperty(INDEV_RESOURCES_FOLDER) != null) {
log.info("Found indev folders for extension. Adding to list of discovered extensions.");
LOGGER.info("Found indev folders for extension. Adding to list of discovered extensions.");
final String extensionClasses = System.getProperty(INDEV_CLASSES_FOLDER);
final String extensionResources = System.getProperty(INDEV_RESOURCES_FOLDER);
try (InputStreamReader reader = new InputStreamReader(new FileInputStream(new File(extensionResources, "extension.json")))) {
@ -260,11 +261,11 @@ public final class ExtensionManager {
private void setupCodeModifiers(@NotNull List<DiscoveredExtension> extensions) {
final ClassLoader cl = getClass().getClassLoader();
if (!(cl instanceof MinestomOverwriteClassLoader)) {
log.warn("Current class loader is not a MinestomOverwriteClassLoader, but " + cl + ". This disables code modifiers (Mixin support is therefore disabled)");
LOGGER.warn("Current class loader is not a MinestomOverwriteClassLoader, but " + cl + ". This disables code modifiers (Mixin support is therefore disabled)");
return;
}
MinestomOverwriteClassLoader modifiableClassLoader = (MinestomOverwriteClassLoader) cl;
log.info("Start loading code modifiers...");
LOGGER.info("Start loading code modifiers...");
for (DiscoveredExtension extension : extensions) {
try {
if (extension.description.has("codeModifiers")) {
@ -276,14 +277,14 @@ public final class ExtensionManager {
if (extension.description.has("mixinConfig")) {
final String mixinConfigFile = extension.description.get("mixinConfig").getAsString();
Mixins.addConfiguration(mixinConfigFile);
log.info("Found mixin in extension " + extension.description.get("name").getAsString() + ": " + mixinConfigFile);
LOGGER.info("Found mixin in extension " + extension.description.get("name").getAsString() + ": " + mixinConfigFile);
}
} catch (Exception e) {
e.printStackTrace();
log.error("Failed to load code modifier for extension in files: " + Arrays.toString(extension.files), e);
LOGGER.error("Failed to load code modifier for extension in files: " + Arrays.toString(extension.files), e);
}
}
log.info("Done loading code modifiers.");
LOGGER.info("Done loading code modifiers.");
}
private static class DiscoveredExtension {

View File

@ -1,12 +1,21 @@
package net.minestom.server.extras;
import lombok.Getter;
import com.mojang.authlib.AuthenticationService;
import com.mojang.authlib.minecraft.MinecraftSessionService;
import com.mojang.authlib.yggdrasil.YggdrasilAuthenticationService;
import net.minestom.server.MinecraftServer;
import net.minestom.server.extras.mojangAuth.MojangCrypt;
import java.net.Proxy;
import java.security.KeyPair;
public final class MojangAuth {
@Getter
private static boolean usingMojangAuth = false;
private static boolean enabled = false;
private static final KeyPair keyPair = MojangCrypt.generateKeyPair();
private static final AuthenticationService authService = new YggdrasilAuthenticationService(Proxy.NO_PROXY, "");
private static final MinecraftSessionService sessionService = authService.createMinecraftSessionService();
/**
* Enables mojang authentication on the server.
@ -15,9 +24,25 @@ public final class MojangAuth {
*/
public static void init() {
if (MinecraftServer.getNettyServer().getAddress() == null) {
usingMojangAuth = true;
enabled = true;
} else {
throw new IllegalStateException("The server has already been started");
}
}
public static boolean isEnabled() {
return enabled;
}
public static KeyPair getKeyPair() {
return keyPair;
}
public static AuthenticationService getAuthService() {
return authService;
}
public static MinecraftSessionService getSessionService() {
return sessionService;
}
}

View File

@ -1,10 +1,12 @@
package net.minestom.server.extras.selfmodification;
import lombok.extern.slf4j.Slf4j;
import net.minestom.server.MinecraftServer;
import org.jetbrains.annotations.NotNull;
import org.objectweb.asm.ClassReader;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.tree.ClassNode;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.io.IOException;
@ -20,9 +22,10 @@ import java.util.Set;
/**
* Class Loader that can modify class bytecode when they are loaded
*/
@Slf4j
public class MinestomOverwriteClassLoader extends URLClassLoader {
public final static Logger LOGGER = LoggerFactory.getLogger(MinecraftServer.class);
private static MinestomOverwriteClassLoader INSTANCE;
/**
@ -105,18 +108,18 @@ public class MinestomOverwriteClassLoader extends URLClassLoader {
try {
// we do not load system classes by ourselves
Class<?> systemClass = ClassLoader.getPlatformClassLoader().loadClass(name);
log.trace("System class: " + systemClass);
LOGGER.trace("System class: " + systemClass);
return systemClass;
} catch (ClassNotFoundException e) {
try {
if (isProtected(name)) {
log.trace("Protected: " + name);
LOGGER.trace("Protected: " + name);
return super.loadClass(name, resolve);
}
return define(name, loadBytes(name, true), resolve);
} catch (Exception ex) {
log.trace("Fail to load class, resorting to parent loader: " + name, ex);
LOGGER.trace("Fail to load class, resorting to parent loader: " + name, ex);
// fail to load class, let parent load
// this forbids code modification, but at least it will load
return super.loadClass(name, resolve);
@ -137,7 +140,7 @@ public class MinestomOverwriteClassLoader extends URLClassLoader {
private Class<?> define(String name, byte[] bytes, boolean resolve) {
Class<?> defined = defineClass(name, bytes, 0, bytes.length);
log.trace("Loaded with code modifiers: " + name);
LOGGER.trace("Loaded with code modifiers: " + name);
if (resolve) {
resolveClass(defined);
}
@ -180,7 +183,7 @@ public class MinestomOverwriteClassLoader extends URLClassLoader {
};
node.accept(writer);
bytes = writer.toByteArray();
log.trace("Modified " + name);
LOGGER.trace("Modified " + name);
}
}
return bytes;
@ -208,7 +211,7 @@ public class MinestomOverwriteClassLoader extends URLClassLoader {
if (CodeModifier.class.isAssignableFrom(modifierClass)) {
CodeModifier modifier = (CodeModifier) modifierClass.getDeclaredConstructor().newInstance();
synchronized (modifiers) {
log.warn("Added Code modifier: " + modifier);
LOGGER.warn("Added Code modifier: " + modifier);
addCodeModifier(modifier);
}
}

View File

@ -1,25 +1,29 @@
package net.minestom.server.extras.selfmodification.mixins;
import lombok.extern.slf4j.Slf4j;
import net.minestom.server.MinecraftServer;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.spongepowered.asm.service.IMixinAuditTrail;
/**
* Takes care of logging mixin operations
*/
@Slf4j
public class MixinAuditTrailMinestom implements IMixinAuditTrail {
public final static Logger LOGGER = LoggerFactory.getLogger(MinecraftServer.class);
@Override
public void onApply(String className, String mixinName) {
log.trace("Applied mixin "+mixinName+" to class "+className);
LOGGER.trace("Applied mixin " + mixinName + " to class " + className);
}
@Override
public void onPostProcess(String className) {
log.trace("Post processing "+className);
LOGGER.trace("Post processing " + className);
}
@Override
public void onGenerate(String className, String generatorName) {
log.trace("Generating class "+className+" via generator "+generatorName);
LOGGER.trace("Generating class " + className + " via generator " + generatorName);
}
}

View File

@ -446,8 +446,8 @@ public abstract class Chunk implements Viewable, DataContainer {
// Retrieve & send the buffer to the connection
playerConnection.sendPacket(getFreshFullDataPacket());
// TODO do not hardcode
if (MinecraftServer.isFixLighting()) {
// TODO do not hardcode light
{
UpdateLightPacket updateLightPacket = new UpdateLightPacket();
updateLightPacket.chunkX = getChunkX();
updateLightPacket.chunkZ = getChunkZ();

View File

@ -2,7 +2,6 @@ package net.minestom.server.network.netty.channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import lombok.extern.slf4j.Slf4j;
import net.minestom.server.MinecraftServer;
import net.minestom.server.entity.Player;
import net.minestom.server.network.ConnectionManager;
@ -10,10 +9,13 @@ import net.minestom.server.network.PacketProcessor;
import net.minestom.server.network.netty.packet.InboundPacket;
import net.minestom.server.network.player.PlayerConnection;
import org.jetbrains.annotations.NotNull;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@Slf4j
public class ClientChannel extends SimpleChannelInboundHandler<InboundPacket> {
private final static Logger LOGGER = LoggerFactory.getLogger(ClientChannel.class);
private final ConnectionManager connectionManager = MinecraftServer.getConnectionManager();
private final PacketProcessor packetProcessor;
@ -36,7 +38,7 @@ public class ClientChannel extends SimpleChannelInboundHandler<InboundPacket> {
if (availableBytes > 0) {
final PlayerConnection playerConnection = packetProcessor.getPlayerConnection(ctx);
log.warn("WARNING: Packet 0x" + Integer.toHexString(packet.packetId)
LOGGER.warn("WARNING: Packet 0x" + Integer.toHexString(packet.packetId)
+ " not fully read (" + availableBytes + " bytes left), " + playerConnection);
packet.body.skipBytes(availableBytes);
@ -61,7 +63,7 @@ public class ClientChannel extends SimpleChannelInboundHandler<InboundPacket> {
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
log.info(cause.getMessage());
LOGGER.info(cause.getMessage());
cause.printStackTrace();
ctx.close();
}

View File

@ -4,6 +4,7 @@ import com.mojang.authlib.GameProfile;
import com.mojang.authlib.exceptions.AuthenticationUnavailableException;
import net.minestom.server.MinecraftServer;
import net.minestom.server.data.type.array.ByteArrayData;
import net.minestom.server.extras.MojangAuth;
import net.minestom.server.extras.mojangAuth.MojangCrypt;
import net.minestom.server.network.packet.client.ClientPreplayPacket;
import net.minestom.server.network.player.NettyPlayerConnection;
@ -38,25 +39,25 @@ public class EncryptionResponsePacket implements ClientPreplayPacket {
try {
final String loginUsername = nettyConnection.getLoginUsername();
if (!Arrays.equals(nettyConnection.getNonce(), getNonce())) {
MinecraftServer.getLOGGER().error(loginUsername + " tried to login with an invalid nonce!");
MinecraftServer.LOGGER.error(loginUsername + " tried to login with an invalid nonce!");
return;
}
if (!loginUsername.isEmpty()) {
final byte[] digestedData = MojangCrypt.digestData("", MinecraftServer.getKeyPair().getPublic(), getSecretKey());
final byte[] digestedData = MojangCrypt.digestData("", MojangAuth.getKeyPair().getPublic(), getSecretKey());
if (digestedData == null) {
// Incorrect key, probably because of the client
MinecraftServer.getLOGGER().error("Connection " + nettyConnection.getRemoteAddress() + " failed initializing encryption.");
MinecraftServer.LOGGER.error("Connection " + nettyConnection.getRemoteAddress() + " failed initializing encryption.");
connection.disconnect();
return;
}
final String string3 = new BigInteger(digestedData).toString(16);
final GameProfile gameProfile = MinecraftServer.getSessionService().hasJoinedServer(new GameProfile(null, loginUsername), string3);
final GameProfile gameProfile = MojangAuth.getSessionService().hasJoinedServer(new GameProfile(null, loginUsername), string3);
nettyConnection.setEncryptionKey(getSecretKey());
MinecraftServer.getLOGGER().info("UUID of player {} is {}", loginUsername, gameProfile.getId());
MinecraftServer.LOGGER.info("UUID of player {} is {}", loginUsername, gameProfile.getId());
CONNECTION_MANAGER.startPlayState(connection, gameProfile.getId(), gameProfile.getName());
}
} catch (AuthenticationUnavailableException e) {
@ -73,10 +74,11 @@ public class EncryptionResponsePacket implements ClientPreplayPacket {
}
public SecretKey getSecretKey() {
return MojangCrypt.decryptByteToSecretKey(MinecraftServer.getKeyPair().getPrivate(), sharedSecret);
return MojangCrypt.decryptByteToSecretKey(MojangAuth.getKeyPair().getPrivate(), sharedSecret);
}
public byte[] getNonce() {
return MinecraftServer.getKeyPair().getPrivate() == null ? this.verifyToken : MojangCrypt.decryptUsingKey(MinecraftServer.getKeyPair().getPrivate(), this.verifyToken);
return MojangAuth.getKeyPair().getPrivate() == null ?
this.verifyToken : MojangCrypt.decryptUsingKey(MojangAuth.getKeyPair().getPrivate(), this.verifyToken);
}
}

View File

@ -69,7 +69,7 @@ public class LoginStartPacket implements ClientPreplayPacket {
}
if (MojangAuth.isUsingMojangAuth() && isNettyClient) {
if (MojangAuth.isEnabled() && isNettyClient) {
// Mojang auth
if (CONNECTION_MANAGER.getPlayer(username) != null) {
connection.sendPacket(new LoginDisconnectPacket(ALREADY_CONNECTED_JSON));

View File

@ -1,7 +1,7 @@
package net.minestom.server.network.packet.server.login;
import net.minestom.server.MinecraftServer;
import net.minestom.server.data.type.array.ByteArrayData;
import net.minestom.server.extras.MojangAuth;
import net.minestom.server.network.packet.server.ServerPacket;
import net.minestom.server.network.packet.server.ServerPacketIdentifier;
import net.minestom.server.network.player.NettyPlayerConnection;
@ -23,7 +23,7 @@ public class EncryptionRequestPacket implements ServerPacket {
@Override
public void write(@NotNull BinaryWriter writer) {
writer.writeSizedString("");
final byte[] publicKey = MinecraftServer.getKeyPair().getPublic().getEncoded();
final byte[] publicKey = MojangAuth.getKeyPair().getPublic().getEncoded();
ByteArrayData.encodeByteArray(writer, publicKey);
ByteArrayData.encodeByteArray(writer, nonce);
}

View File

@ -25,7 +25,7 @@ public class JoinGamePacket implements ServerPacket {
@Override
public void write(@NotNull BinaryWriter writer) {
writer.writeInt(entityId);
writer.writeBoolean(MinecraftServer.isHardcoreLook());
writer.writeBoolean(gameMode.isHardcore());
writer.writeByte(gameMode.getId());
//Previous Gamemode
writer.writeByte(gameMode.getId());

View File

@ -2,8 +2,6 @@ package net.minestom.server.network.player;
import io.netty.channel.Channel;
import io.netty.channel.socket.SocketChannel;
import lombok.Getter;
import lombok.Setter;
import net.minestom.server.entity.PlayerSkin;
import net.minestom.server.extras.mojangAuth.Decrypter;
import net.minestom.server.extras.mojangAuth.Encrypter;
@ -32,14 +30,11 @@ public class NettyPlayerConnection extends PlayerConnection {
private final SocketChannel channel;
private SocketAddress remoteAddress;
@Getter
private boolean encrypted = false;
@Getter
private boolean compressed = false;
//Could be null. Only used for Mojang Auth
@Getter
@Setter
private byte[] nonce = new byte[4];
// Data from client packets
@ -232,4 +227,12 @@ public class NettyPlayerConnection extends PlayerConnection {
this.serverAddress = serverAddress;
this.serverPort = serverPort;
}
public byte[] getNonce() {
return nonce;
}
public void setNonce(byte[] nonce) {
this.nonce = nonce;
}
}

View File

@ -1,6 +1,5 @@
package net.minestom.server.network.player;
import lombok.Getter;
import net.minestom.server.MinecraftServer;
import net.minestom.server.chat.ChatColor;
import net.minestom.server.chat.ColoredText;
@ -34,7 +33,6 @@ public abstract class PlayerConnection {
private static final ColoredText rateLimitKickMessage = ColoredText.of(ChatColor.RED + "Too Many Packets");
//Connection Stats
@Getter
private final AtomicInteger packetCounter = new AtomicInteger(0);
private final AtomicInteger lastPacketCounter = new AtomicInteger(0);
private short tickCounter = 0;
@ -73,6 +71,10 @@ public abstract class PlayerConnection {
}
}
public AtomicInteger getPacketCounter() {
return packetCounter;
}
/**
* Returns a printable identifier for this connection, will be the player username
* or the connection remote address.

View File

@ -96,11 +96,11 @@ public final class SchedulerManager {
* Shutdowns all normal tasks and call the registered shutdown tasks.
*/
public void shutdown() {
MinecraftServer.getLOGGER().info("Executing all shutdown tasks..");
MinecraftServer.LOGGER.info("Executing all shutdown tasks..");
for (Task task : this.getShutdownTasks()) {
task.schedule();
}
MinecraftServer.getLOGGER().info("Shutting down the scheduled execution service and batches pool.");
MinecraftServer.LOGGER.info("Shutting down the scheduled execution service and batches pool.");
this.timerExecutionService.shutdown();
this.batchesPool.shutdown();
try {

View File

@ -1,20 +1,15 @@
package net.minestom.server.world;
import lombok.AccessLevel;
import lombok.Builder;
import lombok.Data;
import net.minestom.server.utils.NamespaceID;
import org.jetbrains.annotations.NotNull;
import org.jglrxavpok.hephaistos.nbt.NBTCompound;
import java.util.Objects;
import java.util.Optional;
import java.util.concurrent.atomic.AtomicInteger;
/**
* https://minecraft.gamepedia.com/Custom_dimension
*/
@Data
@Builder(builderMethodName = "hiddenBuilder", access = AccessLevel.PUBLIC)
public class DimensionType {
private static final AtomicInteger idCounter = new AtomicInteger(0);
@ -35,31 +30,47 @@ public class DimensionType {
.build();
private final int id = idCounter.getAndIncrement();
@NotNull
private final NamespaceID name;
private final boolean natural;
private final float ambientLight;
private final boolean ceilingEnabled;
private final boolean skylightEnabled;
@Builder.Default
private final Optional<Long> fixedTime = Optional.empty();
private final Optional<Long> fixedTime;
private final boolean raidCapable;
private final boolean respawnAnchorSafe;
private final boolean ultrawarm;
@Builder.Default
private final boolean bedSafe = true;
private final boolean bedSafe;
private final boolean piglinSafe;
@Builder.Default
private final int logicalHeight = 256;
@Builder.Default
private final int coordinateScale = 1;
@Builder.Default
private final NamespaceID infiniburn = NamespaceID.from("minecraft:infiniburn_overworld");
private final int logicalHeight;
private final int coordinateScale;
private final NamespaceID infiniburn;
DimensionType(NamespaceID name, boolean natural, float ambientLight, boolean ceilingEnabled, boolean skylightEnabled, Optional<Long> fixedTime, boolean raidCapable, boolean respawnAnchorSafe, boolean ultrawarm, boolean bedSafe, boolean piglinSafe, int logicalHeight, int coordinateScale, NamespaceID infiniburn) {
this.name = name;
this.natural = natural;
this.ambientLight = ambientLight;
this.ceilingEnabled = ceilingEnabled;
this.skylightEnabled = skylightEnabled;
this.fixedTime = fixedTime;
this.raidCapable = raidCapable;
this.respawnAnchorSafe = respawnAnchorSafe;
this.ultrawarm = ultrawarm;
this.bedSafe = bedSafe;
this.piglinSafe = piglinSafe;
this.logicalHeight = logicalHeight;
this.coordinateScale = coordinateScale;
this.infiniburn = infiniburn;
}
public static DimensionTypeBuilder builder(NamespaceID name) {
return hiddenBuilder().name(name);
}
public static DimensionTypeBuilder hiddenBuilder() {
return new DimensionTypeBuilder();
}
public NBTCompound toIndexedNBT() {
NBTCompound nbt = new NBTCompound();
NBTCompound element = toNBT();
@ -93,7 +104,173 @@ public class DimensionType {
return name.toString();
}
public static class DimensionTypeBuilder {
public int getId() {
return this.id;
}
public NamespaceID getName() {
return this.name;
}
public boolean isNatural() {
return this.natural;
}
public float getAmbientLight() {
return this.ambientLight;
}
public boolean isCeilingEnabled() {
return this.ceilingEnabled;
}
public boolean isSkylightEnabled() {
return this.skylightEnabled;
}
public Optional<Long> getFixedTime() {
return this.fixedTime;
}
public boolean isRaidCapable() {
return this.raidCapable;
}
public boolean isRespawnAnchorSafe() {
return this.respawnAnchorSafe;
}
public boolean isUltrawarm() {
return this.ultrawarm;
}
public boolean isBedSafe() {
return this.bedSafe;
}
public boolean isPiglinSafe() {
return this.piglinSafe;
}
public int getLogicalHeight() {
return this.logicalHeight;
}
public int getCoordinateScale() {
return this.coordinateScale;
}
public NamespaceID getInfiniburn() {
return this.infiniburn;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
DimensionType that = (DimensionType) o;
return id == that.id &&
Objects.equals(name, that.name);
}
@Override
public int hashCode() {
return Objects.hash(id, name);
}
public static class DimensionTypeBuilder {
private NamespaceID name;
private boolean natural;
private float ambientLight;
private boolean ceilingEnabled;
private boolean skylightEnabled;
private Optional<Long> fixedTime = Optional.empty();
private boolean raidCapable;
private boolean respawnAnchorSafe;
private boolean ultrawarm;
private boolean bedSafe = true;
private boolean piglinSafe = false;
private int logicalHeight = 256;
private int coordinateScale = 1;
private NamespaceID infiniburn = NamespaceID.from("minecraft:infiniburn_overworld");
DimensionTypeBuilder() {
}
public DimensionType.DimensionTypeBuilder name(NamespaceID name) {
this.name = name;
return this;
}
public DimensionType.DimensionTypeBuilder natural(boolean natural) {
this.natural = natural;
return this;
}
public DimensionType.DimensionTypeBuilder ambientLight(float ambientLight) {
this.ambientLight = ambientLight;
return this;
}
public DimensionType.DimensionTypeBuilder ceilingEnabled(boolean ceilingEnabled) {
this.ceilingEnabled = ceilingEnabled;
return this;
}
public DimensionType.DimensionTypeBuilder skylightEnabled(boolean skylightEnabled) {
this.skylightEnabled = skylightEnabled;
return this;
}
public DimensionType.DimensionTypeBuilder fixedTime(Optional<Long> fixedTime) {
this.fixedTime = fixedTime;
return this;
}
public DimensionType.DimensionTypeBuilder raidCapable(boolean raidCapable) {
this.raidCapable = raidCapable;
return this;
}
public DimensionType.DimensionTypeBuilder respawnAnchorSafe(boolean respawnAnchorSafe) {
this.respawnAnchorSafe = respawnAnchorSafe;
return this;
}
public DimensionType.DimensionTypeBuilder ultrawarm(boolean ultrawarm) {
this.ultrawarm = ultrawarm;
return this;
}
public DimensionType.DimensionTypeBuilder bedSafe(boolean bedSafe) {
this.bedSafe = bedSafe;
return this;
}
public DimensionType.DimensionTypeBuilder piglinSafe(boolean piglinSafe) {
this.piglinSafe = piglinSafe;
return this;
}
public DimensionType.DimensionTypeBuilder logicalHeight(int logicalHeight) {
this.logicalHeight = logicalHeight;
return this;
}
public DimensionType.DimensionTypeBuilder coordinateScale(int coordinateScale) {
this.coordinateScale = coordinateScale;
return this;
}
public DimensionType.DimensionTypeBuilder infiniburn(NamespaceID infiniburn) {
this.infiniburn = infiniburn;
return this;
}
public DimensionType build() {
return new DimensionType(name, natural, ambientLight, ceilingEnabled, skylightEnabled,
fixedTime, raidCapable, respawnAnchorSafe, ultrawarm, bedSafe,
piglinSafe, logicalHeight, coordinateScale, infiniburn);
}
}
}

View File

@ -1,9 +1,5 @@
package net.minestom.server.world.biomes;
import lombok.Builder;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.ToString;
import net.minestom.server.utils.NamespaceID;
import net.minestom.server.utils.validate.Check;
import org.jetbrains.annotations.NotNull;
@ -11,19 +7,15 @@ import org.jglrxavpok.hephaistos.nbt.NBTCompound;
import java.util.concurrent.atomic.AtomicInteger;
@Getter
@Builder
@ToString
@EqualsAndHashCode
public class Biome {
public static final AtomicInteger ID_COUNTER = new AtomicInteger(0);
private static final BiomeEffects DEFAULT_EFFECTS = BiomeEffects.builder()
.fog_color(0xC0D8FF)
.sky_color(0x78A7FF)
.water_color(0x3F76E4)
.water_fog_color(0x50533)
.fogColor(0xC0D8FF)
.skyColor(0x78A7FF)
.waterColor(0x3F76E4)
.waterFogColor(0x50533)
.build();
//A plains biome has to be registered or else minecraft will crash
@ -40,22 +32,30 @@ public class Biome {
private final int id = ID_COUNTER.getAndIncrement();
private final NamespaceID name;
@Builder.Default
private final float depth = 0.2F;
@Builder.Default
private final float temperature = 0.25F;
@Builder.Default
private final float scale = 0.2F;
@Builder.Default
private final float downfall = 0.8F;
@Builder.Default
private final Category category = Category.NONE;
@Builder.Default
private final BiomeEffects effects = DEFAULT_EFFECTS;
@Builder.Default
private final Precipitation precipitation = Precipitation.RAIN;
@Builder.Default
private final TemperatureModifier temperature_modifier = TemperatureModifier.NONE;
private final float depth;
private final float temperature;
private final float scale;
private final float downfall;
private final Category category;
private final BiomeEffects effects;
private final Precipitation precipitation;
private final TemperatureModifier temperature_modifier;
Biome(NamespaceID name, float depth, float temperature, float scale, float downfall, Category category, BiomeEffects effects, Precipitation precipitation, TemperatureModifier temperature_modifier) {
this.name = name;
this.depth = depth;
this.temperature = temperature;
this.scale = scale;
this.downfall = downfall;
this.category = category;
this.effects = effects;
this.precipitation = precipitation;
this.temperature_modifier = temperature_modifier;
}
public static BiomeBuilder builder() {
return new BiomeBuilder();
}
@NotNull
public NBTCompound toNbt() {
@ -80,15 +80,58 @@ public class Biome {
return nbt;
}
public int getId() {
return this.id;
}
public NamespaceID getName() {
return this.name;
}
public float getDepth() {
return this.depth;
}
public float getTemperature() {
return this.temperature;
}
public float getScale() {
return this.scale;
}
public float getDownfall() {
return this.downfall;
}
public Category getCategory() {
return this.category;
}
public BiomeEffects getEffects() {
return this.effects;
}
public Precipitation getPrecipitation() {
return this.precipitation;
}
public TemperatureModifier getTemperature_modifier() {
return this.temperature_modifier;
}
public enum Precipitation {
RAIN("rain"), NONE("none"), SNOW("snow");
@Getter
String type;
Precipitation(String type) {
this.type = type;
}
public String getType() {
return this.type;
}
}
public enum Category {
@ -96,23 +139,93 @@ public class Biome {
SAVANNA("savanna"), ICY("icy"), THE_END("the_end"), BEACH("beach"), FOREST("forest"), OCEAN("ocean"),
DESERT("desert"), RIVER("river"), SWAMP("swamp"), MUSHROOM("mushroom"), NETHER("nether");
@Getter
String type;
Category(String type) {
this.type = type;
}
public String getType() {
return type;
}
}
public enum TemperatureModifier {
NONE("none"), FROZEN("frozen");
@Getter
String type;
TemperatureModifier(String type) {
this.type = type;
}
public String getType() {
return type;
}
}
public static class BiomeBuilder {
private NamespaceID name;
private float depth = 0.2f;
private float temperature = 0.25f;
private float scale = 0.2f;
private float downfall = 0.8f;
private Category category = Category.NONE;
private BiomeEffects effects = DEFAULT_EFFECTS;
private Precipitation precipitation = Precipitation.RAIN;
private TemperatureModifier temperatureModifier = TemperatureModifier.NONE;
BiomeBuilder() {
}
public Biome.BiomeBuilder name(NamespaceID name) {
this.name = name;
return this;
}
public Biome.BiomeBuilder depth(float depth) {
this.depth = depth;
return this;
}
public Biome.BiomeBuilder temperature(float temperature) {
this.temperature = temperature;
return this;
}
public Biome.BiomeBuilder scale(float scale) {
this.scale = scale;
return this;
}
public Biome.BiomeBuilder downfall(float downfall) {
this.downfall = downfall;
return this;
}
public Biome.BiomeBuilder category(Category category) {
this.category = category;
return this;
}
public Biome.BiomeBuilder effects(BiomeEffects effects) {
this.effects = effects;
return this;
}
public Biome.BiomeBuilder precipitation(Precipitation precipitation) {
this.precipitation = precipitation;
return this;
}
public Biome.BiomeBuilder temperatureModifier(TemperatureModifier temperatureModifier) {
this.temperatureModifier = temperatureModifier;
return this;
}
public Biome build() {
return new Biome(name, depth, temperature, scale, downfall, category, effects, precipitation, temperatureModifier);
}
}
}

View File

@ -1,127 +1,291 @@
package net.minestom.server.world.biomes;
import lombok.Builder;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.ToString;
import net.minestom.server.utils.NamespaceID;
import org.jglrxavpok.hephaistos.nbt.NBTCompound;
@Getter
@Builder
@ToString
@EqualsAndHashCode
public class BiomeEffects {
private final int fog_color;
private final int sky_color;
private final int water_color;
private final int water_fog_color;
@Builder.Default private int foliage_color = -1;
@Builder.Default private int grass_color = -1;
@Builder.Default private GrassColorModifier grass_color_modifier = null;
@Builder.Default private BiomeParticles biomeParticles = null;
@Builder.Default private NamespaceID ambient_sound = null;
@Builder.Default private MoodSound mood_sound = null;
@Builder.Default private AdditionsSound additions_sound = null;
@Builder.Default private Music music = null;
private final int fog_color;
private final int sky_color;
private final int water_color;
private final int water_fog_color;
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setInt("fog_color", fog_color);
if (foliage_color != -1)
nbt.setInt("foliage_color", foliage_color);
if (grass_color != -1)
nbt.setInt("grass_color", grass_color);
nbt.setInt("sky_color", sky_color);
nbt.setInt("water_color", water_color);
nbt.setInt("water_fog_color", water_fog_color);
if (grass_color_modifier != null)
nbt.setString("grass_color_modifier", grass_color_modifier.getType());
if (biomeParticles != null)
nbt.set("particle", biomeParticles.toNbt());
if (ambient_sound != null)
nbt.setString("ambient_sound", ambient_sound.toString());
if (mood_sound != null)
nbt.set("mood_sound", mood_sound.toNbt());
if (additions_sound != null)
nbt.set("additions_sound", additions_sound.toNbt());
if (music != null)
nbt.set("music", music.toNbt());
return nbt;
}
private final int foliage_color;
private final int grass_color;
private final GrassColorModifier grass_color_modifier;
private final BiomeParticles biomeParticles;
private final NamespaceID ambient_sound;
private final MoodSound mood_sound;
private final AdditionsSound additions_sound;
private final Music music;
public enum GrassColorModifier {
NONE("none"), DARK_FOREST("dark_forest"), SWAMP("swamp");
BiomeEffects(int fog_color, int sky_color, int water_color, int water_fog_color, int foliage_color, int grass_color, GrassColorModifier grass_color_modifier, BiomeParticles biomeParticles, NamespaceID ambient_sound, MoodSound mood_sound, AdditionsSound additions_sound, Music music) {
this.fog_color = fog_color;
this.sky_color = sky_color;
this.water_color = water_color;
this.water_fog_color = water_fog_color;
this.foliage_color = foliage_color;
this.grass_color = grass_color;
this.grass_color_modifier = grass_color_modifier;
this.biomeParticles = biomeParticles;
this.ambient_sound = ambient_sound;
this.mood_sound = mood_sound;
this.additions_sound = additions_sound;
this.music = music;
}
@Getter
String type;
public static BiomeEffectsBuilder builder() {
return new BiomeEffectsBuilder();
}
GrassColorModifier(String type) {
this.type = type;
}
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setInt("fog_color", fog_color);
if (foliage_color != -1)
nbt.setInt("foliage_color", foliage_color);
if (grass_color != -1)
nbt.setInt("grass_color", grass_color);
nbt.setInt("sky_color", sky_color);
nbt.setInt("water_color", water_color);
nbt.setInt("water_fog_color", water_fog_color);
if (grass_color_modifier != null)
nbt.setString("grass_color_modifier", grass_color_modifier.getType());
if (biomeParticles != null)
nbt.set("particle", biomeParticles.toNbt());
if (ambient_sound != null)
nbt.setString("ambient_sound", ambient_sound.toString());
if (mood_sound != null)
nbt.set("mood_sound", mood_sound.toNbt());
if (additions_sound != null)
nbt.set("additions_sound", additions_sound.toNbt());
if (music != null)
nbt.set("music", music.toNbt());
return nbt;
}
@Getter
@Builder
@ToString
@EqualsAndHashCode
public static class MoodSound {
public int getFog_color() {
return this.fog_color;
}
private final NamespaceID sound;
private final int tick_delay;
private final int block_search_extent;
private final double offset;
public int getSky_color() {
return this.sky_color;
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setString("sound", sound.toString());
nbt.setInt("tick_delay", tick_delay);
nbt.setInt("block_search_extent", block_search_extent);
nbt.setDouble("offset", offset);
return nbt;
}
public int getWater_color() {
return this.water_color;
}
}
public int getWater_fog_color() {
return this.water_fog_color;
}
@Getter
@Builder
@ToString
@EqualsAndHashCode
public static class AdditionsSound {
public int getFoliage_color() {
return this.foliage_color;
}
private final NamespaceID sound;
private final double tick_chance;
public int getGrass_color() {
return this.grass_color;
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setString("sound", sound.toString());
nbt.setDouble("tick_chance", tick_chance);
return nbt;
}
public GrassColorModifier getGrass_color_modifier() {
return this.grass_color_modifier;
}
}
public BiomeParticles getBiomeParticles() {
return this.biomeParticles;
}
@Getter
@Builder
@ToString
@EqualsAndHashCode
public static class Music {
public NamespaceID getAmbient_sound() {
return this.ambient_sound;
}
private final NamespaceID sound;
private final int min_delay;
private final int max_delay;
private final boolean replace_current_music;
public MoodSound getMood_sound() {
return this.mood_sound;
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setString("sound", sound.toString());
nbt.setInt("min_delay", min_delay);
nbt.setInt("max_delay", max_delay);
nbt.setByte("replace_current_music", replace_current_music ? (byte) 1 : (byte) 0);
return nbt;
}
public AdditionsSound getAdditions_sound() {
return this.additions_sound;
}
}
public Music getMusic() {
return this.music;
}
public String toString() {
return "BiomeEffects(fog_color=" + this.getFog_color() + ", sky_color=" +
this.getSky_color() + ", water_color=" + this.getWater_color() + ", water_fog_color=" +
this.getWater_fog_color() + ", foliage_color=" + this.getFoliage_color() + ", grass_color=" +
this.getGrass_color() + ", grass_color_modifier=" + this.getGrass_color_modifier() + ", biomeParticles=" +
this.getBiomeParticles() + ", ambient_sound=" + this.getAmbient_sound() + ", mood_sound=" +
this.getMood_sound() + ", additions_sound=" + this.getAdditions_sound() + ", music=" + this.getMusic() + ")";
}
public enum GrassColorModifier {
NONE("none"), DARK_FOREST("dark_forest"), SWAMP("swamp");
String type;
GrassColorModifier(String type) {
this.type = type;
}
public String getType() {
return this.type;
}
}
public static class MoodSound {
private final NamespaceID sound;
private final int tickDelay;
private final int blockSearchExtent;
private final double offset;
public MoodSound(NamespaceID sound, int tickDelay, int blockSearchExtent, double offset) {
this.sound = sound;
this.tickDelay = tickDelay;
this.blockSearchExtent = blockSearchExtent;
this.offset = offset;
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setString("sound", sound.toString());
nbt.setInt("tick_delay", tickDelay);
nbt.setInt("block_search_extent", blockSearchExtent);
nbt.setDouble("offset", offset);
return nbt;
}
}
public static class AdditionsSound {
private final NamespaceID sound;
private final double tickChance;
public AdditionsSound(NamespaceID sound, double tickChance) {
this.sound = sound;
this.tickChance = tickChance;
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setString("sound", sound.toString());
nbt.setDouble("tick_chance", tickChance);
return nbt;
}
}
public static class Music {
private final NamespaceID sound;
private final int minDelay;
private final int maxDelay;
private final boolean replaceCurrentMusic;
public Music(NamespaceID sound, int minDelay, int maxDelay, boolean replaceCurrentMusic) {
this.sound = sound;
this.minDelay = minDelay;
this.maxDelay = maxDelay;
this.replaceCurrentMusic = replaceCurrentMusic;
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setString("sound", sound.toString());
nbt.setInt("min_delay", minDelay);
nbt.setInt("max_delay", maxDelay);
nbt.setByte("replace_current_music", replaceCurrentMusic ? (byte) 1 : (byte) 0);
return nbt;
}
}
public static class BiomeEffectsBuilder {
private int fogColor;
private int skyColor;
private int waterColor;
private int waterFogColor;
private int foliageColor = -1;
private int grassColor = -1;
private GrassColorModifier grassColorModifier;
private BiomeParticles biomeParticles;
private NamespaceID ambientSound;
private MoodSound moodSound;
private AdditionsSound additionsSound;
private Music music;
BiomeEffectsBuilder() {
}
public BiomeEffects.BiomeEffectsBuilder fogColor(int fogColor) {
this.fogColor = fogColor;
return this;
}
public BiomeEffects.BiomeEffectsBuilder skyColor(int skyColor) {
this.skyColor = skyColor;
return this;
}
public BiomeEffects.BiomeEffectsBuilder waterColor(int waterColor) {
this.waterColor = waterColor;
return this;
}
public BiomeEffects.BiomeEffectsBuilder waterFogColor(int waterFogColor) {
this.waterFogColor = waterFogColor;
return this;
}
public BiomeEffects.BiomeEffectsBuilder foliageColor(int foliageColor) {
this.foliageColor = foliageColor;
return this;
}
public BiomeEffects.BiomeEffectsBuilder grassColor(int grassColor) {
this.grassColor = grassColor;
return this;
}
public BiomeEffects.BiomeEffectsBuilder grassColorModifier(GrassColorModifier grassColorModifier) {
this.grassColorModifier = grassColorModifier;
return this;
}
public BiomeEffects.BiomeEffectsBuilder biomeParticles(BiomeParticles biomeParticles) {
this.biomeParticles = biomeParticles;
return this;
}
public BiomeEffects.BiomeEffectsBuilder ambientSound(NamespaceID ambientSound) {
this.ambientSound = ambientSound;
return this;
}
public BiomeEffects.BiomeEffectsBuilder moodSound(MoodSound moodSound) {
this.moodSound = moodSound;
return this;
}
public BiomeEffects.BiomeEffectsBuilder additionsSound(AdditionsSound additionsSound) {
this.additionsSound = additionsSound;
return this;
}
public BiomeEffects.BiomeEffectsBuilder music(Music music) {
this.music = music;
return this;
}
public BiomeEffects build() {
return new BiomeEffects(fogColor, skyColor, waterColor, waterFogColor, foliageColor,
grassColor, grassColorModifier, biomeParticles,
ambientSound, moodSound, additionsSound, music);
}
}
}

View File

@ -1,122 +1,126 @@
package net.minestom.server.world.biomes;
import lombok.Builder;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.ToString;
import net.minestom.server.instance.block.Block;
import net.minestom.server.instance.block.BlockAlternative;
import net.minestom.server.item.ItemStack;
import net.minestom.server.utils.NamespaceID;
import org.jetbrains.annotations.NotNull;
import org.jglrxavpok.hephaistos.nbt.NBTCompound;
import java.util.Map;
@Getter
@Builder
@ToString
@EqualsAndHashCode
public class BiomeParticles {
private final float probability;
private final ParticleOptions options;
private final float probability;
private final ParticleOptions options;
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setFloat("probability", probability);
nbt.set("options", options.toNbt());
return nbt;
}
public BiomeParticles(float probability, ParticleOptions options) {
this.probability = probability;
this.options = options;
}
public interface ParticleOptions {
NBTCompound toNbt();
}
public NBTCompound toNbt() {
NBTCompound nbt = new NBTCompound();
nbt.setFloat("probability", probability);
nbt.set("options", options.toNbt());
return nbt;
}
@Getter
@Builder
@ToString
@EqualsAndHashCode
public static class BlockParticle implements ParticleOptions {
public interface ParticleOptions {
NBTCompound toNbt();
}
//TODO also can be falling_dust
private static final String type = "block";
private final BlockAlternative block;
public static class BlockParticle implements ParticleOptions {
@Override
public NBTCompound toNbt() {
NBTCompound nbtCompound = new NBTCompound();
Block block1 = Block.fromStateId(block.getId());
nbtCompound.setString("type", type);
nbtCompound.setString("Name", block1.getName());
Map<String, String> propertiesMap = block.createPropertiesMap();
if (propertiesMap.size() != 0) {
NBTCompound properties = new NBTCompound();
propertiesMap.forEach(properties::setString);
nbtCompound.set("Properties", properties);
}
return nbtCompound;
}
//TODO also can be falling_dust
private static final String type = "block";
}
private final BlockAlternative block;
@Getter
@Builder
@ToString
@EqualsAndHashCode
public static class DustParticle implements ParticleOptions {
public BlockParticle(BlockAlternative block) {
this.block = block;
}
private static final String type = "dust";
private final float red;
private final float green;
private final float blue;
private final float scale;
@Override
public NBTCompound toNbt() {
NBTCompound nbtCompound = new NBTCompound();
Block block1 = Block.fromStateId(block.getId());
nbtCompound.setString("type", type);
nbtCompound.setString("Name", block1.getName());
Map<String, String> propertiesMap = block.createPropertiesMap();
if (propertiesMap.size() != 0) {
NBTCompound properties = new NBTCompound();
propertiesMap.forEach(properties::setString);
nbtCompound.set("Properties", properties);
}
return nbtCompound;
}
@Override
public NBTCompound toNbt() {
NBTCompound nbtCompound = new NBTCompound();
nbtCompound.setString("type", type);
nbtCompound.setFloat("r", red);
nbtCompound.setFloat("g", green);
nbtCompound.setFloat("b", blue);
nbtCompound.setFloat("scale", scale);
return nbtCompound;
}
}
}
public static class DustParticle implements ParticleOptions {
@Getter
@Builder
@ToString
@EqualsAndHashCode
public static class ItemParticle implements ParticleOptions {
private static final String type = "dust";
private static final String type = "item";
private final ItemStack item;
private final float red;
private final float green;
private final float blue;
private final float scale;
@Override
public NBTCompound toNbt() {
//todo test count might be wrong type
NBTCompound nbtCompound = item.toNBT();
nbtCompound.setString("type", type);
return nbtCompound;
}
public DustParticle(float red, float green, float blue, float scale) {
this.red = red;
this.green = green;
this.blue = blue;
this.scale = scale;
}
}
@Override
public NBTCompound toNbt() {
NBTCompound nbtCompound = new NBTCompound();
nbtCompound.setString("type", type);
nbtCompound.setFloat("r", red);
nbtCompound.setFloat("g", green);
nbtCompound.setFloat("b", blue);
nbtCompound.setFloat("scale", scale);
return nbtCompound;
}
@Getter
@Builder
@ToString
@EqualsAndHashCode
public static class NormalParticle implements ParticleOptions {
}
private final NamespaceID type;
public static class ItemParticle implements ParticleOptions {
@Override
public NBTCompound toNbt() {
NBTCompound nbtCompound = new NBTCompound();
nbtCompound.setString("type", type.toString());
return nbtCompound;
}
private static final String type = "item";
}
private final ItemStack item;
public ItemParticle(ItemStack item) {
this.item = item;
}
@Override
public NBTCompound toNbt() {
//todo test count might be wrong type
NBTCompound nbtCompound = item.toNBT();
nbtCompound.setString("type", type);
return nbtCompound;
}
}
public static class NormalParticle implements ParticleOptions {
private final NamespaceID type;
public NormalParticle(@NotNull NamespaceID type) {
this.type = type;
}
@Override
public NBTCompound toNbt() {
NBTCompound nbtCompound = new NBTCompound();
nbtCompound.setString("type", type.toString());
return nbtCompound;
}
}
}

View File

@ -43,7 +43,7 @@ public class PlayerInit {
NoiseTestGenerator noiseTestGenerator = new NoiseTestGenerator();
instanceContainer = MinecraftServer.getInstanceManager().createInstanceContainer(DimensionType.OVERWORLD);
instanceContainer.enableAutoChunkLoad(true);
instanceContainer.setChunkGenerator(chunkGeneratorDemo);
instanceContainer.setChunkGenerator(noiseTestGenerator);
// Load some chunks beforehand
final int loopStart = -3;

View File

@ -1,6 +1,5 @@
package demo.generator;
import lombok.Data;
import net.minestom.server.instance.Chunk;
import net.minestom.server.instance.batch.ChunkBatch;
import net.minestom.server.instance.block.Block;
@ -9,23 +8,22 @@ import net.minestom.server.utils.BlockPosition;
import java.util.HashMap;
import java.util.Map;
@Data
public class Structure {
private final Map<BlockPosition, Block> blocks = new HashMap<>();
private final Map<BlockPosition, Block> blocks = new HashMap<>();
public void build(ChunkBatch batch, BlockPosition pos) {
blocks.forEach((bPos, block) -> {
if (bPos.getX() + pos.getX() >= Chunk.CHUNK_SIZE_X || bPos.getX() + pos.getX() < 0)
return;
if (bPos.getZ() + pos.getZ() >= Chunk.CHUNK_SIZE_Z || bPos.getZ() + pos.getZ() < 0)
return;
batch.setBlock(bPos.copy().add(pos), block);
});
}
public void build(ChunkBatch batch, BlockPosition pos) {
blocks.forEach((bPos, block) -> {
if (bPos.getX() + pos.getX() >= Chunk.CHUNK_SIZE_X || bPos.getX() + pos.getX() < 0)
return;
if (bPos.getZ() + pos.getZ() >= Chunk.CHUNK_SIZE_Z || bPos.getZ() + pos.getZ() < 0)
return;
batch.setBlock(bPos.copy().add(pos), block);
});
}
public void addBlock(Block block, int localX, int localY, int localZ) {
blocks.put(new BlockPosition(localX, localY, localZ), block);
}
public void addBlock(Block block, int localX, int localY, int localZ) {
blocks.put(new BlockPosition(localX, localY, localZ), block);
}
}