如何在Threejs纹理中使用compressedTexSubImage2D

时间:2018-11-28 06:57:43

标签: three.js webgl textures

我尝试使用CompressedTexture为Threejs创建TextureAtlas,但是我找不到找到正确格式/内部格式的方法

我得到的错误是:glCompressedTexSubImage2D:格式与内部格式不匹配。

我从THREE.KTXLoader加载压缩的纹理,并使用mipmaps [0] .KTXLoader解析的数据提供TextureAtlas的更新功能

该课程分为三部分:

  • 构造函数:设置纹理的基本信息
  • setRender(renderer):设置使用的未来渲染器和工具
  • setSize:设置我的纹理的大小
  • update:使用压缩纹理更新纹理的一部分

完整课程:

class TextureAtlas extends THREE.Texture{
    constructor() {

        super()

        this.magFilter = THREE.LinearFilter;
        this.minFilter = THREE.LinearMipMapLinearFilter;
        const canvas = document.createElement('canvas');
        canvas.width = 1;
        canvas.height = 1;
        const ctx = canvas.getContext('2d');
        const imageData = ctx.createImageData(1, 1);            
        this.image = imageData
        this.generateMipmaps = false
        this.flipY = false
        // this.unpackAlignment = 1
        this.format = THREE.RGBAFormat
        this.needsUpdate = true
        this.isUpdatableTexture = true
    }

    setRenderer( renderer ) {
        this.renderer = renderer;
        this.gl = this.renderer.getContext()
        this.ct = this.gl.getExtension("WEBGL_compressed_texture_s3tc");
        this.utils = THREE.WebGLUtils(this.gl, this.renderer.extensions)
    }

    setSize( width, height ) {

        if( width === this.width && height === this.height ) return;
        if(!this.renderer){ return }
        var textureProperties = this.renderer.properties.get( this );
        if( !textureProperties.__webglTexture ) return;

        this.width = width;
        this.height = height;

        var activeTexture = this.gl.getParameter( this.gl.TEXTURE_BINDING_2D );
        this.gl.bindTexture( this.gl.TEXTURE_2D, textureProperties.__webglTexture );
        if( !textureProperties.__webglTexture ) this.width = null;

        this.gl.texImage2D(
            this.gl.TEXTURE_2D,
            0,
            this.utils.convert( this.format ),
            width,
            height,
            0,
            this.utils.convert( this.format ),
            this.utils.convert( this.type ),
            null
        );
        this.gl.bindTexture( this.gl.TEXTURE_2D, activeTexture );
        this.needsUpdate = true
    }

    update = ( pixels, x, y, width, height,format )=> {
        // return
        var textureProperties = this.renderer.properties.get( this );
        if( !textureProperties.__webglTexture ) { return}

        var activeTexture = this.gl.getParameter( this.gl.TEXTURE_BINDING_2D );
        this.gl.bindTexture( this.gl.TEXTURE_2D, textureProperties.__webglTexture );

        // WebGL 1 & 2:
        // https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/compressedTexSubImage2D
        // void gl.compressedTexSubImage2D(target, level, xoffset, yoffset, width, height, format, ArrayBufferView? pixels);
        this.gl.compressedTexSubImage2D(
            this.gl.TEXTURE_2D,                                         // texture 2d 3d or cubemap
            0,                                                                          // level of details
            0,//x,                                                                          // left offset
            0,//y,                                                                          // top offset
            width,                                                                  // texture width
            height,                                                                 // texture height
            this.utils.convert(this.ct.COMPRESSED_RGBA_S3TC_DXT5_EXT), // format of the compressed texture
            pixels                                                                  // ArrayBufferView
        );
        this.gl.generateMipmap( this.gl.TEXTURE_2D );
        this.gl.bindTexture( this.gl.TEXTURE_2D, activeTexture );
        this.needsUpdate = true
    }
}

0 个答案:

没有答案