2015-11-20 135 views
0

我想写一个着色器材质来显示带圆角点的THREE.Points()对象。我通过控制片段着色器中的alpha值来做到这一点。使用ShaderMaterial的Alpha颜色

下面是我的代码的完整工作版本。我获得了只在圆内着色像素的预期效果。不过,外面,我得到白色,而不是背景颜色。

This question与我的相关。我尝试设置material.transparent = true,但没有任何效果。

<html> 
    <head> 
     <title>THREEJS alpha shader</title> 
     <style> 
      body { margin: 0; } 
      canvas { width: 100%; height: 100% } 
     </style> 
     <script type="text/javascript" src="http://threejs.org/build/three.min.js"></script> 
     <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script> 
    </head> 
    <body> 
     <!-- Shaders --> 
     <script type="x-shader/x-vertex" id="vertexshader"> 
      void main() { 
       gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0); 
       gl_PointSize = 40.0; // pixels 
      } 
     </script> 

     <script type="x-shader/x-fragment" id="fragmentshader"> 
      varying vec4 color; 

      void main() { 
       // radius 
       float r = length(gl_PointCoord - vec2(0.5, 0.5)); 

       if(r < 0.5) { 
        gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0); 
       } else { 
        gl_FragColor = vec4(1.0, 1.0, 1.0, 0.0); 
       } 
      } 
     </script> 

     <script> 
      var scene = new THREE.Scene(); 
      var camera = new THREE.PerspectiveCamera(75, window.innerWidth/window.innerHeight, 0.1, 1000); 
      var renderer = new THREE.WebGLRenderer(); 
      renderer.setSize(window.innerWidth, window.innerHeight); 
      document.body.appendChild(renderer.domElement); 

      var buffer = new Float32Array(3); // single point located at (0, 0, 0) 
      var geometry = new THREE.BufferGeometry(); 
      geometry.addAttribute('position', new THREE.BufferAttribute(buffer,3)); 

      // create shader material 
      var material = new THREE.ShaderMaterial({ 
       vertexShader : $('#vertexshader').text(), 
       fragmentShader : $('#fragmentshader').text(), 
       }); 

      var point = new THREE.Points(geometry, material); 
      scene.add(point); 
      camera.position.z = 2; 

      var render = function() { 
       requestAnimationFrame(render); 
       renderer.render(scene, camera); 
      }; 
      render(); 
     </script> 
    </body> 
</html> 
+2

您接受的答案不是如何在three.js中完成。而不是将alpha设置为零,这样做:'if(length(gl_PointCoord - vec2(0.5,0.5))> 0.475)discard;' – WestLangley

+0

接受的答案解决了为ShaderMaterial启用alpha混合的问题。但是,您的代码帮助我消除了角落中的奇怪渲染。谢谢。 –

+1

通过设置material.transparent = true,可以在three.js中启用alpha混合。 – WestLangley

回答

1

您需要在OpenGL上下文中启用alpha混合。我不知道是否有一种方法可以做到这一点使用three.js所,但添加这些GL命令来渲染()函数就足够了:

var render = function() { 
    var gl = renderer.context; 
    gl.enable(gl.BLEND); 
    gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA); 
    requestAnimationFrame(render); 
    renderer.render(scene, camera); 
}; 

参见blendFunc的MDN文档了解更多的信息上这个。