2017-09-16 25 views
0

WebGLを使用してDDS texture(主にDXT1とDXT3)をImageDataに変換しようとしています。ここに私のattemp ... WebGLを使用してDDS(DXT3)テクスチャをImageDataに変換する

let ext = <WEBGL_compressed_texture_s3tc>gl.getExtension('WEBGL_compressed_texture_s3tc'); 

let texture = gl.createTexture(); 
gl.bindTexture(gl.TEXTURE_2D, texture); 

let fb = gl.createFramebuffer(); 
gl.bindFramebuffer(gl.FRAMEBUFFER, fb); 
gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, texture, 0); 

gl.compressedTexImage2D(gl.TEXTURE_2D, 0, ext.COMPRESSED_RGBA_S3TC_DXT3_EXT, width, height, 0, sourceImage); 

gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR); 
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR); 

let data = new Uint8Array(width * height * 4); 

gl.readPixels(0, 0, width, height, gl.RGBA, gl.UNSIGNED_BYTE, data); 
gl.deleteFramebuffer(fb); 

let image = new ImageData(new Uint8ClampedArray(data), width, height); 

GLがWebGLRenderingContextとsourceImage(Uint8Array)である

はDXT3形式のテクスチャではあります。ミップマップや何かがない。確かに、 thisスニペットを使ってこのテクスチャをレンダリングしようとしていて、うまくいきました。

コードは、次のエラー(Google Chromeの)でreadPixels機能で失敗:

[.Offscreen-FOR-WebGLの-000001F2F3C04690] GLのERROR :GL_INVALID_FRAMEBUFFER_OPERATION:glReadPixels:フレームバッファ 不完全

もちろん私は答えを探していますが、成功することはありません。たぶんthisが役立つかもしれません。必要があれば、私はいくつかのテクスチャの例を提供することができます。

答えて

2

圧縮テクスチャ形式にはレンダリングできないため、フレームバッファに貼り付けると無効な操作エラーが発生します。非圧縮テクスチャをフレームバッファに添付し、DXTテクスチャからスクリーンスペースクワッドサンプリングを描画する必要があります。これと同じように:私が正しく理解していれば

let ext = <WEBGL_compressed_texture_s3tc>gl.getExtension('WEBGL_compressed_texture_s3tc'); 

// create framebuffer attachment texture 
let colorTarget = gl.createTexture(); 
gl.bindTexture(gl.TEXTURE_2D, colorTarget); 
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST); 
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST); 
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE); 
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE); 
gl.texImage2D(
    gl.TEXTURE_2D, 
    0, 
    gl.RGBA, 
    width, 
    height, 
    0, 
    gl.RGBA, 
    gl.UNSIGNED_BYTE, 
    null 
); 
// setup framebuffer 
let fb = gl.createFramebuffer(); 
gl.bindFramebuffer(gl.FRAMEBUFFER, fb); 
gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, colorTarget, 0); 

// create and upload compressed texture 
let compressedTexture = gl.createTexture(); 
gl.bindTexture(gl.TEXTURE_2D, compressedTexture); 
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR); 
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR); 
gl.compressedTexImage2D(gl.TEXTURE_2D, 0, ext.COMPRESSED_RGBA_S3TC_DXT3_EXT, width, height, 0, sourceImage); 

gl.viewport(0,0,width,height); 
//draw screenspace quad here 

// read back uncompressed color data 
let data = new Uint8Array(width * height * 4); 
gl.readPixels(0, 0, width, height, gl.RGBA, gl.UNSIGNED_BYTE, data); 

gl.deleteFramebuffer(fb); 

let imageData = new ImageData(new Uint8ClampedArray(data), width, height); 
+0

だから... ...、私は何とか、非圧縮RGBA WebGLのテクスチャにDXT WebGLのテクスチャを変換し、フレームバッファとreadPixelsで物事を行う必要がありますか?私はWebGLの初心者ですので、間違っていると理解しています...? –

+0

私の答えにあなたのコードスニペットの修正版を追加して、流れを例示しました –

+0

それは動作しません。試してみると、私は小さなデモを作った。 [this](https://jsfiddle.net/jb8d1pw1/2/)の結果ウィンドウに[このテクスチャ](https://drive.google.com/uc?id=0B4zf5CmYE7lgRFExZmk1Z3BQTEU&export=download)をドラッグ&ドロップするだけです。jsfiddleスニペット。テクスチャが表示されます。しかし、imageDataにテクスチャを変換する[this](https://jsfiddle.net/dk2coq2g/)スニペットはどこかに壊れています。 imageDataのすべてのバイトは0です... –

関連する問題