ThreeJS - Outline Test 5

Based on: https://jsfiddle.net/tfoller/qvrac41L/10/

by tfoller

HTML

<script src="https://threejs.org/build/three.min.js"></script>
<script src="https://threejs.org/examples/js/controls/OrbitControls.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/dat-gui/0.7.5/dat.gui.min.js"></script>
<script>
    var vertexShader = `
        varying vec2 vUv;

        attribute float alpha;
        varying float vAlpha;
        
	    attribute vec3 center;
		varying vec3 vCenter;

        void main() {
            vUv = uv;
            vAlpha = alpha;
            vCenter = center;
            gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);
        }
    `;
    var fragmentShader = `
    
    	//in vec2 ouv;
        //uniform vec3 colors[_LENGTH_];
        //uniform float steps[_LENGTH_];

        //precision mediump float;
        uniform vec3 color1;
        uniform float color1Alpha;
        uniform vec3 borderColor;
        uniform float borderThickness;
        uniform float lines[_LINEPOINTS_];

        varying vec2 vUv;
        varying float vAlpha;
		varying vec3 vCenter;

        bool pointInTriangle(float x2, float y2, float x3, float y3, float x, float y, out float dist)
        {
        float den = 1.0 / (x2 * y3 - x3 * y2);
        float wa = ((y2 - y3) * x + (x3 - x2) * y - x3 * y2 + x2 * y3) * den;
        if(wa < 0.0 || wa > 1.0) return false;
        float wb = (y3 * x - x3 * y) * den;
        if(wb < 0.0 || wb > 1.0) return false;
        float wc = 1.0 - wa - wb;
        if(wc < 0.0 || wc > 1.0) return false;

        den = -x * (y2 - y3) + y * (x2 - x3);
        float crx = x * (x2 * y3 - y2 * x3)/den;
        float cry = y * (x2 * y3 - y2 * x3)/den;
        dist = length(vec2(x,y)) / length(vec2(crx, cry));
        return true;
        }

        void main() {
            float dist = 0.0;
            vec2 uv = vUv;// + 10.0;
            for(int j = 0; j < _LINEPOINTS_; j+=4) {
            	if(pointInTriangle(lines[j], lines[j+1], lines[j+2], lines[j+3], vUv.x, vUv.y, dist)) break;
...

CSS

body {
  overflow: hidden;
  margin: 0;
}

JavaScript

var scene = new THREE.Scene();
var camera = new THREE.PerspectiveCamera(60, window.innerWidth / window.innerHeight, 1, 1000);
camera.position.set(0, 0, 50);
var renderer = new THREE.WebGLRenderer({
  antialias: true
});
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.setClearColor(0x404040);
document.body.appendChild(renderer.domElement);
var controls = new THREE.OrbitControls(camera, renderer.domElement);

const printRounded = (label, arr) => {
const rarr = [...arr].map(e=>Math.round(e));
  console.log(label, rarr);
};

var plane, ellipse, triangle;
var ellipseSegments = 6;
var xRadius = 20;
var yRadius = 10;

const x = 0, y = 0;
const heartShape = new THREE.Shape();
heartShape.moveTo( x + 5, y + 5 );
heartShape.bezierCurveTo( x + 5, y + 5, x + 4, y, x, y );
heartShape.bezierCurveTo( x - 6, y, x - 6, y + 7,x - 6, y + 7 );
heartShape.bezierCurveTo( x - 6, y + 11, x - 3, y + 15.4, x + 5, y + 19 );
heartShape.bezierCurveTo( x + 12, y + 15.4, x + 16, y + 11, x + 16, y + 7 );
heartShape.bezierCurveTo( x + 16, y + 7, x + 16, y, x + 10, y );
heartShape.bezierCurveTo( x + 7, y, x + 5, y + 5, x + 5, y + 5 );
const hgeom = new THREE.ShapeGeometry( heartShape );

function createEllipse(_geom) {
  var shape = new THREE.Shape().absellipse(
    0, 0, // ax, aY
    xRadius, xRadius, // xRadius, yRadius
    0, 2 * Math.PI, // aStartAngle, aEndAngle
    false, // aClockwise
    0 // aRotation
  );
  shape.autoClose = true;
  
  var geom = _geom || 
  
  new THREE.ShapeBufferGeometry(
    shape,
    ellipseSegments
  );
  
  // HEART
  let _shape;
  if(_geom) {
  	_shape = [];
    const _pos = _geom.attributes.position.array;
    const _uv = _geom.attributes.uv.array;
    for(let i = 6; i < _pos.length; i+=3)
    	_shape.push({x: _pos[i], y: _pos[i + 1]});
      
     // shift uvs 
     for(let i = 0; i < _uv.length; i+=2) {
     		_uv[i] -= 5;
        _uv[i + 1] -= 10;
     }
  }
	
  // 2D array of points, world
  const pos = [];
  const shp = _shape ||...