Двухуровневый кеш текстур
This commit is contained in:
parent
0910b093f8
commit
952f245e8f
@ -6,7 +6,6 @@ import org.apache.logging.log4j.LogManager
|
||||
import org.lwjgl.opengl.GL
|
||||
import org.lwjgl.opengl.GL46.*
|
||||
import org.lwjgl.opengl.GLCapabilities
|
||||
import ru.dbotthepony.kstarbound.api.ISBFileLocator
|
||||
import ru.dbotthepony.kstarbound.client.StarboundClient
|
||||
import ru.dbotthepony.kstarbound.client.freetype.FreeType
|
||||
import ru.dbotthepony.kstarbound.client.freetype.InvalidArgumentException
|
||||
@ -28,10 +27,8 @@ import java.lang.ref.Cleaner
|
||||
import java.lang.ref.WeakReference
|
||||
import java.time.Duration
|
||||
import java.util.*
|
||||
import java.util.concurrent.ThreadFactory
|
||||
import java.util.concurrent.locks.LockSupport
|
||||
import kotlin.collections.ArrayList
|
||||
import kotlin.collections.HashMap
|
||||
import kotlin.math.roundToInt
|
||||
import kotlin.properties.ReadWriteProperty
|
||||
import kotlin.reflect.KProperty
|
||||
@ -435,22 +432,27 @@ class GLStateTracker(val client: StarboundClient) {
|
||||
fun newVAO() = VertexArrayObject(this)
|
||||
fun newTexture(name: String = "<unknown>") = GLTexture2D(this, name)
|
||||
|
||||
/**
|
||||
* Так как текстуры не занимают память в куче JVM, а только видеопамять, то
|
||||
* такой кеш довольно хрупкий
|
||||
*/
|
||||
private val named2DTextures: Cache<String, GLTexture2D> = Caffeine.newBuilder()
|
||||
// минимальное время хранения 5 минут и...
|
||||
private val named2DTextures0: Cache<String, GLTexture2D> = Caffeine.newBuilder()
|
||||
.softValues()
|
||||
.expireAfterAccess(Duration.ofMinutes(5))
|
||||
.build()
|
||||
|
||||
// ...бесконечное хранение пока кто-то все ещё использует текстуру
|
||||
private val named2DTextures1: Cache<String, GLTexture2D> = Caffeine.newBuilder()
|
||||
.weakValues()
|
||||
.build()
|
||||
|
||||
init {
|
||||
val ref = WeakReference(named2DTextures)
|
||||
val ref0 = WeakReference(named2DTextures0)
|
||||
val ref1 = WeakReference(named2DTextures1)
|
||||
|
||||
val worker = Runnable {
|
||||
while (true) {
|
||||
val get = ref.get() ?: break
|
||||
get.cleanUp()
|
||||
val get0 = ref0.get() ?: break
|
||||
get0.cleanUp()
|
||||
val get1 = ref1.get() ?: break
|
||||
get1.cleanUp()
|
||||
LockSupport.parkNanos(1_000_000_000L)
|
||||
}
|
||||
}
|
||||
@ -473,14 +475,16 @@ class GLStateTracker(val client: StarboundClient) {
|
||||
fun loadTexture(path: String): GLTexture2D {
|
||||
ensureSameThread()
|
||||
|
||||
return named2DTextures.get(path) {
|
||||
if (!client.starbound.exists(path)) {
|
||||
LOGGER.error("Texture {} is missing! Falling back to {}", path, missingTexturePath)
|
||||
missingTexture
|
||||
} else {
|
||||
newTexture(path).upload(client.starbound.imageData(path)).generateMips().also {
|
||||
it.textureMinFilter = GL_NEAREST
|
||||
it.textureMagFilter = GL_NEAREST
|
||||
return named2DTextures0.get(path) {
|
||||
named2DTextures1.get(it) {
|
||||
if (!client.starbound.exists(it)) {
|
||||
LOGGER.error("Texture {} is missing! Falling back to {}", it, missingTexturePath)
|
||||
missingTexture
|
||||
} else {
|
||||
newTexture(it).upload(client.starbound.imageData(it)).generateMips().also {
|
||||
it.textureMinFilter = GL_NEAREST
|
||||
it.textureMagFilter = GL_NEAREST
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user