1

I am trying to test a simple dot shader in ThreeJS made by 2pha : https://2pha.com/demos/threejs/shaders/simple_dots.html

It seems to not work properly for metaballs using Marching Cubes : https://threejs.org/examples/webgl_marchingcubes.html. Is this a UV coordinates problem? The ThreeJS version has a enableUvs flag but does not seem to be enough.

Here the shader passed to ShaderMaterial

'polkadots' : {
    uniforms: {

        "amount":{type: "f",value: 5.},
        "radius1":{type: "f",value: 0.3},
        "radius2":{type: "f",value: 0.32},
        "color1":{type:"c",value: new THREE.Color(0xffffff)},
        "color2":{type:"c",value: new THREE.Color(0x000000)},

    },

    vertexShader: [
        "varying vec2 vUv;",


        "void main() {",
            "vUv = uv;",
            "vec4 mvPosition = modelViewMatrix * vec4( position, 1.0 );",
            "gl_Position = projectionMatrix * mvPosition;",

        "}",
    ].join( "\n" ),

    fragmentShader: [

        "uniform vec3 color1;",
        "uniform vec3 color2;",
        "uniform float radius1;",
        "uniform float radius2;",
        "uniform float amount;",
        "varying vec2 vUv;",

        "void main(void){",

            "float p = smoothstep(radius1, radius2, length(fract(amount*vUv)-0.5));",
            "vec3 col = mix(color1,color2,vec3(p));",
            "gl_FragColor = vec4(col,1.0);",

        "}",
    ].join( "\n" )
}
compmonks
  • 647
  • 10
  • 24

1 Answers1

0

Yes. Your dot shader is using the UVs to determine where to draw the dots... If your marching cube algo isn't setting the UVs, you'll have to synthesize some yourself... You can do a box unwrapping.. It's not too super complicated but it was fun to figure out.. you loop through the faces of the geometry... figure out which plane the triangle lays on, and get the verts projected onto that uv plane. I took the liberty of writing it up for ya:

    function boxUnwrapUVs(geometry) {
        for (var i = 0; i < geometry.faces.length; i++) {
            var face = geometry.faces[i];
            var faceUVs = geometry.faceVertexUvs[0][i]
            var va = geometry.vertices[geometry.faces[i].a]
            var vb = geometry.vertices[geometry.faces[i].b]
            var vc = geometry.vertices[geometry.faces[i].c]
            var vab = new THREE.Vector3().copy(vb).sub(va)
            var vac = new THREE.Vector3().copy(vc).sub(va)

            //now we have 2 vectors to get the cross product of...
            var vcross = new THREE.Vector3().copy(vab).cross(vac);
            //Find the largest axis of the plane normal...
            vcross.set(Math.abs(vcross.x), Math.abs(vcross.y), Math.abs(vcross.z))
            var majorAxis = vcross.x > vcross.y ? (vcross.x > vcross.z ? 'x' : vcross.y > vcross.z ? 'y' : vcross.y > vcross.z) : vcross.y > vcross.z ? 'y' : 'z'
            //Take the other two axis from the largest axis
            var uAxis = majorAxis == 'x' ? 'y' : majorAxis == 'y' ? 'x' : 'x';
            var vAxis = majorAxis == 'x' ? 'z' : majorAxis == 'y' ? 'z' : 'y';
            faceUVs[0].set(va[uAxis], va[vAxis])
            faceUVs[1].set(vb[uAxis], vb[vAxis])
            faceUVs[2].set(vc[uAxis], vc[vAxis])
        }
        //Tell THREE that our modifications need to be uploaded to the GPU
        geometry.elementsNeedUpdate = geometry.verticesNeedUpdate = true;
    }
manthrax
  • 4,918
  • 1
  • 17
  • 16
  • Thanks @manthrax, I am trying to implement it and will post an update. I am using the marching cubes implementation provided by Threejs :https://threejs.org/examples/webgl_marchingcubes.html. It has a 'enableUVs' flag as well so I thought it was already implemented but does not seem to do it. – compmonks Jul 01 '18 at 15:32
  • Since I could not solve the boxUnwrapping for marchingcubes yet, I simply replaced 'uv' with 'position' in the vertex shader. It currently maps the dots from the vertices of course and does not provide a homogeneous mapping yet :) – compmonks Jul 12 '18 at 19:30
  • Cool.. did you try the boxUnwrapUVs function I posted above? – manthrax Jul 13 '18 at 11:08