简体   繁体   English

在three.js上渲染较重的模型/网格

[英]Render heavy model / mesh on three.js

I know this is a well known question but I was not able to find a good answer. 我知道这是一个众所周知的问题,但我找不到很好的答案。

My usage 我的用法

I use three.js to display 3D models created through drone pictures ( here an example ). 我使用three.js来显示通过无人机图片创建的3D模型( 此处为示例 )。

The problem 问题

I can't render heavy models (1M vertices, 2M faces) : Chrome or WebGl crashed. 我无法渲染沉重的模型(1M顶点,2M面):Chrome或WebGl崩溃了。

What I tried 我尝试了什么

I used Threejs.org examples for all my tests to be sure that it was not my code that didn't work. 我为所有测试使用了Threejs.org示例,以确保不是我的代码不起作用。 I made my test on a x64 Chrome with --max_old_space_size=6144 flag. 我在带有--max_old_space_size = 6144标志的x64 Chrome上进行了测试。

  • Import model in .dae with ColladaLoader --> 2.5Go of RAM is used and Chrome crash (displaying "not enough memory") 使用ColladaLoader在.dae中导入模型->使用了2.5Go的RAM,Chrome崩溃了(显示“内存不足”)
  • Import model in .obj with OBJLoader + MTLLoader --> 2.8Go of RAM is used and WebGl crash 使用OBJLoader + MTLLoader在.obj中导入模型->使用2.8Go RAM并使WebGL崩溃
  • I red many posts about Three.js and memory allocation but many of them speak about remove an object from the scene 我贴了很多有关Three.js和内存分配的文章,但其中许多都谈到从场景中删除对象

Possible solutions 可能的解决方案

  • I saw that .stl (binary) file are more compact, but as far as I know there is no texture with these files, so I can't use it 我看到.stl(二进制)文件更加紧凑,但据我所知这些文件没有纹理,因此我无法使用它
  • Use BinaryLoader (which has GeometryBuffer output) but I need to convert .dae or .obj to binary files and I don't know how to do that 使用BinaryLoader(具有GeometryBuffer输出),但是我需要将.dae或.obj转换为二进制文件,我不知道该怎么做
  • Load my model in multiple parts to not load in one shot ? 将我的模型分为多个部分加载,而不是一次加载? But I didn't saw any example or posts with that kind of treatment 但是我没有看到任何例子或帖子经过这种处理

How to reproduce 如何繁殖

For the code, I use basics examples on Threejs.org. 对于代码,我在Threejs.org上使用了基础示例。 For models : 对于型号:

  • If you want to try with .dae you can find on this folder a working example (WorkingModel.dae / .jpg) and the model who don't work (BigModel.dae / .jpg) 如果要尝试使用.dae,可以在此文件夹中找到一个有效的示例(WorkingModel.dae / .jpg)和不起作用的模型(BigModel.dae / .jpg)
  • If you want to try with .obj you can find on this folder a working example (WorkingModel.dae / .jpg / .mtl) and the model who don't work (BigModel.dae / .jpg / .mtl) 如果要尝试使用.obj,可以在此文件夹中找到一个有效的示例(WorkingModel.dae / .jpg / .mtl)和不起作用的模型(BigModel.dae / .jpg / .mtl)

Any ideas to load the big one ? 有什么主意可以加载吗? Thanks ! 谢谢 !

EDIT 1 : 编辑1:

I tried to put a breakpoint in the SuccessCallback to see if the overload of RAM is during the load or after. 我试图在SuccessCallback中设置一个断点,以查看RAM的过载是在加载期间还是加载之后。 I was not able to hit the breakpoint, so the overload of RAM is before the SuccessCallback. 我无法达到断点,因此RAM的过载在SuccessCallback之前。

Then I went step by step in the ColladaLoader to find what is using so much RAM. 然后,我一步一步地在ColladaLoader中查找使用了这么多RAM的内存。 Here is the "callstack" : 这是“调用堆栈”:

  • myCollada.load() myCollada.load()
  • ColladaLoader.parse() ColladaLoader.parse()
  • Geometry.parse() Geometry.parse()
  • Mesh.parse() Mesh.parse()
    • Source.parse (hit 3 times) = +400mo in RAM Source.parse(命中3次)= + 400mo RAM
    • Vertices.parse = +0mo in RAM Vertices.parse = RAM中的+ 0mo
    • Triangles.parse = +1500mo in RAM RAM中的Triangles.parse = + 1500mo
    • this.geometry3js.computeVertexNormals() = RAM go over 2600Mo and chrome crash this.geometry3js.computeVertexNormals()= RAM超过2600Mo并且chrome崩溃

Could I do any other tests to find the reason of this problem ? 我可以做其他测试以找出此问题的原因吗? Thanks 谢谢

Your textures are waaaay to big, and besides, you don't need them because your model has baked vertex colors, which includes baked lighting. 您的纹理非常大,此外,您不需要它们,因为您的模型具有烘焙的顶点颜色,其中包括烘焙的照明。 Your model therefore does not require UVs eiher. 因此,您的模型不需要UV。

Use ColladaLoader2 , and this pattern. 使用ColladaLoader2和这种模式。 It should work. 它应该工作。

var loader = new THREE.ColladaLoader();

loader.load( 'BigModel.dae', function ( collada ) {

        var dae = collada.scene;

        dae.traverse( function( child ) {

            if ( child instanceof THREE.Mesh ) {

                child.geometry.removeAttribute( 'uv' ); // you don't need it

                child.material = new THREE.MeshBasicMaterial( { // scene lights not required

                    vertexColors: THREE.VertexColors // you have them, use them

                } );

                scene.add( child );
            }

        } );

} );

three.js r.86 three.js r.86

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM