【问题标题】:three.js multiple images on cylinder facethree.js 圆柱面上的多个图像
【发布时间】:2020-03-12 13:48:30
【问题描述】:

我正在尝试使用 three.js 在旋转圆柱体的外部(不是顶部或底部)显示多个图像。我可以显示 1 张图片,但我的目标是并排显示几张。我在材质数组中添加了 3 个纹理,但只显示第一个。任何帮助表示赞赏。

<html>
<head>
    <title>My first three.js app</title>
    <span>Test</span>
    <style>
        body { margin: 0; }
        canvas { width: 100%; height: 100% }
    </style>
</head>
<body>
    <script src="js/three.js"></script>
    <script>
        var scene = new THREE.Scene();
        var camera = new THREE.PerspectiveCamera( 100, window.innerWidth / window.innerHeight, 0.1, 1000 );
        camera.position.y = 24;

        var renderer = new THREE.WebGLRenderer();
        renderer.setSize( window.innerWidth, window.innerHeight );
        document.body.appendChild( renderer.domElement );

        var diameter = 20;
        var geometry = new THREE.CylinderGeometry( diameter, diameter, 15, 32 );

        var texture1 = new THREE.TextureLoader().load( 'images/image1.jpg' );
        var texture2 = new THREE.TextureLoader().load( 'images/image2.jpg' );
        var texture3 = new THREE.TextureLoader().load( 'images/image3.png' );

        texture1.wrapS = THREE.RepeatWrapping;
        //texture.wrapT = THREE.RepeatWrapping;
        //texture.repeat.set( 1, 4 );

        var materials = [];
        materials.push(new THREE.MeshBasicMaterial({ map: texture1 }));
        materials.push(new THREE.MeshBasicMaterial({ map: texture2 }));
        materials.push(new THREE.MeshBasicMaterial({ map: texture3 }));

        var cylinder = new THREE.Mesh( geometry, materials );
        cylinder.position.y = 25;
        scene.add( cylinder);

        camera.position.z = 40;


        function render() {
            requestAnimationFrame(render);
            //cylinder.rotation.z += 0.05;
          cylinder.rotation.y += 0.005;
            renderer.render(scene, camera);
        }
        render();
    </script>
</body>

【问题讨论】:

    标签: javascript three.js


    【解决方案1】:

    您想将三个纹理应用到您的圆柱体。

    如果您不想将纹理合并为单个纹理,一个简单的解决方案是渲染三个圆柱楔,每个都有自己的纹理。使用如下模式:

    var group = new THREE.Group();
    scene.add( group );
    
    var geometry = new THREE.CylinderBufferGeometry( 5, 5, 10, 16, 1, false, 0, 2 * Math.PI / 3 ); // 1/3 cylinder wedge
    
    var endCapMaterial = new THREE.MeshBasicMaterial();
    
    // mesh
    mesh = new THREE.Mesh( geometry, [ new THREE.MeshBasicMaterial( { map: texture1 } ), endCapMaterial, endCapMaterial ] );
    mesh.rotation.set( 0, 0, 0 );
    group.add( mesh );
    
    mesh = new THREE.Mesh( geometry, [ new THREE.MeshBasicMaterial( { map: texture2 } ), endCapMaterial, endCapMaterial ] );
    mesh.rotation.set( 0, 2 * Math.PI / 3, 0 );
    group.add( mesh );
    
    mesh = new THREE.Mesh( geometry, [ new THREE.MeshBasicMaterial( { map: texture3 } ), endCapMaterial, endCapMaterial ] );
    mesh.rotation.set( 0, 4 * Math.PI / 3, 0 );
    group.add( mesh );
    

    three.js r.89

    【讨论】:

      【解决方案2】:

      另一种方法是使用geometry.faces[i].materialIndex 属性为几何体的每个面分配纹理。在这种情况下,您应该使用三的倍数的径向线段数(如果您有 3 个纹理)。

      <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/89/three.min.js"></script>
      <html>
      <head>
          <title>My first three.js app</title>
          <style>
              body { margin: 0; overflow:hidden;}
              canvas { width: 100%; height: 100% }
          </style>
      </head>
      <body>
      <script>
          var scene = new THREE.Scene();
          var camera = new THREE.PerspectiveCamera( 100, window.innerWidth / window.innerHeight, 0.1, 1000 );
          camera.position.y = 24;
      
          var renderer = new THREE.WebGLRenderer();
          renderer.setSize( window.innerWidth, window.innerHeight );
          document.body.appendChild( renderer.domElement );
      
          var diameter = 20;
          var radialSegments = 33;
          var geometry = new THREE.CylinderGeometry( diameter, diameter, 15, radialSegments );
          
          var img1 = "http://d2gg9evh47fn9z.cloudfront.net/800px_COLOURBOX9108127.jpg";
          var img2 = "http://d2gg9evh47fn9z.cloudfront.net/thumb_COLOURBOX8923432.jpg";
          var img3 = "http://d2gg9evh47fn9z.cloudfront.net/800px_COLOURBOX19377428.jpg";
      
          var texture1 = new THREE.TextureLoader().load( img1 );
          var texture2 = new THREE.TextureLoader().load( img2 );
          var texture3 = new THREE.TextureLoader().load( img3 );
      
          THREE.DefaultLoadingManager.onLoad = function () {
              var materials = [];
              materials.push(new THREE.MeshBasicMaterial({ map: texture1 }));
              materials.push(new THREE.MeshBasicMaterial({ map: texture2 }));
              materials.push(new THREE.MeshBasicMaterial({ map: texture3 }));
              var l = geometry.faces.length;
              for (var i = 0; i < l; i++) {
                  if (geometry.faces[i].normal.y !== 0) {
                      // these are caps
                      geometry.faces[i].materialIndex = 0;
                  } else {
                      // each segment has 2 faces
                      geometry.faces[i].materialIndex = Math.floor(i * 3 / (radialSegments * 2));
                  }
              }
      
              var cylinder = new THREE.Mesh( geometry, materials);
              cylinder.position.y = 25;
              scene.add( cylinder);
      
              camera.position.z = 40;
      
              function render() {
                  requestAnimationFrame(render);
                  cylinder.rotation.y += 0.005;
                  renderer.render(scene, camera);
              }
              render();
          }
      </script>
      </body>

      【讨论】:

        猜你喜欢
        • 2013-07-29
        • 2012-09-06
        • 1970-01-01
        • 1970-01-01
        • 2013-02-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-08-23
        相关资源
        最近更新 更多