refactor weather and time storing, fix some world bugs #59

This commit is contained in:
Bixilon 2021-12-14 10:14:26 +01:00
parent d4cc972bb2
commit d9fbee2559
No known key found for this signature in database
GPG Key ID: 5CAD791931B09AC4
11 changed files with 69 additions and 48 deletions

View File

@ -22,6 +22,6 @@ object RainGradientSetGameEventHandler : GameEventHandler {
override val RESOURCE_LOCATION: ResourceLocation = "minecraft:rain_gradient_set".toResourceLocation() override val RESOURCE_LOCATION: ResourceLocation = "minecraft:rain_gradient_set".toResourceLocation()
override fun handle(data: Float, connection: PlayConnection) { override fun handle(data: Float, connection: PlayConnection) {
connection.world.rainGradient = data connection.world.weather.rainGradient = data
} }
} }

View File

@ -22,6 +22,6 @@ object ThunderGradientSetGameEventHandler : GameEventHandler {
override val RESOURCE_LOCATION: ResourceLocation = "minecraft:thunder_gradient_set".toResourceLocation() override val RESOURCE_LOCATION: ResourceLocation = "minecraft:thunder_gradient_set".toResourceLocation()
override fun handle(data: Float, connection: PlayConnection) { override fun handle(data: Float, connection: PlayConnection) {
connection.world.thunderGradient = data connection.world.weather.thunderGradient = data
} }
} }

View File

@ -22,7 +22,7 @@ object RainStartGameEventHandler : GameEventHandler {
override val RESOURCE_LOCATION: ResourceLocation = "minecraft:rain_start".toResourceLocation() override val RESOURCE_LOCATION: ResourceLocation = "minecraft:rain_start".toResourceLocation()
override fun handle(data: Float, connection: PlayConnection) { override fun handle(data: Float, connection: PlayConnection) {
connection.world.raining = true connection.world.weather.raining = true
connection.world.rainGradient = 1.0f connection.world.weather.rainGradient = 1.0f
} }
} }

View File

@ -22,7 +22,7 @@ object RainStopGameEventHandler : GameEventHandler {
override val RESOURCE_LOCATION: ResourceLocation = "minecraft:rain_stop".toResourceLocation() override val RESOURCE_LOCATION: ResourceLocation = "minecraft:rain_stop".toResourceLocation()
override fun handle(data: Float, connection: PlayConnection) { override fun handle(data: Float, connection: PlayConnection) {
connection.world.raining = false connection.world.weather.raining = false
connection.world.rainGradient = 0.0f connection.world.weather.rainGradient = 0.0f
} }
} }

View File

