diff --git a/src/main/java/de/bixilon/minosoft/data/world/chunk/Chunk.kt b/src/main/java/de/bixilon/minosoft/data/world/chunk/Chunk.kt index 1e5ab48dd..db62564d0 100644 --- a/src/main/java/de/bixilon/minosoft/data/world/chunk/Chunk.kt +++ b/src/main/java/de/bixilon/minosoft/data/world/chunk/Chunk.kt @@ -463,14 +463,17 @@ class Chunk( sectionLoop@ for (sectionIndex in startY.sectionHeight downTo 0) { val section = sections[sectionIndex] ?: continue + section.acquire() for (sectionY in ProtocolDefinition.SECTION_MAX_Y downTo 0) { - val light = section.blocks[x, sectionY, z]?.lightProperties ?: continue + val light = section.blocks.unsafeGet(x, sectionY, z)?.lightProperties ?: continue if (light.propagatesSkylight) { continue } y = (sectionIndex + lowestSection) * ProtocolDefinition.SECTION_HEIGHT_Y + sectionY + section.release() break@sectionLoop } + section.release() } skylightHeightmap[(z shl 4) or x] = y } diff --git a/src/main/java/de/bixilon/minosoft/data/world/container/BlockSectionDataProvider.kt b/src/main/java/de/bixilon/minosoft/data/world/container/BlockSectionDataProvider.kt index 0a69f3a35..e21a6acb7 100644 --- a/src/main/java/de/bixilon/minosoft/data/world/container/BlockSectionDataProvider.kt +++ b/src/main/java/de/bixilon/minosoft/data/world/container/BlockSectionDataProvider.kt @@ -109,7 +109,6 @@ class BlockSectionDataProvider( private fun floodFill(): ShortArray { // mark regions and check direct neighbours val regions = ShortArray(ProtocolDefinition.BLOCKS_PER_SECTION) - var nextFloodId = 1.toShort() fun trace(x: Int, y: Int, z: Int, nextId: Short) { val index = y shl 8 or (z shl 4) or x @@ -119,9 +118,6 @@ class BlockSectionDataProvider( } val blockState = unsafeGet(index) if (blockState.isSolid()) { - if (nextId == nextFloodId) { - nextFloodId++ - } return } regions[index] = nextId @@ -133,10 +129,11 @@ class BlockSectionDataProvider( if (z < ProtocolDefinition.SECTION_MAX_Z) trace(x, y, z + 1, nextId) } + var nextFloodId = 1.toShort() for (y in 0 until ProtocolDefinition.SECTION_HEIGHT_Y) { for (z in 0 until ProtocolDefinition.SECTION_WIDTH_Z) { for (x in 0 until ProtocolDefinition.SECTION_WIDTH_X) { - trace(x, y, z, nextFloodId) + trace(x, y, z, nextFloodId++) } } } diff --git a/src/main/java/de/bixilon/minosoft/data/world/positions/BlockPositionUtil.kt b/src/main/java/de/bixilon/minosoft/data/world/positions/BlockPositionUtil.kt new file mode 100644 index 000000000..ff2bd8eb9 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/data/world/positions/BlockPositionUtil.kt @@ -0,0 +1,27 @@ +/* + * Minosoft + * Copyright (C) 2020-2022 Moritz Zwerger + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + * + * This software is not affiliated with Mojang AB, the original developer of Minecraft. + */ + +package de.bixilon.minosoft.data.world.positions + +object BlockPositionUtil { + + fun generatePositionHash(x: Int, y: Int, z: Int): Long { + var hash = (x * 3129871L) xor z.toLong() * 116129781L xor y.toLong() + hash = hash * hash * 42317861L + hash * 11L + return hash shr 16 + } + + inline val BlockPosition.positionHash: Long + get() = generatePositionHash(x, y, z) + +} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/framebuffer/world/overlay/overlays/simple/WallOverlay.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/framebuffer/world/overlay/overlays/simple/WallOverlay.kt index 4cb92708f..dbf328e3a 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/framebuffer/world/overlay/overlays/simple/WallOverlay.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/framebuffer/world/overlay/overlays/simple/WallOverlay.kt @@ -20,10 +20,10 @@ import de.bixilon.minosoft.data.abilities.Gamemodes import de.bixilon.minosoft.data.registries.blocks.BlockState import de.bixilon.minosoft.data.registries.blocks.types.FluidBlock import de.bixilon.minosoft.data.text.formatting.color.RGBColor +import de.bixilon.minosoft.data.world.positions.BlockPositionUtil.positionHash import de.bixilon.minosoft.gui.rendering.RenderWindow import de.bixilon.minosoft.gui.rendering.framebuffer.world.overlay.OverlayFactory import de.bixilon.minosoft.gui.rendering.system.base.texture.texture.AbstractTexture -import de.bixilon.minosoft.gui.rendering.util.VecUtil import de.bixilon.minosoft.gui.rendering.util.vec.vec3.Vec3Util.blockPosition import de.bixilon.minosoft.gui.rendering.util.vec.vec3.Vec3iUtil.EMPTY import java.util.* @@ -58,7 +58,7 @@ class WallOverlay(renderWindow: RenderWindow, z: Float) : SimpleOverlay(renderWi } override fun draw() { - random.setSeed(VecUtil.generatePositionHash(position.x, position.y, position.z)) + random.setSeed(position.positionHash) texture = blockState?.blockModel?.getParticleTexture(random, position) ?: return tintColor = RGBColor(0.1f, 0.1f, 0.1f, 1.0f) diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/WeightedBakedModel.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/WeightedBakedModel.kt index 93d58d086..65087b5a2 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/WeightedBakedModel.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/WeightedBakedModel.kt @@ -17,10 +17,10 @@ import de.bixilon.kotlinglm.vec3.Vec3i import de.bixilon.kutil.exception.Broken import de.bixilon.minosoft.data.direction.Directions import de.bixilon.minosoft.data.registries.blocks.BlockState +import de.bixilon.minosoft.data.world.positions.BlockPositionUtil.positionHash import de.bixilon.minosoft.gui.rendering.models.baked.block.BakedBlockModel import de.bixilon.minosoft.gui.rendering.models.properties.AbstractFaceProperties import de.bixilon.minosoft.gui.rendering.system.base.texture.texture.AbstractTexture -import de.bixilon.minosoft.gui.rendering.util.VecUtil import de.bixilon.minosoft.gui.rendering.world.mesh.WorldMesh import java.util.* import kotlin.math.abs @@ -64,7 +64,7 @@ class WeightedBakedModel( } override fun getParticleTexture(random: Random, blockPosition: Vec3i): AbstractTexture? { - random.setSeed(VecUtil.generatePositionHash(blockPosition.x, blockPosition.y, blockPosition.z)) + random.setSeed(blockPosition.positionHash) return getModel(random)?.getParticleTexture(random, blockPosition) } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/block/BakedBlockStateModel.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/block/BakedBlockStateModel.kt index 334141898..60d80a1e3 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/block/BakedBlockStateModel.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/models/baked/block/BakedBlockStateModel.kt @@ -16,14 +16,16 @@ package de.bixilon.minosoft.gui.rendering.models.baked.block import de.bixilon.kotlinglm.vec3.Vec3i import de.bixilon.minosoft.data.direction.Directions import de.bixilon.minosoft.data.registries.blocks.BlockState +import de.bixilon.minosoft.data.world.positions.BlockPositionUtil import de.bixilon.minosoft.gui.rendering.models.CullUtil.canCull import de.bixilon.minosoft.gui.rendering.models.properties.AbstractFaceProperties import de.bixilon.minosoft.gui.rendering.system.base.texture.texture.AbstractTexture -import de.bixilon.minosoft.gui.rendering.util.VecUtil +import de.bixilon.minosoft.gui.rendering.tint.TintManager import de.bixilon.minosoft.gui.rendering.util.VecUtil.getWorldOffset import de.bixilon.minosoft.gui.rendering.util.vec.vec3.Vec3iUtil.toVec3 import de.bixilon.minosoft.gui.rendering.world.mesh.WorldMesh import de.bixilon.minosoft.gui.rendering.world.preparer.cull.SolidCullSectionPreparer +import de.bixilon.minosoft.util.KUtil.getOrElse import java.util.* class BakedBlockStateModel( @@ -54,7 +56,7 @@ class BakedBlockStateModel( val neighboursModel = neighbour?.blockModel var neighbourProperties: Array? = null if (neighboursModel != null) { - random.setSeed(VecUtil.generatePositionHash(position.x + direction.vector.x, position.y + direction.vector.y, position.z + direction.vector.z)) + random.setSeed(BlockPositionUtil.generatePositionHash(position.x + direction.vector.x, position.y + direction.vector.y, position.z + direction.vector.z)) neighbourProperties = neighboursModel.getTouchingFaceProperties(random, direction.inverted) } for (face in faces) { @@ -66,7 +68,7 @@ class BakedBlockStateModel( continue } } - tint = tints?.getOrNull(face.tintIndex) ?: -1 + tint = tints?.getOrElse(face.tintIndex, TintManager.DEFAULT_TINT_INDEX) ?: TintManager.DEFAULT_TINT_INDEX currentLight = (face.cullFace?.let { light[it.ordinal] } ?: light[SolidCullSectionPreparer.SELF_LIGHT_INDEX]).toInt() face.singleRender(positionArray, mesh, currentLight, tint) if (!rendered) { diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/models/unbaked/element/UnbakedElementFace.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/models/unbaked/element/UnbakedElementFace.kt index d3f5eeb36..1ee60f73d 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/models/unbaked/element/UnbakedElementFace.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/models/unbaked/element/UnbakedElementFace.kt @@ -17,6 +17,7 @@ import de.bixilon.kotlinglm.vec2.Vec2 import de.bixilon.kutil.primitive.IntUtil.toInt import de.bixilon.minosoft.data.direction.Directions import de.bixilon.minosoft.gui.rendering.models.unbaked.element.UnbakedElement.Companion.BLOCK_RESOLUTION +import de.bixilon.minosoft.gui.rendering.tint.TintManager import de.bixilon.minosoft.util.nbt.tag.NBTUtil.listCast data class UnbakedElementFace( @@ -48,7 +49,7 @@ data class UnbakedElementFace( texture = data["texture"].toString(), cullFace = cullFace, rotation = data["rotation"]?.toInt() ?: 0, - tintIndex = data["tintindex"]?.toInt() ?: -1, + tintIndex = data["tintindex"]?.toInt() ?: TintManager.DEFAULT_TINT_INDEX, ) } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/tint/TintManager.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/tint/TintManager.kt index 2186a54fe..2265a67d4 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/tint/TintManager.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/tint/TintManager.kt @@ -107,6 +107,7 @@ class TintManager(private val connection: PlayConnection) { } companion object { + const val DEFAULT_TINT_INDEX = -1 fun getJsonColor(color: Int): RGBColor? { if (color == 0) { diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/util/VecUtil.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/util/VecUtil.kt index 761efb2cc..5772b8441 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/util/VecUtil.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/util/VecUtil.kt @@ -26,6 +26,7 @@ import de.bixilon.minosoft.data.direction.Directions import de.bixilon.minosoft.data.registries.AABB import de.bixilon.minosoft.data.registries.blocks.RandomOffsetTypes import de.bixilon.minosoft.data.registries.blocks.types.Block +import de.bixilon.minosoft.data.world.positions.BlockPositionUtil import de.bixilon.minosoft.gui.rendering.util.vec.vec3.Vec3Util.EMPTY import de.bixilon.minosoft.gui.rendering.util.vec.vec3.Vec3Util.get import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition @@ -191,7 +192,7 @@ object VecUtil { return Vec3.EMPTY } - val positionHash = generatePositionHash(x, 0, z) + val positionHash = BlockPositionUtil.generatePositionHash(x, 0, z) val maxModelOffset = 0.25f // ToDo: PixLyzer: use block.model.max_model_offset fun horizontal(axisHash: Long): Float { @@ -230,12 +231,6 @@ object VecUtil { val Vec3d.empty: Boolean get() = this.length() < 0.001 - fun generatePositionHash(x: Int, y: Int, z: Int): Long { - var hash = (x * 3129871L) xor z.toLong() * 116129781L xor y.toLong() - hash = hash * hash * 42317861L + hash * 11L - return hash shr 16 - } - fun getDistanceToNextIntegerAxisInDirection(position: Vec3d, direction: Vec3d): Double { fun getTarget(direction: Vec3d, position: Vec3d, axis: Axes): Int { return if (direction[axis] > 0) { diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/util/mesh/Mesh.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/util/mesh/Mesh.kt index 119cb5bba..14f308f8d 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/util/mesh/Mesh.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/util/mesh/Mesh.kt @@ -34,7 +34,7 @@ abstract class Mesh( private var _data: DirectArrayFloatList? = data ?: if (onDemand) null else DirectArrayFloatList(initialCacheSize) var data: DirectArrayFloatList get() { - if (onDemand && _data == null) { + if (_data == null && onDemand) { _data = DirectArrayFloatList(initialCacheSize) } return _data as DirectArrayFloatList diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/FluidCullSectionPreparer.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/FluidCullSectionPreparer.kt index cec9d84a6..322893e21 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/FluidCullSectionPreparer.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/FluidCullSectionPreparer.kt @@ -30,13 +30,13 @@ import de.bixilon.minosoft.data.registries.fluid.Fluid import de.bixilon.minosoft.data.text.formatting.color.Colors import de.bixilon.minosoft.data.world.chunk.Chunk import de.bixilon.minosoft.data.world.chunk.ChunkSection +import de.bixilon.minosoft.data.world.positions.BlockPositionUtil.positionHash import de.bixilon.minosoft.gui.rendering.RenderWindow import de.bixilon.minosoft.gui.rendering.models.CullUtil.canCull import de.bixilon.minosoft.gui.rendering.models.properties.FaceProperties import de.bixilon.minosoft.gui.rendering.system.base.texture.TextureTransparencies import de.bixilon.minosoft.gui.rendering.system.base.texture.texture.AbstractTexture import de.bixilon.minosoft.gui.rendering.textures.TextureUtil.getMesh -import de.bixilon.minosoft.gui.rendering.util.VecUtil import de.bixilon.minosoft.gui.rendering.util.VecUtil.plus import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2Util.EMPTY import de.bixilon.minosoft.gui.rendering.util.vec.vec3.Vec3Util.rotate @@ -96,7 +96,7 @@ class FluidCullSectionPreparer( return true } val model = neighbour.blockModel ?: return false - random.setSeed(VecUtil.generatePositionHash(neighbourPosition.x, neighbourPosition.y, neighbourPosition.z)) + random.setSeed(neighbourPosition.positionHash) val size = model.getTouchingFaceProperties(random, direction.inverted) return size?.canCull(FLUID_FACE_PROPERTY, false) ?: false } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/SolidCullSectionPreparer.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/SolidCullSectionPreparer.kt index 854e55454..f988da3ef 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/SolidCullSectionPreparer.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/world/preparer/cull/SolidCullSectionPreparer.kt @@ -31,9 +31,10 @@ import de.bixilon.minosoft.data.world.chunk.Chunk import de.bixilon.minosoft.data.world.chunk.ChunkSection import de.bixilon.minosoft.data.world.chunk.light.SectionLight import de.bixilon.minosoft.data.world.container.BlockSectionDataProvider +import de.bixilon.minosoft.data.world.positions.BlockPosition +import de.bixilon.minosoft.data.world.positions.BlockPositionUtil.positionHash import de.bixilon.minosoft.gui.rendering.RenderWindow import de.bixilon.minosoft.gui.rendering.models.SingleBlockRenderable -import de.bixilon.minosoft.gui.rendering.util.VecUtil import de.bixilon.minosoft.gui.rendering.world.entities.BlockEntityRenderer import de.bixilon.minosoft.gui.rendering.world.entities.MeshedBlockEntityRenderer import de.bixilon.minosoft.gui.rendering.world.entities.OnlyMeshedBlockEntityRenderer @@ -68,7 +69,7 @@ class SolidCullSectionPreparer( var blockEntity: BlockEntity? var model: SingleBlockRenderable var blockState: BlockState - var position: Vec3i + val position = BlockPosition() var rendered: Boolean var tints: IntArray? val neighbourBlocks: Array = arrayOfNulls(Directions.SIZE) @@ -79,8 +80,10 @@ class SolidCullSectionPreparer( val offsetZ = chunkPosition.y * ProtocolDefinition.SECTION_WIDTH_Z for (y in 0 until ProtocolDefinition.SECTION_HEIGHT_Y) { + position.y = offsetY + y val fastBedrock = y == 0 && isLowestSection && fastBedrock for (x in 0 until ProtocolDefinition.SECTION_WIDTH_X) { + position.x = offsetX + x for (z in 0 until ProtocolDefinition.SECTION_WIDTH_Z) { val baseIndex = (z shl 4) or x val index = (y shl 8) or baseIndex @@ -89,7 +92,7 @@ class SolidCullSectionPreparer( continue } light[SELF_LIGHT_INDEX] = sectionLight[index] - position = Vec3i(offsetX + x, offsetY + y, offsetZ + z) + position.z = offsetZ + z val maxHeight = chunk.skylightHeightmap[baseIndex] if (position.y >= maxHeight) { @@ -152,7 +155,7 @@ class SolidCullSectionPreparer( } if (randomBlockModels) { - random.setSeed(VecUtil.generatePositionHash(position.x, position.y, position.z)) + random.setSeed(position.positionHash) } else { random.setSeed(0L) } @@ -205,11 +208,11 @@ class SolidCullSectionPreparer( } private inline fun setNeighbour(neighbourBlocks: Array, x: Int, y: Int, z: Int, light: ByteArray, position: Vec3i, blocks: BlockSectionDataProvider?, sectionLight: SectionLight, chunk: Chunk, ordinal: Int) { - val nextBaseIndex = (z shl 4) or x - val neighbourIndex = y shl 8 or nextBaseIndex + val heightmapIndex = (z shl 4) or x + val neighbourIndex = y shl 8 or heightmapIndex neighbourBlocks[ordinal] = blocks?.unsafeGet(neighbourIndex) light[ordinal] = sectionLight[neighbourIndex] - if (position.y > chunk.skylightHeightmap[nextBaseIndex]) { + if (position.y > chunk.skylightHeightmap[heightmapIndex]) { light[ordinal] = (light[ordinal].toInt() or 0xF0).toByte() } } diff --git a/src/main/java/de/bixilon/minosoft/util/KUtil.kt b/src/main/java/de/bixilon/minosoft/util/KUtil.kt index 06f4e51db..55af632b5 100644 --- a/src/main/java/de/bixilon/minosoft/util/KUtil.kt +++ b/src/main/java/de/bixilon/minosoft/util/KUtil.kt @@ -322,4 +322,11 @@ object KUtil { this[index] = value return true } + + inline fun IntArray.getOrElse(index: Int, `else`: Int): Int { + if (index < 0 || index >= this.size) { + return `else` + } + return this[index] + } } diff --git a/src/main/java/de/bixilon/minosoft/util/collections/bytes/HeapArrayByteList.kt b/src/main/java/de/bixilon/minosoft/util/collections/bytes/HeapArrayByteList.kt index 442879323..fdd76943a 100644 --- a/src/main/java/de/bixilon/minosoft/util/collections/bytes/HeapArrayByteList.kt +++ b/src/main/java/de/bixilon/minosoft/util/collections/bytes/HeapArrayByteList.kt @@ -1,15 +1,15 @@ /* -* Minosoft -* Copyright (C) 2021 Moritz Zwerger -* -* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. -* -* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License along with this program. If not, see . -* -* This software is not affiliated with Mojang AB, the original developer of Minecraft. -*/ + * Minosoft + * Copyright (C) 2020-2022 Moritz Zwerger + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + * + * This software is not affiliated with Mojang AB, the original developer of Minecraft. + */ package de.bixilon.minosoft.util.collections.bytes class HeapArrayByteList( @@ -53,22 +53,30 @@ class HeapArrayByteList( while (newSize - size < needed) { newSize += nextGrowStep } + grow(newSize) + } + + private fun grow(size: Int) { val oldData = data - data = ByteArray(newSize) + data = ByteArray(size) System.arraycopy(oldData, 0, data, 0, oldData.size) } override fun add(value: Byte) { ensureSize(1) data[size++] = value - outputUpToDate = false + if (outputUpToDate) { + outputUpToDate = false + } } override fun addAll(bytes: ByteArray) { ensureSize(bytes.size) System.arraycopy(bytes, 0, data, size, bytes.size) size += bytes.size - outputUpToDate = false + if (outputUpToDate) { + outputUpToDate = false + } } override fun addAll(byteList: AbstractByteList) { @@ -84,6 +92,10 @@ class HeapArrayByteList( } System.arraycopy(source, 0, data, size, byteList.size) size += byteList.size + + if (outputUpToDate) { + outputUpToDate = false + } } private fun checkOutputArray() { diff --git a/src/main/java/de/bixilon/minosoft/util/collections/floats/DirectArrayFloatList.kt b/src/main/java/de/bixilon/minosoft/util/collections/floats/DirectArrayFloatList.kt index 516baf958..cb40487bd 100644 --- a/src/main/java/de/bixilon/minosoft/util/collections/floats/DirectArrayFloatList.kt +++ b/src/main/java/de/bixilon/minosoft/util/collections/floats/DirectArrayFloatList.kt @@ -52,9 +52,13 @@ class DirectArrayFloatList( } else { nextGrowStep } + grow(newSize) + } + + private fun grow(size: Int) { val oldBuffer = buffer - buffer = memAllocFloat(newSize) - limit = newSize + buffer = memAllocFloat(size) + limit = size if (FLOAT_PUT_METHOD == null) { // Java < 16 for (i in 0 until oldBuffer.position()) { buffer.put(oldBuffer.get(i)) @@ -69,7 +73,9 @@ class DirectArrayFloatList( override fun add(value: Float) { ensureSize(1) buffer.put(value) - outputUpToDate = false + if (outputUpToDate) { + outputUpToDate = false + } } override fun addAll(floats: FloatArray) { @@ -81,7 +87,9 @@ class DirectArrayFloatList( exception.printStackTrace() } - outputUpToDate = false + if (outputUpToDate) { + outputUpToDate = false + } } override fun addAll(floatList: AbstractFloatList) { diff --git a/src/main/java/de/bixilon/minosoft/util/collections/floats/HeapArrayFloatList.kt b/src/main/java/de/bixilon/minosoft/util/collections/floats/HeapArrayFloatList.kt index baeb087ec..818d76c35 100644 --- a/src/main/java/de/bixilon/minosoft/util/collections/floats/HeapArrayFloatList.kt +++ b/src/main/java/de/bixilon/minosoft/util/collections/floats/HeapArrayFloatList.kt @@ -1,15 +1,15 @@ /* -* Minosoft -* Copyright (C) 2021 Moritz Zwerger -* -* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. -* -* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License along with this program. If not, see . -* -* This software is not affiliated with Mojang AB, the original developer of Minecraft. -*/ + * Minosoft + * Copyright (C) 2020-2022 Moritz Zwerger + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + * + * This software is not affiliated with Mojang AB, the original developer of Minecraft. + */ package de.bixilon.minosoft.util.collections.floats class HeapArrayFloatList( @@ -53,22 +53,30 @@ class HeapArrayFloatList( while (newSize - size < needed) { newSize += nextGrowStep } + grow(newSize) + } + + private fun grow(size: Int) { val oldData = data - data = FloatArray(newSize) + data = FloatArray(size) System.arraycopy(oldData, 0, data, 0, oldData.size) } override fun add(value: Float) { ensureSize(1) data[size++] = value - outputUpToDate = false + if (outputUpToDate) { + outputUpToDate = false + } } override fun addAll(floats: FloatArray) { ensureSize(floats.size) System.arraycopy(floats, 0, data, size, floats.size) size += floats.size - outputUpToDate = false + if (outputUpToDate) { + outputUpToDate = false + } } override fun addAll(floatList: AbstractFloatList) { @@ -84,6 +92,9 @@ class HeapArrayFloatList( } System.arraycopy(source, 0, data, size, floatList.size) size += floatList.size + if (outputUpToDate) { + outputUpToDate = false + } } private fun checkOutputArray() {