I am trying to apply a THREE.MeshLambertMaterial
to a model in the Autodesk Forge Viewer. The viewer3D.js version is 7.87.0. As soon as I call fragList.setMaterial(fragId, lambertMaterial)
, the model disappears and the following console warning appears:
GL_INVALID_OPERATION: Active draw buffers with missing fragment shader outputs.
Using THREE.MeshBasicMaterial
works without errors, but I want to take advantage of the Lambert material's shading ability. Ideally I would use THREE.MeshPhongMaterial
, but it appears that the Forge Viewer uses a modified version of THREE.MeshPhongMaterial
, so the effects that normally work well with Phong no longer work anymore (e.g. material.envMap
does not behave like it does with a normal THREE material, and the material.combine
property that effects envMap blending cannot be changed).
I have created a Github repository and test page to demonstrate this issue.
Repository: https://github.com/throw-away-97743/ForgeViewerTests
Live Demo: https://throw-away-97743.github.io/ForgeViewerTests/basic-lambert-test.html
Relevant JavaScript code:
// please refer to the live demo and repository
// for a more interactive example
const fragList = model.getFragmentList();
const matMan = Viewer.impl.matman();
const fragIds = Object.keys(fragList.fragments.fragId2dbId);
const lambertMaterial = new THREE.MeshLambertMaterial();
lambertMaterial.color = new THREE.Color(0xff0000);
matMan.addNonHDRMaterial("lambertMaterial", lambertMaterial);
lambertMaterial.envMap = null;
lambertMaterial.needsUpdate = true;
fragIds.forEach(fragId => fragList.setMaterial(fragId, lambertMaterial));
Viewer.impl.invalidate(true);
Edit 2023-04-20: What I'm trying to achieve
In short, I need a material to behave exactly how the MeshLambertMaterial example behaves at https://threejs.org/docs/#api/en/materials/MeshLambertMaterial
But at a bare minimum, I need the following to be met:
- I want to be able to set an envmap on the material, and the material's envmap should wrap around the entire mesh.
- The material must receive lighting, but not use IBL. I don't mind if I have to create an ambient or point light somewhere.
- The material's
.combine
property should work like a typical THREE.js MeshLambertMaterial. - The material should be able to receive a plain color.
- The material should be able to receive a texture.
- The material should be able to receive a bump/normal map.
- The material should be able to receive an alpha map.
- The material should support transparency.
Basically, everything a THREE.MeshLambertMaterial supports.
Here is a graphic explaining a bit more:
Here is a THREE.MeshLambertMaterial demo on the THREE.js docs site: