Handling many elements on screen #720

Closed
danielribeiro opened this Issue Nov 3, 2011 · 6 comments

Projects

None yet

3 participants

@danielribeiro
Contributor

Hi,

Is there a way in Three.js to achieve performance like this, but for cubes with more than 20 of edge length? Even with material and geometry caching, things are not so smooth.

Thanks

@mrdoob
Owner
mrdoob commented Nov 3, 2011

What he is doing on that video is exactly what the minecraft examples do.
http://mrdoob.github.com/three.js/examples/webgl_geometry_minecraft.html

@danielribeiro
Contributor

Yes, but such example doesn't have that many cubes. Even the video doesn't have tha many cubes. A cube composed of 12x12x12 is only 1728 cubes. Doing it with 20x20x20 cubes, is 8k (which goes fine). After that, three.js starts lagging quite a bit. Even with autotUpdateMatrix false.

The minecraft example cheats a bit, using one mesh with all the geometry composed.

@mrdoob
Owner
mrdoob commented Nov 3, 2011

The minecraft example is 128x128. 16384 cubes. But yes, you wouldn't be able to move them.

I haven't tried myself the way explained in the description of that youtube video.

@danielribeiro
Contributor

I am making an open source Three.js experiment (after trying four 3d physics engines...) and when it is done, we will have something more concrete to optmize (let's see how many primitives can three.js handle).

Chrome already complains about garbage collection, render, renderbuffer and loadUniformMatrices.

Edit: it is now done. People can see the demo here, and read more about it here

@alteredq
Contributor
alteredq commented Nov 3, 2011

If you want lots of very fast individually movable cubes, you can do something like gman did in Google IO presentation - have a single batch of triangles and put all per object specific info into attributes.

http://webglsamples.googlecode.com/hg/google-io/2011/index.html

In three.js this could be done using custom attributes and ShaderMaterial.

With uniforms and individual draw calls you'll never be able to get more than few thousands of individual objects (on my notebook, max numbers are 7000 static objects and 2650 dynamic objects at 60 fps - 7000 is pretty much raw WebGL JS=>GPU boundary limit, doing almost nothing else than just pushing to GPU per-object matrices and calling drawElements).

The only way around is above mentioned use-case specific use of attributes for batching of per-object info. Though you may still run into JS-side bottlenecks if you try to control movement from JS - gman's examples have animation baked into vertex shader, attribute buffers are not updated per frame, only at init.

Whenever I do throughout optimizations, ultimately I hit bottlenecks of JS engine - once you have many elements, garbage collection starts to dominate costs, even if you yourself don't create any new objects.

@danielribeiro
Contributor

Wow, that is crazy. However, 18k objects with 16 fps is not that great compared to what java can do on desktop with opengl.

The project behind the samples can be found here on github: https://github.com/greggman/tdl

But thanks a lot for the link. Now I have some direction if I need crazy performance.

@mrdoob mrdoob closed this Nov 25, 2011
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment