threejs线框显示与消失

1、首先创建一个场景、相机和渲染器

// 创建一个场景
var scene = new THREE.Scene();

// 创建一个相机
var camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
camera.position.z = 5;

// 创建一个渲染器
var renderer = new THREE.WebGLRenderer({ antialias: true });
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);

2、使用GLTFLoader加载GLB文件,并遍历场景中的子对象。

对于每个Group,我们将其添加到场景中,并为其添加鼠标移入和移出事件监听器。

// 加载GLB文件
var loader = new THREE.GLTFLoader();
loader.load('path/to/your/file.glb', function (gltf) {
  // 获取GLTF场景
  var gltfScene = gltf.scene;

  // 遍历场景中的子对象,将Group添加到场景中
  gltfScene.traverse(function (child) {
    if (child instanceof THREE.Group) {
      scene.add(child);

      // 添加鼠标移入和移出事件监听器
      child.addEventListener('mouseover', function () {
        createEdges(child);
      });

      child.addEventListener('mouseout', function () {
        var edgesMesh = child.getObjectByName("edgesMesh");
        if (edgesMesh) {
          child.remove(edgesMesh);
        }
      });
    }
  });
}, undefined, function (error) {
  console.error(error);
});

3、在鼠标移入,移出

移入时,我们使用createEdges函数创建边框几何体,并将其添加到当前Group中。
移出时,我们使用getObjectByName方法找到边框几何体,并将其从Group中移除。

// 添加鼠标事件监听器
document.addEventListener('mousemove', onMouseMove, false);

function onMouseMove(event) {
  // 计算鼠标在屏幕上的位置
  var mouse = new THREE.Vector2();
  mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
  mouse.y = - (event.clientY / window.innerHeight) * 2 + 1;

  // 创建一个射线投射器
  var raycaster = new THREE.Raycaster();
  raycaster.setFromCamera(mouse, camera);

  // 检测与射线相交的物体
  var intersects = raycaster.intersectObjects(scene.children, true);

  // 遍历相交的物体,判断是否是Group
  for (var i = 0; i < intersects.length; i++) {
    var obj = intersects[i].object;

    if (obj instanceof THREE.Group) {
      // 鼠标移入Group
      if (!obj.userData.hovered) {
        createEdges(obj);
        obj.userData.hovered = true;
      }
    } else {
      // 鼠标移出Group
      if (obj.parent instanceof THREE.Group) {
        var group = obj.parent;
        if (group.userData.hovered) {
          var edgesMesh = group.getObjectByName("edgesMesh");
          if (edgesMesh) {
            group.remove(edgesMesh);
          }
          group.userData.hovered = false;
        }
      }
    }
  }
}

4、全部代码

请注意,我们为每个Group添加了userData.hovered属性来跟踪Group是否已经被鼠标移入过

// 创建一个场景
var scene = new THREE.Scene();

// 创建一个相机
var camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
camera.position.z = 5;

// 创建一个渲染器
var renderer = new THREE.WebGLRenderer({ antialias: true });
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);

// 创建边框材质
var edgeMaterial = new THREE.LineBasicMaterial({ color: 0xff0000 });

// 创建边框几何体函数
function createEdges(group) {
  var edges = new THREE.EdgesGeometry(group.children[0].geometry);
  var edgesMesh = new THREE.LineSegments(edges, edgeMaterial);
  group.add(edgesMesh);
}

// 加载GLB文件
var loader = new THREE.GLTFLoader();
loader.load('path/to/your/file.glb', function (gltf) {
  // 获取GLTF场景
  var gltfScene = gltf.scene;

  // 遍历场景中的子对象,将Group添加到场景中
  gltfScene.traverse(function (child) {
    if (child instanceof THREE.Group) {
      scene.add(child);

      // 添加鼠标移入和移出事件监听器
      child.addEventListener('mouseover', function () {
        createEdges(child);
      });

      child.addEventListener('mouseout', function () {
        var edgesMesh = child.getObjectByName("edgesMesh");
        if (edgesMesh) {
          child.remove(edgesMesh);
        }
      });
    }
  });
}, undefined, function (error) {
  console.error(error);
});

// 添加鼠标事件监听器
document.addEventListener('mousemove', onMouseMove, false);

function onMouseMove(event) {
  // 计算鼠标在屏幕上的位置
  var mouse = new THREE.Vector2();
  mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
  mouse.y = - (event.clientY / window.innerHeight) * 2 + 1;

  // 创建一个射线投射器
  var raycaster = new THREE.Raycaster();
  raycaster.setFromCamera(mouse, camera);

  // 检测与射线相交的物体
  var intersects = raycaster.intersectObjects(scene.children, true);

  // 遍历相交的物体,判断是否是Group
  for (var i = 0; i < intersects.length; i++) {
    var obj = intersects[i].object;

    if (obj instanceof THREE.Group) {
      // 鼠标移入Group
      if (!obj.userData.hovered) {
        createEdges(obj);
        obj.userData.hovered = true;
      }
    } else {
      // 鼠标移出Group
      if (obj.parent instanceof THREE.Group) {
        var group = obj.parent;
        if (group.userData.hovered) {
          var edgesMesh = group.getObjectByName("edgesMesh");
          if (edgesMesh) {
            group.remove(edgesMesh);
          }
          group.userData.hovered = false;
        }
      }
    }
  }
}

// 渲染场景
function animate() {
  requestAnimationFrame(animate);
  renderer.render(scene, camera);
}
animate();
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

国服第三切图仔

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值