0

This might be a rookie mistake but im stuck with it for many hours, so i thought i would ask here. I´m new to three.js but looking through the forum i found some good examples of mesh editing and managing a imported model but after adapting my code to this example im stuck right now.

I want to drag the vertices of the model but when i try to click the vertices i have the <a class='gotoLine' href='#140:42'>140:42</a> Uncaught ReferenceError: points is not defined"

I cant seem to the get the var points outside of the function object otherwise i get a black screen.

The next challenge would be exporting it to GLTF and to a 3D printer.

EDIT: i managed to change the vertices, but my model wont transform accordingly to the mesh. And testing i found out that i have many vertices on top of each other, even though i have the

geometry.mergeVertices(); geometry.computeFaceNormals(); geometry.computeVertexNormals();

enabled.


This is my code right now: https://jsfiddle.net/felipefsalazar/j9c1L6yr/6/

//SETUP DA TELA
var points, geometry;
var scene = new THREE.Scene();
var camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
camera.position.set(0, 5, 10);
var renderer = new THREE.WebGLRenderer();
renderer.setClearColor(0x404040);
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);

//CONTROLE com o MOUSE
var controls = new THREE.OrbitControls(camera, renderer.domElement);

//LUZ
var light = new THREE.DirectionalLight(0xffffff, 0.5);
light.position.setScalar(100);
scene.add(light);
scene.add(new THREE.AmbientLight(0xffffff, 0.5));

//GRID CINZA NA TELA
scene.add(new THREE.GridHelper(100, 100));

//LOAD DO OBJETO
var objLoader = new THREE.OBJLoader();

objLoader.load('https://raw.githubusercontent.com/felipefsalazar/venus/master/venuspeq.obj',


  function(object) {

    child = object.children[0];
    geometry = new THREE.Geometry().fromBufferGeometry(child.geometry);
    geometry.computeFaceNormals();
    geometry.mergeVertices(geometry);
    geometry.computeVertexNormals();
    geometry = new THREE.BufferGeometry().fromGeometry(geometry);

    scene.add(object);

    //MALHA DA ESTATUA
    var plane = new THREE.Mesh(geometry, new THREE.MeshBasicMaterial({
      wireframe: true,
      color: "blue"
    }));
    scene.add(plane);

    //PONTOS NA ESTÁTUA PARA MEXER
    points = new THREE.Points(geometry, new THREE.PointsMaterial({
      size: 0.25,
      color: "yellow"
    }));
    scene.add(points);


    //MALHA DA ESTATUA (wireframe)
    venuspeq = new THREE.Mesh(geometry, mesh);

    //ROTAÇÃO DO OBJETO
    //object.rotation.x = -Math.PI * 0.5;

    //BOX DE AJUDA DO OBJETO
    //var box = new THREE.Box3().setFromObject(object);
    //var box3Helper = new THREE.Box3Helper(box);
    //scene.add(box3Helper);



  });


var raycaster = new THREE.Raycaster();
raycaster.params.Points.threshold = 0.25;
var mouse = new THREE.Vector2();
var intersects = null;
var plane = new THREE.Plane();
var planeNormal = new THREE.Vector3();
var currentIndex = null;
var planePoint = new THREE.Vector3();
var dragging = false;

window.addEventListener("mousedown", mouseDown, false);
window.addEventListener("mousemove", mouseMove, false);
window.addEventListener("mouseup", mouseUp, false);



function mouseDown(event) {
  setRaycaster(event);
  getIndex();
  dragging = true;
    if (currentIndex != null){
        controls.enabled = false;
        }
}

function mouseMove(event) {
  if (dragging && currentIndex !== null) {
    setRaycaster(event);
    raycaster.ray.intersectPlane(plane, planePoint);
    geometry.attributes.position.setXYZ(currentIndex, planePoint.x, planePoint.y, planePoint.z);
    geometry.attributes.position.needsUpdate = true;
  }
}

function mouseUp(event) {
  dragging = false;
  currentIndex = null;
    controls.enabled = true;
}

function getIndex() {
  intersects = raycaster.intersectObject(points);
  if (intersects.length === 0) {
    currentIndex = null;
    return;
  }
  currentIndex = intersects[0].index;
  setPlane(intersects[0].point);
}

function setPlane(point) {
  planeNormal.subVectors(camera.position, point).normalize();
  plane.setFromNormalAndCoplanarPoint(planeNormal, point);
}

function setRaycaster(event) {
  getMouse(event);
  raycaster.setFromCamera(mouse, camera);
}

function getMouse(event) {
  mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
  mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;
}


//RENDER
function render() {
  requestAnimationFrame(render);
  renderer.render(scene, camera);
}
render();
body {
  overflow: hidden;
  margin: 0;
}
<script src="https://threejs.org/build/three.min.js"></script>
<script src="https://threejs.org/examples/js/loaders/OBJLoader.js"></script>
<script src="https://threejs.org/examples/js/controls/OrbitControls.js"></script>

