world rendering: reduce memory footprint, improve performance

This commit is contained in:
Bixilon 2022-09-02 19:31:44 +02:00
parent f9e779e6ee
commit dce90431ee
No known key found for this signature in database
GPG Key ID: 5CAD791931B09AC4
5 changed files with 38 additions and 24 deletions

View File

@ -142,32 +142,31 @@ enum class BlockProperties {
val map: MutableMap<String, MutableList<BlockProperties>> = mutableMapOf()
for (value in values()) {
val list = map.getOrPut(value.group) { mutableListOf() }
list.add(value)
map.getOrPut(value.group) { mutableListOf() } += value
}
return@run map
}
fun parseProperty(group: String, value: Any): Pair<BlockProperties, Any> {
PROPERTIES[group]?.let {
var retProperty: BlockProperties? = null
var retValue: Any? = null
val properties = PROPERTIES[group] ?: throw IllegalArgumentException("Can not find group: $group, expected value $value")
for (blockProperty in it) {
retValue = try {
blockProperty.serializer.deserialize(value)
} catch (exception: Throwable) {
continue
}
retProperty = blockProperty
}
var property: BlockProperties? = null
var retValue: Any? = null
if (retProperty == null || retValue == null) {
throw IllegalArgumentException("Can not parse value $value for group $group")
for (blockProperty in properties) {
retValue = try {
blockProperty.serializer.deserialize(value)
} catch (exception: Throwable) {
continue
}
return Pair(retProperty, retValue)
} ?: throw IllegalArgumentException("Can not find group: $group, expected value $value")
property = blockProperty
}
if (property == null || retValue == null) {
throw IllegalArgumentException("Can not parse value $value for group $group")
}
return Pair(property, retValue)
}
}
}

View File

@ -69,7 +69,7 @@ interface ChatComponentRenderer<T : ChatComponent> {
val textMesh = mesh.textMesh!!
val primitives = calculatePrimitiveCount(text)
textMesh.data.ensureSize(primitives * textMesh.order.size * SingleWorldMesh.SectionArrayMeshStruct.FLOATS_PER_VERTEX)
textMesh.data.ensureSize(primitives * textMesh.order.size * SingleWorldMesh.WorldMeshStruct.FLOATS_PER_VERTEX)
val consumer = WorldGUIConsumer(textMesh, matrix, light)
render3dFlat(renderWindow, Vec2i(), scale, maxSize, consumer, text, light)

View File

@ -47,10 +47,12 @@ class BakedFace(
color.g *= ((tint shr 8) and 0xFF) / RGBColor.COLOR_FLOAT_DIVIDER
color.b *= (tint and 0xFF) / RGBColor.COLOR_FLOAT_DIVIDER
}
val rgb = color.rgb
val textureShaderId = Float.fromBits(texture.renderData.shaderTextureId)
val tintLight = Float.fromBits(color.rgb or (light shl 24))
for ((index, textureIndex) in meshToUse.order) {
val indexOffset = index * 3
meshToUse.addVertex(floatArrayOf(positions[indexOffset + 0] + position[0], positions[indexOffset + 1] + position[1], positions[indexOffset + 2] + position[2]), uv[textureIndex], texture, rgb, light)
meshToUse.addVertex(positions[indexOffset + 0] + position[0], positions[indexOffset + 1] + position[1], positions[indexOffset + 2] + position[2], uv[textureIndex], texture, textureShaderId, tintLight)
}
}
}

View File

@ -64,7 +64,7 @@ class SignBlockEntityRenderer(
for (line in sign.lines) {
primitives += ChatComponentRenderer.calculatePrimitiveCount(line)
}
textMesh.data.ensureSize(primitives * textMesh.order.size * SingleWorldMesh.SectionArrayMeshStruct.FLOATS_PER_VERTEX)
textMesh.data.ensureSize(primitives * textMesh.order.size * SingleWorldMesh.WorldMeshStruct.FLOATS_PER_VERTEX)
for (line in sign.lines) {
ChatComponentRenderer.render3dFlat(renderWindow, textPosition, TEXT_SCALE, Vec3(0.0f, -yRotation, 0.0f), Vec2i(SIGN_MAX_WIDTH * TEXT_SCALE, Font.TOTAL_CHAR_HEIGHT * TEXT_SCALE), mesh, line, light)

View File

@ -20,10 +20,11 @@ import de.bixilon.minosoft.gui.rendering.system.base.texture.texture.AbstractTex
import de.bixilon.minosoft.gui.rendering.util.mesh.Mesh
import de.bixilon.minosoft.gui.rendering.util.mesh.MeshStruct
class SingleWorldMesh(renderWindow: RenderWindow, initialCacheSize: Int, onDemand: Boolean = false) : Mesh(renderWindow, SectionArrayMeshStruct, initialCacheSize = initialCacheSize, onDemand = onDemand) {
class SingleWorldMesh(renderWindow: RenderWindow, initialCacheSize: Int, onDemand: Boolean = false) : Mesh(renderWindow, WorldMeshStruct, initialCacheSize = initialCacheSize, onDemand = onDemand) {
var distance: Float = 0.0f // Used for sorting
fun addVertex(position: FloatArray, uv: Vec2, texture: AbstractTexture, tintColor: Int, light: Int) {
data.ensureSize(WorldMeshStruct.FLOATS_PER_VERTEX)
val transformedUV = texture.renderData.transformUV(uv)
data.add(position[0])
data.add(position[1])
@ -34,13 +35,25 @@ class SingleWorldMesh(renderWindow: RenderWindow, initialCacheSize: Int, onDeman
data.add(Float.fromBits(tintColor or (light shl 24)))
}
fun addVertex(x: Float, y: Float, z: Float, uv: Vec2, texture: AbstractTexture, shaderTextureId: Float, tintLight: Float) {
data.ensureSize(WorldMeshStruct.FLOATS_PER_VERTEX)
val transformedUV = texture.renderData.transformUV(uv)
data.add(x)
data.add(y)
data.add(z)
data.add(transformedUV.x)
data.add(transformedUV.y)
data.add(shaderTextureId)
data.add(tintLight)
}
data class SectionArrayMeshStruct(
data class WorldMeshStruct(
val position: Vec3,
val uv: Vec2,
val indexLayerAnimation: Int,
val tintLight: Int,
) {
companion object : MeshStruct(SectionArrayMeshStruct::class)
companion object : MeshStruct(WorldMeshStruct::class)
}
}