Three.js: Expose 'attributes' and 'geometries' from WebGLRenderer

Created on 8 May 2019  路  13Comments  路  Source: mrdoob/three.js

If I add these two lines to WebGLRenderer.initGLContext

    _this.attributes = attributes;
    _this.geometries = geometries;

Then I can do this to grab the underlying WebGL vertex and index buffers for my BufferGeometry and populate them from external WebGL code.

            var bufferGeometry = new THREE.BufferGeometry();
            bufferGeometry.setIndex([]);
            bufferGeometry.addAttribute( 'position', new THREE.Float32BufferAttribute([], 3));            
            bufferGeometry.addAttribute( 'normal', new THREE.Float32BufferAttribute([], 3));            
            bufferGeometry.addAttribute( 'uv', new THREE.Uint16BufferAttribute([], 2, true));

            renderer.geometries.update(bufferGeometry);
            var posBuf = renderer.attributes.get(bufferGeometry.attributes['position']).buffer;
            var norBuf = renderer.attributes.get(bufferGeometry.attributes['normal']).buffer;            
            var uvBuf = renderer.attributes.get(bufferGeometry.attributes['uv']).buffer;
            var indexBuf = renderer.attributes.get(bufferGeometry.index).buffer;

Is this a change you guys would consider taking? This is with the goal of getting volumetric video content playing inside of THREE.js scenes.

Thanks!
Evan

Most helpful comment

I just wanted to chip in and say this feature is exactly what I need :) We stream geometry in chunks and doing the roundtrip through BufferGeometry really is a pain. The GLBufferAttribute of https://github.com/mrdoob/three.js/pull/13196 also looks pretty good, so that would be totally OK too.

All 13 comments

Then I can do this to grab the underlying WebGL vertex and index buffers for my BufferGeometry and populate them from external WebGL code.

Would it be very inconvenient for you to populate data to the BufferGeometry instead? It might be easier to evaluate this issue if you can explain your workflow in more detail.

The geometry is animated at 30 FPS, which is updated on the GPU with WebGL transform feedback. Directly populating the BufferGeometry object would mean round-tripping to CPU memory and back right?

Pretty much we have an existing WebGL component that can interface with a native WebGL application: the application gives us their buffer handles, we populate them on each tick with the animated geometry. We're hoping to build a THREE.js integration now to let users build more rich experiences with THREE.js and our volumetric video content.

Wouldn't exposing attributes already be sufficient? What would you do with geometries?

Well I found that I need to call:

renderer.geometries.update(bufferGeometry);

To get the attributes initialized, otherwise all the attributes.get calls in the code snippet above return null. If there's another way to get the attributes populated though I'd happily use that instead 馃槃

Would something like #11883 solve your problem, too? Also check out the respective PR #13196

That looks pretty good. Index buffers are just another BufferAttribute right so I'd be able to use a GLBufferAttribute for my indices too? I'll try to modify my project to work with that branch and see if I run into any issues.

Index buffers are just another BufferAttribute right so I'd be able to use a GLBufferAttribute for my indices too?

I think so.

I'll try to modify my project to work with that branch and see if I run into any issues.

That would be good to know 馃憤 .

OK I grabbed raub's fork and modified my code to use GLBufferAttribute instead of my hacked access to the attributes and geometries lookups, everything seems to work fine.

It would be nice if the GLBufferAttribute constructor could take a normalized parameter like BufferAttribute does, but setting it directly on the attribute after creation also seems to work:

            var uvAtt = new THREE.GLBufferAttribute(gl, uvBuf, gl.UNSIGNED_SHORT, 2, 0);
            uvAtt.normalized = true;
            bufferGeometry.addAttribute( 'uv', uvAtt);

It would be nice if the GLBufferAttribute constructor could take a normalized parameter like BufferAttribute does

That's true.

@mrdoob Do you think it's worth to add GLBufferAttribute to the library? It seems there are some scenarios where a more flexibel version of BufferAttribute is helpful to users.

I just wanted to chip in and say this feature is exactly what I need :) We stream geometry in chunks and doing the roundtrip through BufferGeometry really is a pain. The GLBufferAttribute of https://github.com/mrdoob/three.js/pull/13196 also looks pretty good, so that would be totally OK too.

@evodabas I've added the normalized param in 9ba4d012bb4b8943d85d824044a17f60acae85d9

Nice 馃憤 What's the status of this feature overall, are there plans for #13196 to make it into a release anytime soon?

Instead of exposing internal components, it's better to focus on an API like presented in #13196. Closing in favor of #11883.

Was this page helpful?
0 / 5 - 0 ratings