@ -22,7 +22,9 @@ import de.bixilon.minosoft.data.registries.blocks.types.FluidBlock
import de.bixilon.minosoft.data.registries.dimension.DimensionProperties import de.bixilon.minosoft.data.registries.dimension.DimensionProperties
import de.bixilon.minosoft.data.world.biome.accessor.BiomeAccessor import de.bixilon.minosoft.data.world.biome.accessor.BiomeAccessor
import de.bixilon.minosoft.data.world.biome.accessor.NoiseBiomeAccessor import de.bixilon.minosoft.data.world.biome.accessor.NoiseBiomeAccessor
import de.bixilon.minosoft.data.world.time.WorldTime
import de.bixilon.minosoft.data.world.view.WorldView import de.bixilon.minosoft.data.world.view.WorldView
import de.bixilon.minosoft.data.world.weather.WorldWeather
import de.bixilon.minosoft.gui.rendering.particle.ParticleRenderer import de.bixilon.minosoft.gui.rendering.particle.ParticleRenderer
import de.bixilon.minosoft.gui.rendering.particle.types.Particle import de.bixilon.minosoft.gui.rendering.particle.types.Particle
import de.bixilon.minosoft.gui.rendering.util.VecUtil.blockPosition import de.bixilon.minosoft.gui.rendering.util.VecUtil.blockPosition
@ -35,10 +37,8 @@ import de.bixilon.minosoft.modding.event.events.BlockSetEvent
import de.bixilon.minosoft.modding.event.events.ChunkDataChangeEvent import de.bixilon.minosoft.modding.event.events.ChunkDataChangeEvent
import de.bixilon.minosoft.modding.event.events.ChunkUnloadEvent import de.bixilon.minosoft.modding.event.events.ChunkUnloadEvent
import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection
import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition
import de.bixilon.minosoft.util.KUtil.lockMapOf import de.bixilon.minosoft.util.KUtil.lockMapOf
import de.bixilon.minosoft.util.KUtil.toSynchronizedMap import de.bixilon.minosoft.util.KUtil.toSynchronizedMap
import de.bixilon.minosoft.util.MMath
import de.bixilon.minosoft.util.ReadWriteLock import de.bixilon.minosoft.util.ReadWriteLock
import de.bixilon.minosoft.util.chunk.ChunkUtil.canBuildBiomeCache import de.bixilon.minosoft.util.chunk.ChunkUtil.canBuildBiomeCache
import de.bixilon.minosoft.util.chunk.ChunkUtil.getChunkNeighbourPositions import de.bixilon.minosoft.util.chunk.ChunkUtil.getChunkNeighbourPositions
@ -46,13 +46,9 @@ import de.bixilon.minosoft.util.chunk.ChunkUtil.isInViewDistance
import de.bixilon.minosoft.util.chunk.ChunkUtil.received import de.bixilon.minosoft.util.chunk.ChunkUtil.received
import de.bixilon.minosoft.util.collections.LockMap import de.bixilon.minosoft.util.collections.LockMap
import de.bixilon.minosoft.util.delegate.DelegateManager.delegate import de.bixilon.minosoft.util.delegate.DelegateManager.delegate
import glm_.func.common.clamp
import glm_.vec2.Vec2i import glm_.vec2.Vec2i
import glm_.vec3.Vec3 import glm_.vec3.Vec3
import glm_.vec3.Vec3i import glm_.vec3.Vec3i
import kotlin.math.PI
import kotlin.math.abs
import kotlin.math.cos
import kotlin.random.Random import kotlin.random.Random
/** /**
@ -70,11 +66,8 @@ class World(
var difficulty: Difficulties? = null var difficulty: Difficulties? = null
var difficultyLocked = false var difficultyLocked = false
var hashedSeed = 0L var hashedSeed = 0L
var time = 0L val time = WorldTime(this)
var age = 0L val weather = WorldWeather()
var raining = false
var rainGradient = 0.0f
var thunderGradient = 0.0f
val view = WorldView(connection) val view = WorldView(connection)
private val random = Random private val random = Random
@ -234,25 +227,6 @@ class World(
return get(blockPosition.chunkPosition)?.getLight(blockPosition.inChunkPosition) ?: 0x00 return get(blockPosition.chunkPosition)?.getLight(blockPosition.inChunkPosition) ?: 0x00
} }
val skyAngle: Float
get() {
val fractionalPath = MMath.fractionalPart(abs(time) / ProtocolDefinition.TICKS_PER_DAYf - 0.25)
val angle = 0.5 - cos(fractionalPath * Math.PI) / 2.0
return ((fractionalPath * 2.0 + angle) / 3.0).toFloat()
}
val lightBase: Double
get() {
var base = 1.0f - (cos(skyAngle * 2.0 * PI) * 2.0 + 0.2)
base = base.clamp(0.0, 1.0)
base = 1.0 - base
base *= 1.0 - ((rainGradient * 5.0) / 16.0)
base *= 1.0 - (((thunderGradient * rainGradient) * 5.0) / 16.0)
return base * 0.8 + 0.2
}
/** /**
* @return All 8 neighbour chunks * @return All 8 neighbour chunks
*/ */

View File

