Angelzzz
Angelzzz

Reputation: 1446

How to linke objects and move them relatively in three js?

I created kind of mannequin with three.js.

I want to make it possible to:

  1. link all objects with connection child-parent
  2. move objects relatively (if hand moved, than elbow whould be moved, but if wrist moved, than other parts should not be moved)

I wrote code below and made jsfiddle example. Not sure whether it is correct way.

var scene, camera, renderer, pivot;

//main
init();
animate();

//init
function init() {
  //scene
  scene = new THREE.Scene();
  scene.background = new THREE.Color(0xf0f0f0);

  //camera
  camera = new THREE.PerspectiveCamera(140, window.innerWidth / window.innerHeight, 0.1, 10000);

  //neck
  var geometry = new THREE.BoxBufferGeometry(2, 3, 1);
  var material = new THREE.MeshNormalMaterial({
    transparent: true,
    opacity: 0.5
  });
  var figure = new THREE.Mesh(geometry, material);
  figure.position.set(0, 1.5, 0);

  //body
  var geometry2 = new THREE.BoxBufferGeometry(0.5, 0.5, 0.5);
  /* geometry2.rotateZ(THREE.Math.degToRad(90)); // ROTATE GEOMETRY SO IT'S IN THE CORRECT ORIENTATION */
  var figure2 = new THREE.Mesh(geometry2, material);
  figure2.position.set(0, 1.5, 0); // MOVE THE GEOMOETRY UP BY HALF SO PIVOT IS AT THE BOTTOM OF THE GEO
  /* figure2.rotation.set(0, 0, Math.PI / 2); */
  figure.add(figure2);

  //head
  var geometry3 = new THREE.SphereGeometry(0.75, 32, 32);
  var material3 = new THREE.MeshBasicMaterial({
    color: 0xffff00
  });
  var sphere3 = new THREE.Mesh(geometry3, material3);
  sphere3.position.set(0, 2.5, 0);
  figure.add(sphere3)

  //right shoulder 
  var geometry4 = new THREE.SphereGeometry(0.25, 32, 32);
  var material4 = new THREE.MeshBasicMaterial({
    color: 0xffff00
  });
  var sphere4 = new THREE.Mesh(geometry4, material4);
  sphere4.position.set(1.25, 1.25, 0);
  figure.add(sphere4)

  //right hand top
  var geometry5 = new THREE.BoxBufferGeometry(0.5, 1.5, 0.5);
  var figure5 = new THREE.Mesh(geometry5, material);
  figure5.position.set(1.25, 0.25, 0);
  figure.add(figure5);

  //right elbow
  var geometry6 = new THREE.SphereGeometry(0.25, 32, 32);
  var sphere6 = new THREE.Mesh(geometry6, material3);
  sphere6.position.set(1.25, -0.75, 0);
  figure.add(sphere6)

  //right hand bottom
  var geometry7 = new THREE.BoxBufferGeometry(0.5, 1.5, 0.5);
  var figure7 = new THREE.Mesh(geometry7, material);
  figure7.position.set(1.25, -1.75, 0);
  figure.add(figure7);
  
  //right hand bottom sphere
  var geometry8 = new THREE.SphereGeometry(0.25, 32, 32);
  var sphere8 = new THREE.Mesh(geometry8, material3);
  sphere8.position.set(1.25, -2.75, 0);
  figure.add(sphere8);
  
  //right wrist
  var geometry9 = new THREE.BoxBufferGeometry(0.5, 0.5, 0.5);
  var figure9 = new THREE.Mesh(geometry9, material);
  figure9.position.set(1.25, -3.25, 0);
  figure.add(figure9);
  
  //left shoulder 
  var geometry10 = new THREE.SphereGeometry(0.25, 32, 32);
  var sphere10 = new THREE.Mesh(geometry10, material4);
  sphere10.position.set(-1.25, 1.25, 0);
  figure.add(sphere10)

  //left hand top
  var geometry11 = new THREE.BoxBufferGeometry(0.5, 1.5, 0.5);
  var figure11 = new THREE.Mesh(geometry11, material);
  figure11.position.set(-1.25, 0.25, 0);
  figure.add(figure11);

  //left elbow
  var geometry12 = new THREE.SphereGeometry(0.25, 32, 32);
  var sphere12 = new THREE.Mesh(geometry12, material3);
  sphere12.position.set(-1.25, -0.75, 0);
  figure.add(sphere12)

  //left hand bottom
  var geometry13 = new THREE.BoxBufferGeometry(0.5, 1.5, 0.5);
  var figure13 = new THREE.Mesh(geometry13, material);
  figure13.position.set(-1.25, -1.75, 0);
  figure.add(figure13);
  
  //left hand bottom sphere
  var geometry14 = new THREE.SphereGeometry(0.25, 32, 32);
  var sphere14 = new THREE.Mesh(geometry14, material3);
  sphere14.position.set(-1.25, -2.75, 0);
  figure.add(sphere14);
  
  //left wrist
  var geometry15 = new THREE.BoxBufferGeometry(0.5, 0.5, 0.5);
  var figure15 = new THREE.Mesh(geometry15, material);
  figure15.position.set(-1.25, -3.25, 0);
  figure.add(figure15);
  
  //left hip
  var geometry16 = new THREE.SphereGeometry(0.5, 32, 32);
  var sphere16 = new THREE.Mesh(geometry16, material3);
  sphere16.position.set(-0.5, -2.25, 0);
  figure.add(sphere16);
  
  //left haunch
  var geometry17 = new THREE.BoxBufferGeometry(1, 1.75, 1);
  var figure17 = new THREE.Mesh(geometry17, material);
  figure17.position.set(-0.5, -3.65, 0);
  figure.add(figure17);
  
  //left knee
  var geometry18 = new THREE.SphereGeometry(0.5, 32, 32);
  var sphere18 = new THREE.Mesh(geometry18, material3);
  sphere18.position.set(-0.5, -5, 0);
  figure.add(sphere18);
  
  //left shin
  var geometry19 = new THREE.BoxBufferGeometry(1, 1.75, 1);
  var figure19 = new THREE.Mesh(geometry19, material);
  figure19.position.set(-0.5, -6.35, 0);
  figure.add(figure19);
 
  //left ankle
  var geometry20 = new THREE.SphereGeometry(0.25, 32, 32);
  var sphere20 = new THREE.Mesh(geometry20, material3);
  sphere20.position.set(-0.5, -7.5, 0);
  figure.add(sphere20);
  
  //left foot
  var geometry21 = new THREE.BoxBufferGeometry(1, 0.25, 1.5);
  var figure21 = new THREE.Mesh(geometry21, material);
  figure21.position.set(-0.5, -7.85, 0.25);
  figure.add(figure21);
  
  //right hip
  var geometry22 = new THREE.SphereGeometry(0.5, 32, 32);
  var sphere22 = new THREE.Mesh(geometry22, material3);
  sphere22.position.set(0.5, -2.25, 0);
  figure.add(sphere22);
  
  //right haunch
  var geometry23 = new THREE.BoxBufferGeometry(1, 1.75, 1);
  var figure23 = new THREE.Mesh(geometry23, material);
  figure23.position.set(0.5, -3.65, 0);
  figure.add(figure23);

  //right knee
  var geometry24 = new THREE.SphereGeometry(0.5, 32, 32);
  var sphere24 = new THREE.Mesh(geometry24, material3);
  sphere24.position.set(0.5, -5, 0);
  figure.add(sphere24);
  
  //right shin
  var geometry25 = new THREE.BoxBufferGeometry(1, 1.75, 1);
  var figure25 = new THREE.Mesh(geometry25, material);
  figure25.position.set(0.5, -6.35, 0);
  figure.add(figure25);
 
  //right ankle
  var geometry26 = new THREE.SphereGeometry(0.25, 32, 32);
  var sphere26 = new THREE.Mesh(geometry26, material3);
  sphere26.position.set(0.5, -7.5, 0);
  figure.add(sphere26);
  
  //right foot
  var geometry27 = new THREE.BoxBufferGeometry(1, 0.25, 1.5);
  var figure27 = new THREE.Mesh(geometry27, material);
  figure27.position.set(0.5, -7.85, 0.25);
  figure.add(figure27);


  //add figure
  scene.add(figure);

  scene.add(new THREE.AxesHelper());

  renderer = new THREE.WebGLRenderer({
    antialias: true
  });
  renderer.setSize(window.innerWidth, window.innerHeight);
  document.body.appendChild(renderer.domElement);

  //add grid
  /* scene.add(new THREE.GridHelper(10, 20)) */

  camera.position.z = 5;

  //top view on object
  /*  camera.position.set(0, 10, 0);
   camera.up.set(0, 0, -1);
   camera.lookAt(0, 0, 0); */

  //controls to rotate camera
  controls2 = new THREE.OrbitControls(camera, renderer.domElement);
  controls2.minPolarAngle = Math.PI/2;
  controls2.maxPolarAngle = Math.PI/2;

  //controls to drag object in 3d
  /*   var cubePoints = [];
    cubePoints.push(figure2);
    var controls = new THREE.DragControls(cubePoints, camera, renderer.domElement); */

}


//animate
function animate() {
  requestAnimationFrame(animate);

  render();
};

//render
function render() {
  renderer.render(scene, camera);
};

Upvotes: 0

Views: 666

Answers (1)

leogarcia
leogarcia

Reputation: 31

To link meshes in Three.js I usually use groups (see https://threejs.org/docs/#api/en/objects/Group), I also use them to change the pivot point of a mesh by placing the mesh in a group with the wanted pivot point in the center coordinates of the group.

Of course you can nest groups for your case, like a group with the hand mesh which can be inside another group with the forearm mesh and so on.

In order to move the elbow position according to the hand position (if I get what you say right), you should use Inverse Kinematics, there are implementations for Three.js like https://github.com/jsantell/THREE.IK but I never used it so I can't tell you more about it.

Hope you solve your problem.

Upvotes: 1

Related Questions