Optimization + fixed custom block placement

This commit is contained in:
Felix Cravic 2020-04-26 20:41:58 +02:00
parent d4cf29c7a7
commit 26debd0d4b
9 changed files with 77 additions and 78 deletions

View File

@ -141,6 +141,10 @@ public class PlayerInit {
itemEntity.setVelocity(velocity, 500); itemEntity.setVelocity(velocity, 500);
}); });
player.setEventCallback(PlayerDisconnectEvent.class, event -> {
System.out.println("DISCONNECTION " + player.getUsername());
});
player.setEventCallback(PlayerLoginEvent.class, event -> { player.setEventCallback(PlayerLoginEvent.class, event -> {
event.setSpawningInstance(instanceContainer); event.setSpawningInstance(instanceContainer);
}); });

View File

@ -4,6 +4,7 @@ import net.minestom.server.instance.Biome;
import net.minestom.server.instance.Chunk; import net.minestom.server.instance.Chunk;
import net.minestom.server.instance.ChunkGenerator; import net.minestom.server.instance.ChunkGenerator;
import net.minestom.server.instance.batch.ChunkBatch; import net.minestom.server.instance.batch.ChunkBatch;
import net.minestom.server.instance.block.Block;
import java.util.Random; import java.util.Random;
@ -19,7 +20,7 @@ public class ChunkGeneratorDemo extends ChunkGenerator {
if (random.nextInt(100) > 10) { if (random.nextInt(100) > 10) {
batch.setCustomBlock(x, y, z, "custom_block"); batch.setCustomBlock(x, y, z, "custom_block");
} else { } else {
batch.setBlock(x, y, z, (short) 10); batch.setBlock(x, y, z, Block.COMMAND_BLOCK);
} }
} }
} }

View File

@ -4,6 +4,7 @@ import net.minestom.server.instance.Biome;
import net.minestom.server.instance.Chunk; import net.minestom.server.instance.Chunk;
import net.minestom.server.instance.ChunkGenerator; import net.minestom.server.instance.ChunkGenerator;
import net.minestom.server.instance.batch.ChunkBatch; import net.minestom.server.instance.batch.ChunkBatch;
import net.minestom.server.instance.block.Block;
import net.minestom.server.utils.noise.FastNoise; import net.minestom.server.utils.noise.FastNoise;
import java.util.Random; import java.util.Random;
@ -20,7 +21,7 @@ public class NoiseTestGenerator extends ChunkGenerator {
@Override @Override
public void generateChunkData(ChunkBatch batch, int chunkX, int chunkZ) { public void generateChunkData(ChunkBatch batch, int chunkX, int chunkZ) {
for (byte x = 0; x < Chunk.CHUNK_SIZE_X; x++) for (byte x = 0; x < Chunk.CHUNK_SIZE_X; x++) {
for (byte z = 0; z < Chunk.CHUNK_SIZE_Z; z++) { for (byte z = 0; z < Chunk.CHUNK_SIZE_Z; z++) {
float height = fastNoise.GetSimplex(x + Chunk.CHUNK_SIZE_X * chunkX, z + Chunk.CHUNK_SIZE_Z * chunkZ) * 135; float height = fastNoise.GetSimplex(x + Chunk.CHUNK_SIZE_X * chunkX, z + Chunk.CHUNK_SIZE_Z * chunkZ) * 135;
height = Math.max(height, 70); height = Math.max(height, 70);
@ -28,10 +29,11 @@ public class NoiseTestGenerator extends ChunkGenerator {
if (random.nextInt(100) > 10) { if (random.nextInt(100) > 10) {
batch.setCustomBlock(x, y, z, "custom_block"); batch.setCustomBlock(x, y, z, "custom_block");
} else { } else {
batch.setBlock(x, y, z, (short) 10); batch.setBlock(x, y, z, Block.DIAMOND_ORE);
} }
} }
} }
}
} }
@Override @Override

View File