@ -0,0 +1,37 @@
package de.bixilon.minosoft.data.world.time
import de.bixilon.minosoft.data.world.World
import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition
import de.bixilon.minosoft.util.MMath
import glm_.func.common.clamp
import kotlin.math.PI
import kotlin.math.abs
import kotlin.math.cos
class WorldTime(
private val world: World,
) {
var time = 0L
var age = 0L
val skyAngle: Float
get() {
val fractionalPath = MMath.fractionalPart(abs(time) / ProtocolDefinition.TICKS_PER_DAYf - 0.25)
val angle = 0.5 - cos(fractionalPath * Math.PI) / 2.0
return ((fractionalPath * 2.0 + angle) / 3.0).toFloat()
}
val lightBase: Double
get() {
var base = 1.0f - (cos(skyAngle * 2.0 * PI) * 2.0 + 0.2)
base = base.clamp(0.0, 1.0)
base = 1.0 - base
base *= 1.0 - ((world.weather.rainGradient * 5.0) / 16.0)
base *= 1.0 - (((world.weather.thunderGradient * world.weather.rainGradient) * 5.0) / 16.0)
return base * 0.8 + 0.2
}
}

View File

@ -0,0 +1,8 @@
package de.bixilon.minosoft.data.world.weather
class WorldWeather {
var raining = false
var rainGradient = 0.0f
var thunderGradient = 0.0f
}

View File

@ -46,7 +46,7 @@ class SkyRenderer(
private val skyboxMesh = SkyboxMesh(renderWindow) private val skyboxMesh = SkyboxMesh(renderWindow)
private var skySunMesh = SimpleTextureMesh(renderWindow) private var skySunMesh = SimpleTextureMesh(renderWindow)
private lateinit var sunTexture: AbstractTexture private lateinit var sunTexture: AbstractTexture
private var sunMatrixUpToDate: Boolean = true private var updateSun: Boolean = true
var baseColor = RenderConstants.DEFAULT_SKY_COLOR var baseColor = RenderConstants.DEFAULT_SKY_COLOR
@ -66,22 +66,21 @@ class SkyRenderer(
} }
}) })
connection.registerEvent(CallbackEventInvoker.of<TimeChangeEvent> { connection.registerEvent(CallbackEventInvoker.of<TimeChangeEvent> {
if (connection.world.time != it.time) { if (connection.world.time.time != it.time) {
sunMatrixUpToDate = true updateSun = true
} }
}) })
sunTexture = renderWindow.textureManager.staticTextures.createTexture(SUN_TEXTURE_RESOURCE_LOCATION) sunTexture = renderWindow.textureManager.staticTextures.createTexture(SUN_TEXTURE_RESOURCE_LOCATION)
} }
private fun setSunMatrix(projectionViewMatrix: Mat4) { private fun setSunMatrix(projectionViewMatrix: Mat4) {
val timeAngle = (connection.world.skyAngle * 360.0f).rad val timeAngle = (connection.world.time.skyAngle * 360.0f).rad
val rotatedMatrix = if (timeAngle == 0.0f) { val rotatedMatrix = if (timeAngle == 0.0f) {
projectionViewMatrix projectionViewMatrix
} else { } else {
projectionViewMatrix.rotate(timeAngle, Vec3(0.0f, 0.0f, 1.0f)) projectionViewMatrix.rotate(timeAngle, Vec3(0.0f, 0.0f, 1.0f))
} }
skySunShader.use().setMat4("uSkyViewProjectionMatrix", rotatedMatrix) skySunShader.use().setMat4("uSkyViewProjectionMatrix", rotatedMatrix)
sunMatrixUpToDate = false
} }
override fun postInit() { override fun postInit() {
@ -89,7 +88,7 @@ class SkyRenderer(
} }
private fun drawSun() { private fun drawSun() {
if (sunMatrixUpToDate) { if (updateSun) {
setSunMatrix(renderWindow.camera.matrixHandler.projectionMatrix * renderWindow.camera.matrixHandler.viewMatrix.toMat3().toMat4()) setSunMatrix(renderWindow.camera.matrixHandler.projectionMatrix * renderWindow.camera.matrixHandler.viewMatrix.toMat3().toMat4())
skySunMesh.unload() skySunMesh.unload()
@ -102,11 +101,12 @@ class SkyRenderer(
position = position, position = position,
texture = sunTexture, texture = sunTexture,
uv = uv, uv = uv,
tintColor = ChatColors.WHITE.with(alpha = 1.0f - connection.world.rainGradient), // ToDo: Depends on time tintColor = ChatColors.WHITE.with(alpha = 1.0f - connection.world.weather.rainGradient), // ToDo: Depends on time
) )
} }
) )
skySunMesh.load() skySunMesh.load()
updateSun = false
} }
renderSystem.enable(RenderingCapabilities.BLENDING) renderSystem.enable(RenderingCapabilities.BLENDING)

