Transparency issue within the same mesh

Hi everyone!

As can be seen in the picture, the plants and the water are all from the same transparent mesh. However, it seems like the plant’s mesh is making the water behind it see-through. I know that transparency is a very tricky topic in WebGL, does anybody know how to fix this?

Thanks!

1 Like

Hi! Sometimes help add mesh.renderOrder=-1; or mesh.renderOrder=1;

You might try setting depthWrite=false on any transparent materials.

I think it would probably also pay off to split some of these parts into separate meshes, if they are merged now.

I took some time and split the meshes apart, but depthWrite=false results in really weird behaviors:

The meshes in the back are now rendering on top of the closer ones. However, I am using setTransparentSort to sort them by distance to camera, but that seems to be ignored.

Do you have the option of using .alphaTest instead of .transparent, for the foliage? If they don’t need partial transparency but are just cutouts from a texture, that will avoid all of these issues.

Also see: Material: Add .alphaHash and .alphaHashScale by donmccurdy · Pull Request #24271 · mrdoob/three.js · GitHub

I am using both transparent=true and alphaTest=0.1, how should I do it instead?

If I remove transparent=true, the objects disappear from the scene.

Correction: The background just appears to be black instead of disappearing:

As long as .transparent=true is set, there are really difficult sorting issues involved. If you don’t need any semi-transparency you can disable .transparent and just use .alphaTest for more of a mask/cutout effect. This avoids the sorting issues.

I don’t know why the background would become black here though. It should be the case that any parts of the texture with opacity less than the .alphaTest value will disappear. You could try some higher values like .5 or .75 perhaps. Otherwise we might need to see more of the material configuration or (ideally) a demo.

The water texture is actually semi-transparent, so is there a way to sort the transparent faces better?

This is the source code to creating the materials, and this is my attempt to sort the transparent faces.

Thanks!

You’ll really want any semi-transparent voxels to be separated from the opaque and alpha-tested ones, with separate materials. Is that the case here?

three.js sorts Mesh objects by the distance of the center of their bounding box relative to the camera. With transparent Meshes sorted in a separate pass. The custom sort applies to Meshes, not faces. Sorting triangles, faces, or voxels on every frame relative to the camera tends to be too expensive, three.js does not attempt to do that.

The scene looks great! How did you manage to do so?

Sometimes help add mesh.renderOrder=-1; or mesh.renderOrder=1;

renderer.toneMapping=3;
renderer.toneMappingExposure = 1;
renderer.outputEncoding=THREE.sRGBEncoding;
tex["ground_1_diffuse"].encoding=THREE.sRGBEncoding;
tex["ground_1_diffuse"].needsUpdate=true;
tex["dirt"].encoding=THREE.sRGBEncoding;

^I haven’t seen the relevant code of this example but would assume:

  1. it does not need to use .transparent=true on the grass
  2. the water is a single continuous surface, rather than a lot of interlocked voxels

both of these make correct sorting much more possible.