0
votes

I was able to make a donut with Three.js using THREE.TorusGeometry. But I can't get it to look like a flat ring like the ones in these pictures:

http://www.google.com/imgres?imgurl=http://www.titanjewellery.co.uk/Mens/TI21-Titanium-8mm-Flat-Brushed-Ring.jpg&imgrefurl=http://www.titanjewellery.co.uk/Mens/8mm-Brushed-Titanium-Flat-Ring.html&h=301&w=232&sz=16&tbnid=LCN7eQuo2wyG_M:&tbnh=90&tbnw=69&zoom=1&usg=__3vayMvDy26tsj2hwvCK9SsYwVwY=&docid=ZMdcBBBQOzMSoM&sa=X&ei=pEhsUeL4FKWJiAKCzIHYCQ&ved=0CEAQ9QEwBA&dur=1660

Here's what my donut looks like: enter image description here

Is there another Three.js geometry that can generate a flat ring (right with flat inner and outer walls)? Or another way of going about this?

Thanks for any pointers you can share! :)

Update: The code and dependencies were taken from:

http://mrdoob.github.io/three.js/examples/misc_controls_trackball.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>three.js webgl - trackball controls</title>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
    <style>
      body {
        color: #000;
        font-family:Monospace;
        font-size:13px;
        text-align:center;
        font-weight: bold;

        background-color: #fff;
        margin: 0px;
        overflow: hidden;
      }

      #info {
        color:#000;
        position: absolute;
        top: 0px; width: 100%;
        padding: 5px;
      }

      a {
        color: red;
      }
    </style>
  </head>
  <body>
    <div id="container"></div>
    <div id="info">
      <a href="http://threejs.org" target="_blank">three.js</a> - trackball controls example</br>MOVE mouse &amp; press LEFT/A: rotate, MIDDLE/S: zoom, RIGHT/D: pan
    </div>

    <script src="three.min.js"></script>
    <script src="TrackballControls.js"></script>
    <script src="Detector.js"></script>
    <script src="stats.min.js"></script>
    <script>
      if ( ! Detector.webgl ) Detector.addGetWebGLMessage();
      var container, stats;
      var camera, controls, scene, renderer;
      var cross;

      init();
      animate();

      function init() {
        camera = new THREE.PerspectiveCamera( 60, window.innerWidth / window.innerHeight, 1, 1000 );
        camera.position.z = 500;

        controls = new THREE.TrackballControls( camera );
        controls.rotateSpeed = 1.0;
        controls.zoomSpeed = 1.2;
        controls.panSpeed = 0.8;
        controls.noZoom = false;
        controls.noPan = false;
        controls.staticMoving = true;
        controls.dynamicDampingFactor = 0.3;
        controls.keys = [ 65, 83, 68 ];
        controls.addEventListener( 'change', render );

        // world
        scene = new THREE.Scene();
        scene.fog = new THREE.FogExp2( 0xcccccc, 0.002 );

        var radius = 100;
        var tubeRadius = 50;
        var radialSegments = 8 * 10;
        var tubularSegments = 6 * 15;
        var arc = Math.PI * 2;
        var geometry = new THREE.TorusGeometry( radius, tubeRadius, radialSegments, tubularSegments, arc );
        var material =  new THREE.MeshLambertMaterial( { color:0xffffff, shading: THREE.FlatShading } );

        for ( var i = 0; i < 1; i ++ ) {
          var mesh = new THREE.Mesh( geometry, material );
          mesh.updateMatrix();
          mesh.matrixAutoUpdate = false;
          scene.add( mesh );
        } 

        // lights
        light = new THREE.DirectionalLight( 0xffffff );
        light.position.set( 1, 1, 1 );
        scene.add( light );

        light = new THREE.DirectionalLight( 0x002288 );
        light.position.set( -1, -1, -1 );
        scene.add( light );

        light = new THREE.AmbientLight( 0x222222 );
        scene.add( light );

        // renderer
        renderer = new THREE.WebGLRenderer( { antialias: false } );
        renderer.setClearColor( scene.fog.color, 1 );
        renderer.setSize( window.innerWidth, window.innerHeight );

        container = document.getElementById( 'container' );
        container.appendChild( renderer.domElement );
        //

        window.addEventListener( 'resize', onWindowResize, false );
      }

      function onWindowResize() {
        camera.aspect = window.innerWidth / window.innerHeight;
        camera.updateProjectionMatrix();
        renderer.setSize( window.innerWidth, window.innerHeight );
        controls.handleResize();
        render();
      }

      function animate() {
        requestAnimationFrame( animate );
        controls.update();
      }

      function render() {
        renderer.render( scene, camera );
      }
    </script>
  </body>
</html>

http://jsfiddle.net/alininja/b4qGx/1/

3
@RobertHarvey: I've updated the question with the code and JSFiddle. Thanks for looking! - Zhao Li

3 Answers

5
votes

There are multiple options:

  1. Use TubeGeometry - this is probably what you need
  2. ExtrudeGeometry to extrude a disk
  3. lathe an offset rectangle with LatheGeometry
  4. Use THREE.Shape -> grab the tube like shape from the webgl_geometry_shapes sample
2
votes

You can use the RingGeometry function. The following code adds to the scene a full (between 0 and 360 degrees) wireframed red ring of inner radius equals to 10 and outer radio equals to 20. You can play with the other indicated variables to adjust the aspect of the disc you want to generate ()

var geometry = new THREE.RingGeometry(10, 20, thetaSegments, phiSegments, 0, Math.PI * 2);
var ring = new THREE.Mesh(geometry, new THREE.MeshBasicMaterial({color: 0xff0000, wireframe: true}));
ring.position.set(25, 30, 0);
scene.add(ring);
0
votes

Check this code!

var geometry = new THREE.TorusGeometry( 3, 0.5, 20, 2999 );
  ring1 = new THREE.Mesh(geometry, new THREE.MeshBasicMaterial({color: 0xffffff, wireframe: true}));
scene.add(ring1);