View File

@ -29,7 +29,7 @@ import kotlin.math.max
import kotlin.math.pow import kotlin.math.pow
import kotlin.math.sin import kotlin.math.sin
@Deprecated("Needs refactoring")
class LightMap(private val connection: PlayConnection) { class LightMap(private val connection: PlayConnection) {
private val profile = connection.profiles.rendering.light private val profile = connection.profiles.rendering.light
private val nightVisionStatusEffect = connection.registries.statusEffectRegistry[DefaultStatusEffects.NIGHT_VISION] private val nightVisionStatusEffect = connection.registries.statusEffectRegistry[DefaultStatusEffects.NIGHT_VISION]
@ -50,7 +50,7 @@ class LightMap(private val connection: PlayConnection) {
} }
fun update() { fun update() {
val skyGradient = connection.world.lightBase.toFloat() val skyGradient = connection.world.time.lightBase.toFloat()
// ToDo: Lightning // ToDo: Lightning

View File

@ -16,6 +16,7 @@ import de.bixilon.minosoft.modding.event.EventInitiators
import de.bixilon.minosoft.modding.event.events.connection.play.PlayConnectionEvent import de.bixilon.minosoft.modding.event.events.connection.play.PlayConnectionEvent
import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection
import de.bixilon.minosoft.protocol.packets.s2c.play.WorldTimeSetS2CP import de.bixilon.minosoft.protocol.packets.s2c.play.WorldTimeSetS2CP
import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition
class TimeChangeEvent( class TimeChangeEvent(
connection: PlayConnection, connection: PlayConnection,
@ -25,5 +26,5 @@ class TimeChangeEvent(
) : PlayConnectionEvent(connection, initiator) { ) : PlayConnectionEvent(connection, initiator) {
constructor(connection: PlayConnection, packet: WorldTimeSetS2CP) : this(connection, EventInitiators.SERVER, packet.age, packet.time) constructor(connection: PlayConnection, packet: WorldTimeSetS2CP) : this(connection, EventInitiators.SERVER, packet.age, packet.time % ProtocolDefinition.TICKS_PER_DAY)
} }

View File

@ -16,6 +16,7 @@ import de.bixilon.minosoft.modding.event.events.TimeChangeEvent
import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection
import de.bixilon.minosoft.protocol.packets.s2c.PlayS2CPacket import de.bixilon.minosoft.protocol.packets.s2c.PlayS2CPacket
import de.bixilon.minosoft.protocol.protocol.PlayInByteBuffer import de.bixilon.minosoft.protocol.protocol.PlayInByteBuffer
import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition
import de.bixilon.minosoft.util.logging.Log import de.bixilon.minosoft.util.logging.Log
import de.bixilon.minosoft.util.logging.LogLevels import de.bixilon.minosoft.util.logging.LogLevels
import de.bixilon.minosoft.util.logging.LogMessageType import de.bixilon.minosoft.util.logging.LogMessageType
@ -25,8 +26,8 @@ class WorldTimeSetS2CP(buffer: PlayInByteBuffer) : PlayS2CPacket() {
val time = buffer.readLong() val time = buffer.readLong()
override fun handle(connection: PlayConnection) { override fun handle(connection: PlayConnection) {
connection.world.age = age connection.world.time.age = age
connection.world.time = time connection.world.time.time = time % ProtocolDefinition.TICKS_PER_DAY
connection.fireEvent(TimeChangeEvent(connection, this)) connection.fireEvent(TimeChangeEvent(connection, this))
} }