improve block entity ticking performance

This commit is contained in:
Moritz Zwerger 2023-10-22 22:43:56 +02:00
parent d0ea37e93a
commit 35fd2eebb7
No known key found for this signature in database
GPG Key ID: 5CAD791931B09AC4
7 changed files with 18 additions and 13 deletions

View File

@ -29,7 +29,7 @@ abstract class BlockEntity(
open fun updateNBT(nbt: JsonObject) = Unit
open fun tick(connection: PlayConnection, blockState: BlockState, blockPosition: Vec3i, random: Random) = Unit
open fun tick(connection: PlayConnection, state: BlockState, position: Vec3i, random: Random) = Unit
open fun getRenderer(context: RenderContext, state: BlockState, position: Vec3i, light: Int): BlockEntityRenderer<out BlockEntity>? {
if (this.renderer?.state != state) {

View File

@ -63,18 +63,18 @@ class CampfireBlockEntity(connection: PlayConnection) : BlockEntity(connection)
}
override fun tick(connection: PlayConnection, blockState: BlockState, blockPosition: Vec3i, random: Random) {
if (blockState.block !is CampfireBlock || !blockState.isLit()) {
override fun tick(connection: PlayConnection, state: BlockState, position: Vec3i, random: Random) {
if (state.block !is CampfireBlock || !state.isLit()) {
return
}
if (random.nextFloat() < 0.11f) {
for (i in 0 until random.nextInt(2) + 2) {
blockState.block.spawnSmokeParticles(connection, blockState, blockPosition, false, random)
state.block.spawnSmokeParticles(connection, state, position, false, random)
}
}
val facing = blockState.getFacing().campfireId
val facing = state.getFacing().campfireId
for ((index, item) in items.withIndex()) {
item ?: continue
@ -83,7 +83,7 @@ class CampfireBlockEntity(connection: PlayConnection) : BlockEntity(connection)
}
val direction = HORIZONTAL[Math.floorMod(index + facing, Directions.SIDES.size)]
val position = Vec3d(blockPosition) + Vec3d(
val position = Vec3d(position) + Vec3d(
0.5f - direction.vector.x * DIRECTION_OFFSET + direction.rotateY().vector.x * DIRECTION_OFFSET,
0.5f,
0.5f - direction.vector.z * DIRECTION_OFFSET + direction.rotateY().vector.z * DIRECTION_OFFSET,

View File

@ -59,8 +59,8 @@ class MobSpawnerBlockEntity(connection: PlayConnection) : BlockEntity(connection
// ToDo: {MaxNearbyEntities: 6s, RequiredPlayerRange: 16s, SpawnCount: 4s, x: -80, y: 4, SpawnData: {id: "minecraft:zombie"}, z: 212, id: "minecraft:mob_spawner", MaxSpawnDelay: 800s, SpawnRange: 4s, Delay: 0s, MinSpawnDelay: 200s}
}
override fun tick(connection: PlayConnection, blockState: BlockState, blockPosition: Vec3i, random: Random) {
spawnParticles(blockPosition, random)
override fun tick(connection: PlayConnection, state: BlockState, position: Vec3i, random: Random) {
spawnParticles(position, random)
}
companion object : BlockEntityFactory<MobSpawnerBlockEntity> {

View File

@ -57,7 +57,7 @@ class NoteBlockBlockEntity(connection: PlayConnection) : BlockEntity(connection)
// ToDo: Play sound?
}
override fun tick(connection: PlayConnection, blockState: BlockState, blockPosition: Vec3i, random: Random) {
override fun tick(connection: PlayConnection, state: BlockState, position: Vec3i, random: Random) {
if (!showParticleNextTick) {
return
}
@ -65,7 +65,7 @@ class NoteBlockBlockEntity(connection: PlayConnection) : BlockEntity(connection)
noteParticleType?.let {
connection.world += NoteParticle(connection, blockPosition.toVec3d + Vec3d(0.5, 1.2, 0.5), blockState.getNote() / 24.0f, it.default())
connection.world += NoteParticle(connection, position.toVec3d + Vec3d(0.5, 1.2, 0.5), state.getNote() / 24.0f, it.default())
}
}

View File

@ -46,16 +46,21 @@ class ChunkSection(
if (blockEntities.isEmpty) {
return
}
val offset = Vec3i.of(chunkPosition, sectionHeight)
val position = Vec3i()
acquire()
val min = blockEntities.minPosition
val max = blockEntities.maxPosition
for (y in min.y..max.y) {
position.y = offset.y + y
for (z in min.z..max.z) {
position.z = offset.z + z
for (x in min.x..max.x) {
val index = getIndex(x, y, z)
val entity = blockEntities[index] ?: continue
val state = blocks[index] ?: continue
val position = Vec3i.of(chunkPosition, sectionHeight, index.indexPosition)
position.x = offset.x + x
entity.tick(connection, state, position, random)
}
}

View File

@ -32,7 +32,7 @@ class ChunkMesh(
var translucentMesh: SingleChunkMesh? = SingleChunkMesh(context, if (smallMesh) 3000 else 10000, onDemand = true)
var transparentMesh: SingleChunkMesh? = SingleChunkMesh(context, if (smallMesh) 3000 else 20000, onDemand = true)
var textMesh: SingleChunkMesh? = SingleChunkMesh(context, if (smallMesh) 5000 else 50000, onDemand = true)
var blockEntities: List<BlockEntityRenderer<*>>? = null
var blockEntities: ArrayList<BlockEntityRenderer<*>>? = null
// used for frustum culling
val minPosition = Vec3i(16)

View File

@ -62,7 +62,7 @@ class SolidSectionMesher(
val isHighestSection = sectionHeight == chunk.maxSection
val blocks = section.blocks
val sectionLight = section.light
val entities: MutableList<BlockEntityRenderer<*>> = ArrayList()
val entities: ArrayList<BlockEntityRenderer<*>> = ArrayList(section.blockEntities.count)
val position = BlockPosition()
val neighbourBlocks: Array<BlockState?> = arrayOfNulls(Directions.SIZE)