GLES20 从图像文件的字节数组中绘制纹理

GLES20 draw texture from image file's byte array

我正在尝试使用 opengl 从图像文件字节中绘制纹理:

//Read bytes from image URI
@Throws(IOException::class)
private fun Uri.readBytes(): ByteArray? =
    context.contentResolver.openInputStream(this)?.buffered()?.use { it.readBytes() }

//Create ByteBuffer for OpenGL
val pixels = ByteBuffer.wrap(data).flip()
            glTextureId = OpenGlUtils.loadTexture(pixels, width, height, glTextureId)

        //Trying to draw texture
fun loadTexture(data: ByteBuffer, width: Int, height: Int, usedTexId: Int): Int {
        val textures = IntArray(1)
        GLES20.glGenTextures(1, textures, 0)
        GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, textures[0])
        GLES20.glTexParameterf(
            GLES20.GL_TEXTURE_2D,
            GLES20.GL_TEXTURE_MAG_FILTER, GLES20.GL_LINEAR.toFloat()
        )
        GLES20.glTexParameterf(
            GLES20.GL_TEXTURE_2D,
            GLES20.GL_TEXTURE_MIN_FILTER, GLES20.GL_LINEAR.toFloat()
        )
        GLES20.glTexParameterf(
            GLES20.GL_TEXTURE_2D,
            GLES20.GL_TEXTURE_WRAP_S, GLES20.GL_CLAMP_TO_EDGE.toFloat()
        )
        GLES20.glTexParameterf(
            GLES20.GL_TEXTURE_2D,
            GLES20.GL_TEXTURE_WRAP_T, GLES20.GL_CLAMP_TO_EDGE.toFloat()
        )
        GLES20.glTexImage2D(
            GLES20.GL_TEXTURE_2D, 0, GLES20.GL_RGBA, width, height,
            0, GLES20.GL_RGBA, GLES20.GL_UNSIGNED_BYTE, data
        )
}

但结果是这样的 result

如果我更改最后一行,将使用文件字节数组从位图中绘制图片,如下所示:

GLUtils.texImage2D(GLES20.GL_TEXTURE_2D, 0, BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.size), 0)

它显示正确的图像,但它工作得太慢(我需要每 100 毫秒绘制 2mb 纹理,并且纹理变化看起来很滞后),这就是为什么这种方式不适合我

我找到了解决方案。据我了解,位图按原始图像大小(宽度 * 高度 * 4(对于 ARGB))分配用于解码的字节,并调整自身大小以适合纹理。 所以我实现了 TurboJpeg 库,现在我将 jpeg 解码为正确的大小,将输出字节放入 ByteBuffer,并显示从此缓冲区创建的纹理。现在它几乎可以立即绘制纹理