Threejs扁平螺旋形状

时间:2018-06-18 16:03:53

标签: three.js

我正在考虑创建一个螺旋形状,并希望对该方法有一些指导。想象一下,你在一根圆柱形管子周围缠绕一条扁平的缎带(每匝之间有一个空格),这就是我想要创造的形状。

我最初的想法是使用管几何,但似乎只能接受圆形轮廓。我想要一个扁平/直的配置文件

由于我最终还想要在螺旋末端形成一个形状,我想要创建几个点阵列,一个用于外螺旋,另一个用于内螺旋,然后使用三个形状,但我相信只能做2D形状,这不会是。

虽然定义一个圆柱体会非常有用,但只是在它上面放一个纹理就不会给我我需要的控制

螺旋背后的数学并不困难,我只是不知道ThreeeJS中实际创建它的最佳方法?任何指导都将非常感谢。

1 个答案:

答案 0 :(得分:1)

任何人都有兴趣我从三个话语页面得到了一个不错的回复...

https://discourse.threejs.org/t/creating-a-helical-sweep-with-a-flat-profile/3163/2

所有来自该论坛的“prisoner849”,直接链接到一个代码笔与他的答案,涉及弯曲一个薄盒

https://jsfiddle.net/5Lycd4rm/7/

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

var controls = new THREE.OrbitControls(camera, renderer.domElement);

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

var rbnWidth = .5;
var rbnThickness = 0.1;
var rbnSteps = 1;
var rbnStepLength = 1.5;
var rbnSegsPerStep = 50;
var rbnRadius = 1;

var rbnGeom = new THREE.BoxGeometry(rbnSteps * Math.PI * 2, rbnWidth, rbnThickness, rbnSteps * rbnSegsPerStep, 1, 1);
rbnGeom.computeBoundingBox();
var size = new THREE.Vector3();
rbnGeom.boundingBox.getSize(size);
rbnGeom.translate(size.x * 0.5, size.y * 0.5, size.z * 0.5);

// bend it!

rbnGeom.vertices.forEach(v => {
  let angle = -v.x;
  let radius = rbnRadius + v.z;
  let shift = (v.x / (Math.PI * 2)) * rbnStepLength + v.y;

  v.x = Math.cos(angle) * radius;
  v.y = shift;
  v.z = Math.sin(angle) * radius;
}); 

rbnGeom.computeFaceNormals();
rbnGeom.computeVertexNormals();

rbnGeom.center();


var ribbon = new THREE.Mesh(rbnGeom, new THREE.MeshStandardMaterial({color: 0x0099ff}));
scene.add(ribbon);

render();

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