1 Answers1

0

Your problem is with JavaScript scope. You have to make sure that points is available throughout your code, and not just inside a single function. For example:

function init() {
   var points = 1;
}

// This will not work because points is only available
// inside the init function
init();
console.log(points);

to fix this issue, declare your variable outside the function so you're taking its scope up one level:

var points;
function init() {
    points = 1;
}

// Now you'll get the desired output of 1
init();
console.log(points);

See here for a fixed version. Notice I had to declare both var points, geometry; at the beginning of your code so they're both available throughout all functions:

//SETUP DA TELA
var points, geometry;
var scene = new THREE.Scene();
var camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
camera.position.set(0, 5, 10);
var renderer = new THREE.WebGLRenderer();
renderer.setClearColor(0x404040);
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);

//CONTROLE com o MOUSE
var controls = new THREE.OrbitControls(camera, renderer.domElement);

//LUZ
var light = new THREE.DirectionalLight(0xffffff, 0.5);
light.position.setScalar(100);
scene.add(light);
scene.add(new THREE.AmbientLight(0xffffff, 0.5));

//GRID CINZA NA TELA
scene.add(new THREE.GridHelper(100, 100));

//LOAD DO OBJETO
var objLoader = new THREE.OBJLoader();

objLoader.load('https://raw.githubusercontent.com/felipefsalazar/venus/master/venuspeq.obj',


  function(object) {

    child = object.children[0];
    geometry = new THREE.Geometry().fromBufferGeometry(child.geometry);
    geometry.computeFaceNormals();
    //geometry.mergeVertices();
    geometry.computeVertexNormals();
    geometry = new THREE.BufferGeometry().fromGeometry(geometry);

    scene.add(object);

    //MALHA DA ESTATUA
    var plane = new THREE.Mesh(geometry, new THREE.MeshBasicMaterial({
      wireframe: true,
      color: "blue"
    }));
    scene.add(plane);

    //PONTOS NA ESTÁTUA PARA MEXER
    points = new THREE.Points(geometry, new THREE.PointsMaterial({
      size: 0.15,
      color: "red"
    }));
    scene.add(points);


    //MALHA DA ESTATUA (wireframe)
    //venuspeq = new THREE.Mesh(geometry, mesh);

    //ROTAÇÃO DO OBJETO
    //object.rotation.x = -Math.PI * 0.5;

    //BOX DE AJUDA DO OBJETO
    //var box = new THREE.Box3().setFromObject(object);
    //var box3Helper = new THREE.Box3Helper(box);
    //scene.add(box3Helper);



  });


var raycaster = new THREE.Raycaster();
raycaster.params.Points.threshold = 0.15;
var mouse = new THREE.Vector2();
var intersects = null;
var plane = new THREE.Plane();
var planeNormal = new THREE.Vector3();
var currentIndex = null;
var planePoint = new THREE.Vector3();
var dragging = false;

window.addEventListener("mousedown", mouseDown, false);
window.addEventListener("mousemove", mouseMove, false);
window.addEventListener("mouseup", mouseUp, false);



function mouseDown(event) {
  setRaycaster(event);
  getIndex();
  dragging = true;
}

function mouseMove(event) {
  if (dragging && currentIndex !== null) {
    setRaycaster(event);
    raycaster.ray.intersectPlane(plane, planePoint);
    geometry.attributes.position.setXYZ(currentIndex, planePoint.x, planePoint.y, planePoint.z);
    geometry.attributes.position.needsUpdate = true;
  }
}

function mouseUp(event) {
  dragging = false;
  currentIndex = null;
}

function getIndex() {
  intersects = raycaster.intersectObject(points);
  if (intersects.length === 0) {
    currentIndex = null;
    return;
  }
  currentIndex = intersects[0].index;
  setPlane(intersects[0].point);
}

function setPlane(point) {
  planeNormal.subVectors(camera.position, point).normalize();
  plane.setFromNormalAndCoplanarPoint(planeNormal, point);
}

function setRaycaster(event) {
  getMouse(event);
  raycaster.setFromCamera(mouse, camera);
}

function getMouse(event) {
  mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
  mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;
}



//RENDER
function render() {
  requestAnimationFrame(render);
  renderer.render(scene, camera);
}
render();
body {
  overflow: hidden;
  margin: 0;
}
<script src="https://threejs.org/build/three.min.js"></script>
<script src="https://threejs.org/examples/js/loaders/OBJLoader.js"></script>
<script src="https://threejs.org/examples/js/controls/OrbitControls.js"></script>
M -
  • 26,908
  • 11
  • 49
  • 81