点云纹理alpha混合(THREEJS)

问题描述 投票:0回答:1

我使用ShaderMaterial创建具有基于属性的大小和不透明度的点云。我还需要贴图。问题在于纹理的渲染没有透明度。看起来每种纹理像素颜色都以某种方式与背景颜色(本例中为白色)混合;如何避免这种情况?

enter image description here

我使用svg纹理:

<div id="circle-texture" style="width: 0; height: 0; display: none">
    <svg width="32" height="32" xmlns="http://www.w3.org/2000/svg" version="1.1">
        <circle cx="16" cy="16" r="13" stroke="none" fill="white" fill-opacity="1" />        
    </svg>    
</div>

这是我的片段着色器:

<script type="x-shader/x-fragment" id="point-cloud-fragment-shader">

...  

uniform sampler2D texture;   

varying vec3 vColor;

varying float vOpacity;   

#include <clipping_planes_pars_fragment>

void main() {

    #include <clipping_planes_fragment>

    vec3 outgoingLight = vec3( 0.0 );

    vec4 diffuseColor = vec4( diffuse, vOpacity );  

    if (enableTexture) {            
        vec4 mapTexel = texture2D( texture, gl_PointCoord );            
        diffuseColor *= mapTexelToLinear( mapTexel );
    }

    diffuseColor.rgb *= vColor;

    outgoingLight = diffuseColor.rgb;
    gl_FragColor = vec4( outgoingLight, diffuseColor.a );
}

在以下情况下放弃修复:

if ( gl_FragColor.a < 0.001 ) discard;

但是有可能不丢弃吗? (使用自定义混合功能或其他方法)我玩过自定义混合功能,但到目前为止没有成功。

enter image description here

three.js shader textures fragment-shader blending
1个回答
0
投票

在处理部分透明的点云时有效的设置是将transparent: truedepthTest: falseblending mode设为必要。根据您的用例,加法或乘法混合看起来不错,并且消除了对子图形深度进行排序的需要,因为混合消除了将颜色放置在另一个“前面”的需要:

const spriteMat = new THREE.ShaderMaterial({
    uniforms: {
        // List of uniforms
    },
    vertexShader: spriteVert,
    fragmentShader: spriteFrag,
    blending: THREE.AdditiveBlending,
    depthTest: false,
    transparent: true
});

[Turn transparent: true会尊重片段着色器中的alpha通道,因此您不再需要丢弃像素。

© www.soinside.com 2019 - 2024. All rights reserved.