mirror of
https://github.com/curioustorvald/Terrarum.git
synced 2026-06-10 10:34:06 +09:00
fixing "roundworld anomaly": some actors won't render
This commit is contained in:
@@ -1389,31 +1389,28 @@ open class ActorWBMovable(renderOrder: RenderOrder, val immobileBody: Boolean =
|
|||||||
|
|
||||||
// FIXME test me: this extra IF statement is supposed to not draw actors that's outside of the camera.
|
// FIXME test me: this extra IF statement is supposed to not draw actors that's outside of the camera.
|
||||||
// basic code without offsetX/Y DOES work, but obviously offsets are not tested.
|
// basic code without offsetX/Y DOES work, but obviously offsets are not tested.
|
||||||
if (hitbox.startX - offsetX in WorldCamera.x - hitbox.width - offsetX..WorldCamera.x + WorldCamera.width + offsetX &&
|
if (WorldCamera.xCentre > leftsidePadding && centrePosPoint.x <= rightsidePadding) {
|
||||||
hitbox.endY + offsetY in WorldCamera.y - hitbox.height - offsetY..WorldCamera.y + WorldCamera.height + offsetY) {
|
// camera center neg, actor center pos
|
||||||
if (WorldCamera.xCentre > leftsidePadding && centrePosPoint.x <= rightsidePadding) {
|
sprite.render(batch,
|
||||||
// camera center neg, actor center pos
|
(hitbox.startX - offsetX).toFloat() + world!!.width * TILE_SIZE,
|
||||||
sprite.render(batch,
|
(hitbox.startY - offsetY).toFloat(),
|
||||||
(hitbox.startX - offsetX).toFloat() + world!!.width * TILE_SIZE,
|
(scale).toFloat()
|
||||||
(hitbox.startY - offsetY).toFloat(),
|
)
|
||||||
(scale).toFloat()
|
}
|
||||||
)
|
else if (WorldCamera.xCentre < rightsidePadding && centrePosPoint.x >= leftsidePadding) {
|
||||||
}
|
// camera center pos, actor center neg
|
||||||
else if (WorldCamera.xCentre < rightsidePadding && centrePosPoint.x >= leftsidePadding) {
|
sprite.render(batch,
|
||||||
// camera center pos, actor center neg
|
(hitbox.startX - offsetX).toFloat() - world!!.width * TILE_SIZE,
|
||||||
sprite.render(batch,
|
(hitbox.startY - offsetY).toFloat(),
|
||||||
(hitbox.startX - offsetX).toFloat() - world!!.width * TILE_SIZE,
|
(scale).toFloat()
|
||||||
(hitbox.startY - offsetY).toFloat(),
|
)
|
||||||
(scale).toFloat()
|
}
|
||||||
)
|
else {
|
||||||
}
|
sprite.render(batch,
|
||||||
else {
|
(hitbox.startX - offsetX).toFloat(),
|
||||||
sprite.render(batch,
|
(hitbox.startY - offsetY).toFloat(),
|
||||||
(hitbox.startX - offsetX).toFloat(),
|
(scale).toFloat()
|
||||||
(hitbox.startY - offsetY).toFloat(),
|
)
|
||||||
(scale).toFloat()
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -30,6 +30,7 @@ import net.torvald.terrarum.modulebasegame.worldgenerator.WorldGenerator
|
|||||||
import net.torvald.terrarum.ui.ConsoleWindow
|
import net.torvald.terrarum.ui.ConsoleWindow
|
||||||
import net.torvald.terrarum.ui.UICanvas
|
import net.torvald.terrarum.ui.UICanvas
|
||||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
||||||
|
import net.torvald.terrarum.worlddrawer.CreateTileAtlas.TILE_SIZE
|
||||||
import net.torvald.terrarum.worlddrawer.FeaturesDrawer
|
import net.torvald.terrarum.worlddrawer.FeaturesDrawer
|
||||||
import net.torvald.terrarum.worlddrawer.LightmapRenderer
|
import net.torvald.terrarum.worlddrawer.LightmapRenderer
|
||||||
import net.torvald.terrarum.worlddrawer.WorldCamera
|
import net.torvald.terrarum.worlddrawer.WorldCamera
|
||||||
@@ -475,8 +476,12 @@ open class Ingame(batch: SpriteBatch) : IngameInstance(batch) {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private var worldWidth: Double = 0.0
|
||||||
|
|
||||||
|
|
||||||
protected fun updateGame(delta: Float) {
|
protected fun updateGame(delta: Float) {
|
||||||
val world = this.world as GameWorldExtension
|
val world = this.world as GameWorldExtension
|
||||||
|
worldWidth = world.width.toDouble() * TILE_SIZE
|
||||||
|
|
||||||
particlesActive = 0
|
particlesActive = 0
|
||||||
|
|
||||||
@@ -570,6 +575,8 @@ open class Ingame(batch: SpriteBatch) : IngameInstance(batch) {
|
|||||||
visibleActorsRenderMidTop = actorsRenderMidTop.filter { it.inScreen() }
|
visibleActorsRenderMidTop = actorsRenderMidTop.filter { it.inScreen() }
|
||||||
visibleActorsRenderFront = actorsRenderFront.filter { it.inScreen() }
|
visibleActorsRenderFront = actorsRenderFront.filter { it.inScreen() }
|
||||||
visibleActorsRenderOverlay=actorsRenderOverlay.filter { it.inScreen() }
|
visibleActorsRenderOverlay=actorsRenderOverlay.filter { it.inScreen() }
|
||||||
|
|
||||||
|
//printdbg(this, "total visible actors: ${visibleActorsRenderMiddle.size}")
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun repossessActor() {
|
private fun repossessActor() {
|
||||||
@@ -716,31 +723,40 @@ open class Ingame(batch: SpriteBatch) : IngameInstance(batch) {
|
|||||||
private fun distToActorSqr(a: ActorWithBody, p: ActorWithBody) =
|
private fun distToActorSqr(a: ActorWithBody, p: ActorWithBody) =
|
||||||
min(// take min of normal position and wrapped (x < 0) position
|
min(// take min of normal position and wrapped (x < 0) position
|
||||||
(a.hitbox.centeredX - p.hitbox.centeredX).sqr() +
|
(a.hitbox.centeredX - p.hitbox.centeredX).sqr() +
|
||||||
(a.hitbox.centeredY - p.hitbox.centeredY).sqr(),
|
(a.hitbox.centeredY - p.hitbox.centeredY).sqr(),
|
||||||
(a.hitbox.centeredX - p.hitbox.centeredX + world.width * CreateTileAtlas.TILE_SIZE).sqr() +
|
((a.hitbox.centeredX + world.width * CreateTileAtlas.TILE_SIZE) - p.hitbox.centeredX).sqr() +
|
||||||
(a.hitbox.centeredY - p.hitbox.centeredY).sqr(),
|
(a.hitbox.centeredY - p.hitbox.centeredY).sqr(),
|
||||||
(a.hitbox.centeredX - p.hitbox.centeredX - world.width * CreateTileAtlas.TILE_SIZE).sqr() +
|
((a.hitbox.centeredX - world.width * CreateTileAtlas.TILE_SIZE) - p.hitbox.centeredX).sqr() +
|
||||||
(a.hitbox.centeredY - p.hitbox.centeredY).sqr()
|
(a.hitbox.centeredY - p.hitbox.centeredY).sqr()
|
||||||
)
|
)
|
||||||
private fun distToCameraSqr(a: ActorWithBody) =
|
private fun distToCameraSqr(a: ActorWithBody) =
|
||||||
min(
|
min(
|
||||||
(a.hitbox.startX - WorldCamera.x).sqr() +
|
(a.hitbox.centeredX - WorldCamera.xCentre).sqr() +
|
||||||
(a.hitbox.startY - WorldCamera.y).sqr(),
|
(a.hitbox.centeredY - WorldCamera.yCentre).sqr(),
|
||||||
(a.hitbox.startX - WorldCamera.x + world.width * CreateTileAtlas.TILE_SIZE).sqr() +
|
((a.hitbox.centeredX + world.width * CreateTileAtlas.TILE_SIZE) - WorldCamera.xCentre).sqr() +
|
||||||
(a.hitbox.startY - WorldCamera.y).sqr(),
|
(a.hitbox.centeredY - WorldCamera.yCentre).sqr(),
|
||||||
(a.hitbox.startX - WorldCamera.x - world.width * CreateTileAtlas.TILE_SIZE).sqr() +
|
((a.hitbox.centeredX - world.width * CreateTileAtlas.TILE_SIZE) - WorldCamera.xCentre).sqr() +
|
||||||
(a.hitbox.startY - WorldCamera.y).sqr()
|
(a.hitbox.centeredY - WorldCamera.yCentre).sqr()
|
||||||
)
|
)
|
||||||
|
|
||||||
/** whether the actor is within screen */
|
/** whether the actor is within screen */
|
||||||
// FIXME "roundworld anomaly"
|
|
||||||
private fun ActorWithBody.inScreen() =
|
private fun ActorWithBody.inScreen() =
|
||||||
distToCameraSqr(this) <=
|
|
||||||
(Terrarum.WIDTH.plus(this.hitbox.width.div(2)).
|
|
||||||
times(1 / screenZoom).sqr() +
|
|
||||||
Terrarum.HEIGHT.plus(this.hitbox.height.div(2)).
|
|
||||||
times(1 / screenZoom).sqr())
|
|
||||||
|
|
||||||
|
// y
|
||||||
|
this.hitbox.endY >= WorldCamera.y && this.hitbox.startY <= WorldCamera.yEnd
|
||||||
|
|
||||||
|
&&
|
||||||
|
|
||||||
|
// x: camera is on the right side of the seam
|
||||||
|
((this.hitbox.endX - worldWidth >= WorldCamera.x && this.hitbox.startX - worldWidth <= WorldCamera.xEnd) ||
|
||||||
|
// x: camera in on the left side of the seam
|
||||||
|
(this.hitbox.endX + worldWidth >= WorldCamera.x && this.hitbox.startX + worldWidth <= WorldCamera.xEnd) ||
|
||||||
|
// x: neither
|
||||||
|
(this.hitbox.endX >= WorldCamera.x && this.hitbox.startX <= WorldCamera.xEnd))
|
||||||
|
|
||||||
|
|
||||||
|
private val cameraWindowX = WorldCamera.x.toDouble()..WorldCamera.xEnd.toDouble()
|
||||||
|
private val cameraWindowY = WorldCamera.y.toDouble()..WorldCamera.yEnd.toDouble()
|
||||||
|
|
||||||
/** whether the actor is within update range */
|
/** whether the actor is within update range */
|
||||||
private fun ActorWithBody.inUpdateRange() = distToCameraSqr(this) <= ACTOR_UPDATE_RANGE.sqr()
|
private fun ActorWithBody.inUpdateRange() = distToCameraSqr(this) <= ACTOR_UPDATE_RANGE.sqr()
|
||||||
|
|||||||
@@ -49,7 +49,14 @@ open class FixtureBase(blockBox0: BlockBox, val blockBoxProps: BlockBoxProps = B
|
|||||||
|
|
||||||
for (x in posX until posX + blockBox.width) {
|
for (x in posX until posX + blockBox.width) {
|
||||||
for (y in posY until posY + blockBox.height) {
|
for (y in posY until posY + blockBox.height) {
|
||||||
world.setTileTerrain(x, y, blockBox.collisionType)
|
if (blockBox.collisionType == BlockBox.ALLOW_MOVE_DOWN) {
|
||||||
|
// if the collision type is allow_move_down, only the top surface tile should be "the platform"
|
||||||
|
// lower part must not have such property (think of the table!)
|
||||||
|
// TODO does this ACTUALLY work ?!
|
||||||
|
world.setTileTerrain(x, y, if (y == posY) BlockBox.ALLOW_MOVE_DOWN else BlockBox.NO_COLLISION)
|
||||||
|
}
|
||||||
|
else
|
||||||
|
world.setTileTerrain(x, y, blockBox.collisionType)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -67,7 +74,6 @@ open class FixtureBase(blockBox0: BlockBox, val blockBoxProps: BlockBoxProps = B
|
|||||||
|
|
||||||
return true // TODO for the tests' sake, just get fucking spawned
|
return true // TODO for the tests' sake, just get fucking spawned
|
||||||
|
|
||||||
// FIXME has "roundworld anomaly"; check 'ActorWithBody.inScreen()'
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -17,6 +17,10 @@ object WorldCamera {
|
|||||||
private set
|
private set
|
||||||
var y: Int = 0 // top position
|
var y: Int = 0 // top position
|
||||||
private set
|
private set
|
||||||
|
var xEnd: Int = 0 // right position
|
||||||
|
private set
|
||||||
|
var yEnd: Int = 0 // bottom position
|
||||||
|
private set
|
||||||
inline val gdxCamX: Float // centre position
|
inline val gdxCamX: Float // centre position
|
||||||
get() = xCentre.toFloat()
|
get() = xCentre.toFloat()
|
||||||
inline val gdxCamY: Float// centre position
|
inline val gdxCamY: Float// centre position
|
||||||
@@ -53,6 +57,8 @@ object WorldCamera {
|
|||||||
world.height * TILE_SIZE - height - TILE_SIZE.toFloat()
|
world.height * TILE_SIZE - height - TILE_SIZE.toFloat()
|
||||||
)).floorInt().clampCameraY(world)
|
)).floorInt().clampCameraY(world)
|
||||||
|
|
||||||
|
xEnd = x + width
|
||||||
|
yEnd = y + height
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun Int.clampCameraY(world: GameWorld): Int {
|
private fun Int.clampCameraY(world: GameWorld): Int {
|
||||||
|
|||||||
Reference in New Issue
Block a user