Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/blackberry/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 在THREE.js中,强制精灵对象始终位于skydome对象的前面_Javascript_Three.js_Shader_Sprite - Fatal编程技术网

Javascript 在THREE.js中,强制精灵对象始终位于skydome对象的前面

Javascript 在THREE.js中,强制精灵对象始终位于skydome对象的前面,javascript,three.js,shader,sprite,Javascript,Three.js,Shader,Sprite,我目前有一个自定义着色器在skydome上绘制渐变,并且希望在skydome前面有一个太阳/月亮(从用户的角度)。做到这一点最简单的方法是为太阳和月亮安装精灵,但出现的问题是精灵卡在天穹内(精灵在天穹的一半前面,一半后面)。我试图用polygonoffset解决这个问题,但这似乎对精灵对象不起作用 所以我的问题是,如何在skydome顶部设置太阳/月亮,而不必修改我的自定义skydome着色器以添加具有渐变的太阳/月亮纹理(这可能会非常困难) 下面是skydome的“我的天空”着色器的代码 ne

我目前有一个自定义着色器在skydome上绘制渐变,并且希望在skydome前面有一个太阳/月亮(从用户的角度)。做到这一点最简单的方法是为太阳和月亮安装精灵,但出现的问题是精灵卡在天穹内(精灵在天穹的一半前面,一半后面)。我试图用polygonoffset解决这个问题,但这似乎对精灵对象不起作用

所以我的问题是,如何在skydome顶部设置太阳/月亮,而不必修改我的自定义skydome着色器以添加具有渐变的太阳/月亮纹理(这可能会非常困难)

下面是skydome的“我的天空”着色器的代码

new THREE.ShaderMaterial({
    uniforms: {
        glow: {
            type: "t",
            value: THREE.ImageUtils.loadTexture(DEFAULT_PATH+"glow2.png")
        },
        color: {
            type: "t",
            value: THREE.ImageUtils.loadTexture(DEFAULT_PATH+"sky2.png")
        },
        lightDir: {
            type: "v3",
            value: self.lightPos
        }
    },
    vertexShader: [
        "varying vec3 vWorldPosition;",
        "varying vec3 vPosition;",
        "void main() {",
            "vec4 worldPosition = modelMatrix * vec4(position, 1.0);",
            "vWorldPosition = worldPosition.xyz;",
            "vPosition = position;",
            "gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);",
        "}"
    ].join("\n"),
    fragmentShader: [
        "uniform sampler2D glow;",
        "uniform sampler2D color;",
        "uniform vec3 lightDir;",
        "varying vec3 vWorldPosition;",
        "varying vec3 vPosition;",
        "void main() {",
            "vec3 V = normalize(vWorldPosition.xzy);",
            "vec3 L = normalize(lightDir.xzy);",
            "float vl = dot(V, L);",
            "vec4 Kc = texture2D(color, vec2((L.y + 1.0) / 2.0, V.y));",
            "vec4 Kg = texture2D(glow,  vec2((L.y + 1.0) / 2.0, vl));",
            "gl_FragColor = vec4(Kc.rgb + Kg.rgb * Kg.a / 2.0, Kc.a);",
        "}",
    ].join("\n")
});

确保您的skydome绘制在任何其他对象之前,并禁用材质上的
depthWrite
/
depthTest
标志(
depthWrite
在此处是最重要的):


其中,
skydome
是您在其上应用了
材质的网格

请确保在任何其他对象之前绘制skydome,并禁用材质上的
深度thwrite
/
深度测试
标志(
深度thwrite
是此处的重点):

其中,
skydome
是您应用了
yourmaterial
的网格

yourmaterial = new THREE.ShaderMaterial({...});
yourmaterial.depthWrite = false;
yourmaterial.depthTest = false;
skydome.renderDepth = 1e20;