Proportional editing

by VictorCrisalix

HTML

<!-- Import maps polyfill -->
<!-- Remove this when import maps will be widely supported -->
<script async src="https://unpkg.com/es-module-shims@1.3.6/dist/es-module-shims.js"></script>
    
<script type="importmap">
	{
		"imports": {
			"three": "https://unpkg.com/three/build/three.module.js",
      "three/addons/": "https://unpkg.com/three/examples/jsm/"
		}
	}
</script>

CSS

body {
  padding: 0;
  margin: 0;
}

canvas {
  display: block;
}

JavaScript

import * as THREE from 'three'
import { GUI } from 'three/addons/libs/lil-gui.module.min.js'

// scene stuff
const renderer = new THREE.WebGLRenderer({ antialias: true }) // create a renderer
renderer.setSize(window.innerWidth, window.innerHeight)
document.body.appendChild(renderer.domElement)
const camera = new THREE.PerspectiveCamera(30, window.innerWidth / window.innerHeight, 0.1, 1000) // create a camera
camera.position.z = 4
camera.position.y = -0.03
const scene = new THREE.Scene() // create a scene
scene.background = new THREE.Color(0xffffff) // set white background color

// plane stuff
const size = 2 // plane size
const segments = 40 // plane segments
const geometry = new THREE.PlaneGeometry(size, size, segments, segments) // create a plane geometry
const material = new THREE.MeshNormalMaterial() // assign it a material
const mesh = new THREE.Mesh(geometry, material) // create mesh
scene.add(mesh) // and add it to the scene
const positionAttribute = mesh.geometry.attributes.position // position attribute
const verticesCount = positionAttribute.array.length / 3 // vertices count
mesh.rotateX(-Math.PI / 3) // rotate the plane for visualization purposes
mesh.rotateZ(-Math.PI / 4)

// original plane stuff
const originalGeometry = new THREE.PlaneGeometry(size, size, segments, segments) // create a plane geometry
const originalMesh = new THREE.Mesh(originalGeometry) // create mesh

// proportional editing stuff
const range = 0.25 // initial range
const intensity = 0.5 // initial intensity
const originalVertexPosition = new THREE.Vector3() // current editing vertex position of the original mesh
const displacement = new THREE.Vector3(0, 0, 1) // main displacement direction
const gaussianDisplacement = new THREE.Vector3() // and scale it with the gaussian value
const middleIndex = Math.ceil(verticesCount / 2) - 1 // middle vertex index of the mesh
const centerPosition = new THREE.Vector3() // vertex position for gaussian bell...