@ -14,7 +14,7 @@ public interface BlockModifier {
void setBlock(int x, int y, int z, short blockId, Data data); void setBlock(int x, int y, int z, short blockId, Data data);
void setCustomBlock(int x, int y, int z, short blockId, Data data); void setCustomBlock(int x, int y, int z, short customBlockId, Data data);
default void setBlock(int x, int y, int z, short blockId) { default void setBlock(int x, int y, int z, short blockId) {
setBlock(x, y, z, blockId, null); setBlock(x, y, z, blockId, null);
@ -24,8 +24,8 @@ public interface BlockModifier {
setBlock(x, y, z, block.getBlockId(), null); setBlock(x, y, z, block.getBlockId(), null);
} }
default void setCustomBlock(int x, int y, int z, short blockId) { default void setCustomBlock(int x, int y, int z, short customBlockId) {
setCustomBlock(x, y, z, blockId, null); setCustomBlock(x, y, z, customBlockId, null);
} }
default void setBlock(BlockPosition blockPosition, Block block) { default void setBlock(BlockPosition blockPosition, Block block) {
@ -45,21 +45,21 @@ public interface BlockModifier {
setBlock(position.toBlockPosition(), blockId); setBlock(position.toBlockPosition(), blockId);
} }
default void setCustomBlock(int x, int y, int z, String blockId, Data data) { default void setCustomBlock(int x, int y, int z, String customBlockId, Data data) {
CustomBlock customBlock = BLOCK_MANAGER.getBlock(blockId); CustomBlock customBlock = BLOCK_MANAGER.getCustomBlock(customBlockId);
setCustomBlock(x, y, z, customBlock.getId(), data); setCustomBlock(x, y, z, customBlock.getId(), data);
} }
default void setCustomBlock(int x, int y, int z, String blockId) { default void setCustomBlock(int x, int y, int z, String customBlockId) {
setCustomBlock(x, y, z, blockId, null); setCustomBlock(x, y, z, customBlockId, null);
} }
default void setCustomBlock(BlockPosition blockPosition, String blockId) { default void setCustomBlock(BlockPosition blockPosition, String customBlockId) {
setCustomBlock(blockPosition.getX(), blockPosition.getY(), blockPosition.getZ(), blockId); setCustomBlock(blockPosition.getX(), blockPosition.getY(), blockPosition.getZ(), customBlockId);
} }
default void setCustomBlock(Position position, String blockId) { default void setCustomBlock(Position position, String customBlockId) {
setCustomBlock(position.toBlockPosition(), blockId); setCustomBlock(position.toBlockPosition(), customBlockId);
} }
} }

View File

@ -70,22 +70,14 @@ public class Chunk implements Viewable {
setBlock(x, y, z, blockId, (short) 0, data, null); setBlock(x, y, z, blockId, (short) 0, data, null);
} }
public void UNSAFE_setBlock(int x, int y, int z, short blockId) {
UNSAFE_setBlock(x, y, z, blockId, null);
}
public void UNSAFE_setCustomBlock(int x, int y, int z, short customBlockId, Data data) { public void UNSAFE_setCustomBlock(int x, int y, int z, short customBlockId, Data data) {
CustomBlock customBlock = BLOCK_MANAGER.getBlock(customBlockId); CustomBlock customBlock = BLOCK_MANAGER.getCustomBlock(customBlockId);
if (customBlock == null) if (customBlock == null)
throw new IllegalArgumentException("The custom block " + customBlockId + " does not exist or isn't registered"); throw new IllegalArgumentException("The custom block " + customBlockId + " does not exist or isn't registered");
setCustomBlock(x, y, z, customBlock, data); setCustomBlock(x, y, z, customBlock, data);
} }
public void UNSAFE_setCustomBlock(int x, int y, int z, short customBlockId) {
UNSAFE_setCustomBlock(x, y, z, customBlockId, null);
}
private void setCustomBlock(int x, int y, int z, CustomBlock customBlock, Data data) { private void setCustomBlock(int x, int y, int z, CustomBlock customBlock, Data data) {
UpdateConsumer updateConsumer = customBlock.hasUpdate() ? customBlock::update : null; UpdateConsumer updateConsumer = customBlock.hasUpdate() ? customBlock::update : null;
setBlock(x, y, z, customBlock.getBlockId(), customBlock.getId(), data, updateConsumer); setBlock(x, y, z, customBlock.getBlockId(), customBlock.getId(), data, updateConsumer);
@ -159,7 +151,7 @@ public class Chunk implements Viewable {
public CustomBlock getCustomBlock(int x, int y, int z) { public CustomBlock getCustomBlock(int x, int y, int z) {
short id = customBlocksId[getBlockIndex(x, y, z)]; short id = customBlocksId[getBlockIndex(x, y, z)];
return id != 0 ? BLOCK_MANAGER.getBlock(id) : null; return id != 0 ? BLOCK_MANAGER.getCustomBlock(id) : null;
} }
protected CustomBlock getCustomBlock(int index) { protected CustomBlock getCustomBlock(int index) {
@ -168,8 +160,10 @@ public class Chunk implements Viewable {
} }
protected void refreshBlockValue(int x, int y, int z, short blockId, short customId) { protected void refreshBlockValue(int x, int y, int z, short blockId, short customId) {
this.blocksId[getBlockIndex(x, y, z)] = blockId; int blockIndex = getBlockIndex(x, y, z);
this.customBlocksId[getBlockIndex(x, y, z)] = customId;
this.blocksId[blockIndex] = blockId;
this.customBlocksId[blockIndex] = customId;
} }
protected void refreshBlockValue(int x, int y, int z, short blockId) { protected void refreshBlockValue(int x, int y, int z, short blockId) {

View File

@ -44,47 +44,48 @@ public class InstanceContainer extends Instance {
} }
@Override @Override
public synchronized void setBlock(int x, int y, int z, short blockId, Data data) { public void setBlock(int x, int y, int z, short blockId, Data data) {
Chunk chunk = getChunkAt(x, z); setBlock(x, y, z, blockId, (short) 0, data);
synchronized (chunk) {
int index = SerializerUtils.coordToChunkIndex(x, y, z);
callBlockDestroy(chunk, index, x, y, z);
BlockPosition blockPosition = new BlockPosition(x, y, z);
blockId = executeBlockPlacementRule(blockId, blockPosition);
chunk.UNSAFE_setBlock(x, y, z, blockId, data);
executeNeighboursBlockPlacementRule(blockPosition);
sendBlockChange(chunk, x, y, z, blockId);
}
} }
@Override @Override
public synchronized void setCustomBlock(int x, int y, int z, short blockId, Data data) { public void setCustomBlock(int x, int y, int z, short customBlockId, Data data) {
short blockId = BLOCK_MANAGER.getCustomBlock(customBlockId).getBlockId();
setBlock(x, y, z, blockId, customBlockId, data);
}
private synchronized void setBlock(int x, int y, int z, short blockId, short customBlockId, Data data) {
Chunk chunk = getChunkAt(x, z); Chunk chunk = getChunkAt(x, z);
synchronized (chunk) { synchronized (chunk) {
int index = SerializerUtils.coordToChunkIndex(x, y, z); boolean isCustomBlock = customBlockId != 0;
callBlockDestroy(chunk, index, x, y, z); int index = SerializerUtils.coordToChunkIndex(x, y, z);
BlockPosition blockPosition = new BlockPosition(x, y, z); BlockPosition blockPosition = new BlockPosition(x, y, z);
// Call the destroy listener if previous block was a custom block
callBlockDestroy(chunk, index, blockPosition);
// Change id based on neighbors
blockId = executeBlockPlacementRule(blockId, blockPosition); blockId = executeBlockPlacementRule(blockId, blockPosition);
chunk.UNSAFE_setCustomBlock(x, y, z, blockId, data); // Set the block
if (isCustomBlock) {
chunk.UNSAFE_setCustomBlock(x, y, z, customBlockId, data);
} else {
chunk.UNSAFE_setBlock(x, y, z, blockId, data);
}
// Refresh neighbors since a new block has been placed
executeNeighboursBlockPlacementRule(blockPosition); executeNeighboursBlockPlacementRule(blockPosition);
callBlockPlace(chunk, index, x, y, z); // Call the place listener for custom block
if (isCustomBlock)
callBlockPlace(chunk, index, blockPosition);
short id = BLOCK_MANAGER.getBlock(blockId).getBlockId(); // Refresh player chunk block
sendBlockChange(chunk, x, y, z, id); sendBlockChange(chunk, blockPosition, blockId);
} }
} }
@ -94,22 +95,23 @@ public class InstanceContainer extends Instance {
synchronized (chunk) { synchronized (chunk) {
chunk.refreshBlockValue(x, y, z, blockId); chunk.refreshBlockValue(x, y, z, blockId);
sendBlockChange(chunk, x, y, z, blockId); BlockPosition blockPosition = new BlockPosition(x, y, z);
sendBlockChange(chunk, blockPosition, blockId);
} }
} }
private void callBlockDestroy(Chunk chunk, int index, int x, int y, int z) { private void callBlockDestroy(Chunk chunk, int index, BlockPosition blockPosition) {
CustomBlock previousBlock = chunk.getCustomBlock(index); CustomBlock previousBlock = chunk.getCustomBlock(index);
if (previousBlock != null) { if (previousBlock != null) {
Data previousData = chunk.getData(index); Data previousData = chunk.getData(index);
previousBlock.onDestroy(this, new BlockPosition(x, y, z), previousData); previousBlock.onDestroy(this, blockPosition, previousData);
} }
} }
private void callBlockPlace(Chunk chunk, int index, int x, int y, int z) { private void callBlockPlace(Chunk chunk, int index, BlockPosition blockPosition) {
CustomBlock actualBlock = chunk.getCustomBlock(index); CustomBlock actualBlock = chunk.getCustomBlock(index);
Data previousData = chunk.getData(index); Data previousData = chunk.getData(index);
actualBlock.onPlace(this, new BlockPosition(x, y, z), previousData); actualBlock.onPlace(this, blockPosition, previousData);
} }
private short executeBlockPlacementRule(short blockId, BlockPosition blockPosition) { private short executeBlockPlacementRule(short blockId, BlockPosition blockPosition) {
@ -148,22 +150,19 @@ public class InstanceContainer extends Instance {
public void breakBlock(Player player, BlockPosition blockPosition) { public void breakBlock(Player player, BlockPosition blockPosition) {
Chunk chunk = getChunkAt(blockPosition); Chunk chunk = getChunkAt(blockPosition);
int blockX = blockPosition.getX(); int x = blockPosition.getX();
int blockY = blockPosition.getY(); int y = blockPosition.getY();
int blockZ = blockPosition.getZ(); int z = blockPosition.getZ();
short blockId = chunk.getBlockId(blockX, blockY, blockZ); short blockId = chunk.getBlockId(x, y, z);
if (blockId == 0) { if (blockId == 0) {
sendChunkSectionUpdate(chunk, ChunkUtils.getSectionAt(blockPosition.getY()), player); sendChunkSectionUpdate(chunk, ChunkUtils.getSectionAt(y), player);
return; return;
} }
PlayerBlockBreakEvent blockBreakEvent = new PlayerBlockBreakEvent(blockPosition); PlayerBlockBreakEvent blockBreakEvent = new PlayerBlockBreakEvent(blockPosition);
player.callEvent(PlayerBlockBreakEvent.class, blockBreakEvent); player.callEvent(PlayerBlockBreakEvent.class, blockBreakEvent);
if (!blockBreakEvent.isCancelled()) { if (!blockBreakEvent.isCancelled()) {
int x = blockPosition.getX();
int y = blockPosition.getY();
int z = blockPosition.getZ();
// Break or change the broken block based on event result // Break or change the broken block based on event result
short resultBlockId = blockBreakEvent.getResultBlock(); short resultBlockId = blockBreakEvent.getResultBlock();
@ -355,9 +354,9 @@ public class InstanceContainer extends Instance {
this.folder = folder; this.folder = folder;
} }
private void sendBlockChange(Chunk chunk, int x, int y, int z, short blockId) { private void sendBlockChange(Chunk chunk, BlockPosition blockPosition, short blockId) {
BlockChangePacket blockChangePacket = new BlockChangePacket(); BlockChangePacket blockChangePacket = new BlockChangePacket();
blockChangePacket.blockPosition = new BlockPosition(x, y, z); blockChangePacket.blockPosition = blockPosition;
blockChangePacket.blockId = blockId; blockChangePacket.blockId = blockId;
chunk.sendPacketToViewers(blockChangePacket); chunk.sendPacketToViewers(blockChangePacket);
} }

View File

@ -139,11 +139,11 @@ public class SharedInstance extends Instance {
} }
@Override @Override
public void setCustomBlock(int x, int y, int z, short blockId, Data data) { public void setCustomBlock(int x, int y, int z, short customBlockId, Data data) {
instanceContainer.setBlock(x, y, z, blockId, data); instanceContainer.setBlock(x, y, z, customBlockId, data);
} }
public InstanceContainer getContainer() { public InstanceContainer getInstanceContainer() {
return instanceContainer; return instanceContainer;
} }
} }

View File

@ -9,16 +9,16 @@ import java.util.Map;
public class BlockManager { public class BlockManager {
private Short2ObjectMap<CustomBlock> blocksInternalId = new Short2ObjectOpenHashMap<>(); private Short2ObjectMap<CustomBlock> customBlocksInternalId = new Short2ObjectOpenHashMap<>();
private Map<String, CustomBlock> blocksId = new HashMap<>(); private Map<String, CustomBlock> customBlocksId = new HashMap<>();
private Short2ObjectOpenHashMap<BlockPlacementRule> placementRules = new Short2ObjectOpenHashMap<>(); private Short2ObjectOpenHashMap<BlockPlacementRule> placementRules = new Short2ObjectOpenHashMap<>();
public void registerCustomBlock(CustomBlock customBlock) { public void registerCustomBlock(CustomBlock customBlock) {
String identifier = customBlock.getIdentifier(); String identifier = customBlock.getIdentifier();
short id = customBlock.getId(); short id = customBlock.getId();
this.blocksInternalId.put(id, customBlock); this.customBlocksInternalId.put(id, customBlock);
this.blocksId.put(identifier, customBlock); this.customBlocksId.put(identifier, customBlock);
} }
public void registerBlockPlacementRule(BlockPlacementRule blockPlacementRule) { public void registerBlockPlacementRule(BlockPlacementRule blockPlacementRule) {
@ -35,12 +35,12 @@ public class BlockManager {
return getBlockPlacementRule(block.getBlockId()); return getBlockPlacementRule(block.getBlockId());
} }
public CustomBlock getBlock(String identifier) { public CustomBlock getCustomBlock(String identifier) {
return blocksId.get(identifier); return customBlocksId.get(identifier);
} }
public CustomBlock getBlock(short id) { public CustomBlock getCustomBlock(short id) {
return blocksInternalId.get(id); return customBlocksInternalId.get(id);
} }
} }

View File

@ -56,7 +56,6 @@ public class ClientChannel extends ChannelInboundHandlerAdapter {
@Override @Override
public void channelInactive(ChannelHandlerContext ctx) { public void channelInactive(ChannelHandlerContext ctx) {
System.out.println("DISCONNECTION");
PlayerConnection playerConnection = packetProcessor.getPlayerConnection(ctx); PlayerConnection playerConnection = packetProcessor.getPlayerConnection(ctx);
if (playerConnection != null) { if (playerConnection != null) {
playerConnection.refreshOnline(false); playerConnection.refreshOnline(false);