Skip to content

Commit 3664522

Browse files
committed
fix virtualization bugs
1 parent 77ec591 commit 3664522

File tree

3 files changed

+31
-22
lines changed

3 files changed

+31
-22
lines changed

src/main/kotlin/solve/rendering/engine/core/renderers/FramesRenderer.kt

Lines changed: 20 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -27,15 +27,18 @@ import solve.scene.controller.SceneController
2727
import solve.scene.model.VisualizationFrame
2828
import solve.utils.ceilToInt
2929
import java.util.concurrent.CopyOnWriteArrayList
30+
import kotlin.io.path.nameWithoutExtension
3031
import kotlin.math.abs
32+
import kotlin.math.max
3133
import kotlin.math.min
3234

3335
class FramesRenderer(
3436
window: Window
3537
) : Renderer(window) {
3638
private data class LoadedBufferFrameData(
3739
val textureData: Texture2DData,
38-
val bufferIndex: Int
40+
val bufferIndex: Int,
41+
val name: String
3942
)
4043

4144
override val maxBatchSize = 1000
@@ -56,7 +59,7 @@ class FramesRenderer(
5659
private val framesRatio: Float
5760
get() = framesWidth.toFloat() / framesHeight.toFloat()
5861

59-
private var cameraLastGridCellPosition = getScreenCenterGridCellPosition()
62+
private var cameraLastGridCellPosition = getScreenTopLeftGridCellPosition()
6063

6164
private val bufferFramesToUpload = CopyOnWriteArrayList<LoadedBufferFrameData>(mutableListOf())
6265
private val framesLoadingCoroutineScope = CoroutineScope(Dispatchers.Default)
@@ -77,6 +80,7 @@ class FramesRenderer(
7780
}
7881

7982
this.gridWidth = min(gridWidth, selectedFrames.count())
83+
haveNewFramesSelection = true
8084
}
8185

8286
fun setNewSceneFrames(frames: List<VisualizationFrame>) {
@@ -112,7 +116,7 @@ class FramesRenderer(
112116
shaderProgram.uploadVector2i(BuffersSizeUniformName, buffersSize)
113117
shaderProgram.uploadInt(TexturesArrayUniformName, 0)
114118
shaderProgram.uploadFloat(TexturesRatioUniformName, framesRatio)
115-
shaderProgram.uploadVector2f(CameraPositionUniformName, getScreenCenterGridCellPosition().toFloatVector())
119+
shaderProgram.uploadVector2f(CameraPositionUniformName, getScreenTopLeftGridCellPosition().toFloatVector())
116120
}
117121

118122
override fun createNewBatch(zIndex: Int) =
@@ -154,7 +158,7 @@ class FramesRenderer(
154158
}
155159

156160
private fun enableVirtualization() {
157-
cameraLastGridCellPosition = getScreenCenterGridCellPosition()
161+
cameraLastGridCellPosition = getScreenTopLeftGridCellPosition()
158162
isVirtualizationEnabled = true
159163
}
160164

@@ -173,7 +177,7 @@ class FramesRenderer(
173177
}
174178

175179
private fun updateBuffersTextures() {
176-
val cameraGridCellPosition = getScreenCenterGridCellPosition()
180+
val cameraGridCellPosition = getScreenTopLeftGridCellPosition()
177181
if (cameraGridCellPosition != cameraLastGridCellPosition) {
178182
loadNewTexturesToBuffers(cameraGridCellPosition)
179183
}
@@ -194,30 +198,26 @@ class FramesRenderer(
194198
val rectHeight: Int
195199
if (gridCellPositionDelta.x != 0) {
196200
rectWidth = abs(gridCellPositionDelta.x)
197-
rectHeight = buffersSize.y
201+
rectHeight = min(buffersSize.y, gridHeight)
198202
} else {
199203
rectHeight = abs(gridCellPositionDelta.y)
200-
rectWidth = buffersSize.x
204+
rectWidth = min(buffersSize.x, gridWidth)
201205
}
202206
val newFramesRect = IntRect(
203207
if (gridCellPositionDelta.x > 0) {
204208
cameraPosition.x + buffersSize.x - gridCellPositionDelta.x
205209
} else {
206-
cameraPosition.x
210+
max(0, cameraPosition.x)
207211
},
208212
if (gridCellPositionDelta.y > 0) {
209213
cameraPosition.y + buffersSize.y - gridCellPositionDelta.y
210214
} else {
211-
cameraPosition.y
215+
max(0, cameraPosition.y)
212216
},
213217
rectWidth,
214218
rectHeight
215219
)
216-
if (newFramesRect.x0 > 0 && newFramesRect.x1 < gridWidth &&
217-
newFramesRect.y0 > 0 && newFramesRect.y1 < gridHeight
218-
) {
219220
loadRectFramesToBuffers(newFramesRect)
220-
}
221221
}
222222

223223
private fun getFramesAtRect(rect: IntRect): List<List<VisualizationFrame>> {
@@ -245,17 +245,22 @@ class FramesRenderer(
245245
}
246246

247247
val buffersOffset = Vector2i(framesRect.x0 % buffersSize.x, framesRect.y0 % buffersSize.y)
248+
val uploadedBuffersIndices = mutableSetOf<Int>()
248249

249250
for (y in 0 until rectFrames.count()) {
250251
for (x in 0 until rectFrames[y].count()) {
251252
val textureBuffersIndex =
252253
((buffersOffset.y + y) % buffersSize.y) * buffersSize.x + (buffersOffset.x + x) % buffersSize.x
254+
if (uploadedBuffersIndices.contains(textureBuffersIndex))
255+
continue
256+
253257
uploadFrameToBuffersArray(rectFrames[y][x], textureBuffersIndex)
258+
uploadedBuffersIndices.add(textureBuffersIndex)
254259
}
255260
}
256261
}
257262

258-
private fun getScreenCenterGridCellPosition(): Vector2i {
263+
private fun getScreenTopLeftGridCellPosition(): Vector2i {
259264
val cameraGridCellPosition = Vector2f(window.camera.position.x / framesRatio, window.camera.position.y)
260265
return (cameraGridCellPosition - Vector2f(buffersSize) / 2f).toIntVector()
261266
}
@@ -291,7 +296,7 @@ class FramesRenderer(
291296
return@launch
292297
}
293298

294-
bufferFramesToUpload.add(LoadedBufferFrameData(textureData, index))
299+
bufferFramesToUpload.add(LoadedBufferFrameData(textureData, index, frame.imagePath.nameWithoutExtension))
295300
}
296301
}
297302

src/main/kotlin/solve/scene/SceneFacade.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ import tornadofx.find
2626
*/
2727
object SceneFacade {
2828
val lastVisualizationKeepSettingsProperty = SimpleObjectProperty(true)
29-
private var lastVisualizationKeepSettings: Boolean
29+
var lastVisualizationKeepSettings: Boolean
3030
get() = lastVisualizationKeepSettingsProperty.value
3131
private set(value) {
3232
lastVisualizationKeepSettingsProperty.value = value

src/main/kotlin/solve/scene/view/SceneView.kt

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -30,12 +30,16 @@ class SceneView : View() {
3030
override val root = canvas.canvas
3131

3232
private val projectChangedEventHandler = InvalidationListener {
33-
val framesSize = controller.scene.frameSize
34-
val framesSizeVector = Vector2i(framesSize.width.toInt(), framesSize.height.toInt())
35-
canvas.setNewSceneFrames(controller.scene.frames, framesSizeVector)
33+
3634
}
37-
private val framesChangedEventHandler = InvalidationListener {
38-
canvas.setFramesSelection(controller.scene.frames)
35+
private val sceneChangedEventHandler = InvalidationListener {
36+
if (SceneFacade.lastVisualizationKeepSettings) {
37+
canvas.setFramesSelection(controller.scene.frames)
38+
} else {
39+
val framesSize = controller.scene.frameSize
40+
val framesSizeVector = Vector2i(framesSize.width.toInt(), framesSize.height.toInt())
41+
canvas.setNewSceneFrames(controller.scene.frames, framesSizeVector)
42+
}
3943
}
4044

4145
init {
@@ -52,7 +56,7 @@ class SceneView : View() {
5256

5357
private fun addSceneFramesBindings() {
5458
SceneFacade.lastVisualizationKeepSettingsProperty.addListener(projectChangedEventHandler)
55-
controller.sceneProperty.addListener(framesChangedEventHandler)
59+
controller.sceneProperty.addListener(sceneChangedEventHandler)
5660
}
5761

5862
private fun addSceneParamsBindings() {

0 commit comments

Comments
 (0)