鼠标位置与 THREE.Point 交互

发布于 2025-01-16 14:12:25 字数 3030 浏览 1 评论 0原文

我正在学习 Three.js 并尝试重现一些很酷的效果作为训练方法。

我有一个 Obj 文件地球仪,我想向其中添加一些粒子交互。

到目前为止我的工作: https://codepen.io/Imsenji/pen/QWOBMWN?editors =0010

我正在尝试做什么:https://dala.craftedbygc.com/ (或类似)

这是我的代码:

// OBJ model

const obj = new OBJLoader();
obj.load("https://res.cloudinary.com/dltqzyazm/raw/upload/v1648118569/2dgame/globe2_gl4laq.obj", function (object) {
  let material = new THREE.PointsMaterial({
    color: colour,
    size: 0.035,
    // map: cross,
  });
  let mesh = new THREE.Points(object.children[0].geometry, material);

  mesh.scale.multiplyScalar(0.025);
  mesh.rotation.y = 2 * Math.PI * 0.7;
  mesh.position.x = objectsDistance * 0.5;
  mesh.position.y = -objectsDistance * 0.1;
  scene.add(mesh);
});
//----------------------


 * Particles
 */
// Geometry
const particlesCount = 1000;
const positions = new Float32Array(particlesCount * 3);

for (let i = 0; i < particlesCount; i++) {
  positions[i * 3 + 0] = (Math.random() - 0.5) * 10;
  positions[i * 3 + 1] =
    objectsDistance * 0.5 -
    Math.random() * objectsDistance * sectionMeshes.length;
  positions[i * 3 + 2] = (Math.random() - 0.5) * 10;
}

const particlesGeometry = new THREE.BufferGeometry();
particlesGeometry.setAttribute(
  "position",
  new THREE.BufferAttribute(positions, 3)
);

// Material
const particlesMaterial = new THREE.PointsMaterial({
  color: "#c0a43c",
  sizeAttenuation: true,
  size: 0.2,
  transparent: true,
  map: cross,
});

// Points
const particles = new THREE.Points(particlesGeometry, particlesMaterial);
scene.add(particles);

//   // Interaction
var uniforms = {
  mouse: {
    value: new THREE.Vector3(),
  },
  radius: {
    value: 3.5,
  },
};

material.onBeforeCompile = (shader) => {
  shader.uniforms.mouse = uniforms.mouse;
  shader.uniforms.radius = uniforms.radius;
  // console.log(shader.vertexShader);
  shader.vertexShader =
    `
    uniform vec3 mouse;
  uniform float radius;
` + shader.vertexShader;
  shader.vertexShader = shader.vertexShader.replace(
    `#include <begin_vertex>`,
    `#include <begin_vertex>

    vec3 dir = transformed - mouse;

    float dist = length(dir);

    if (dist < radius){
      float ratio = 1. - dist / radius;

      vec3 shift = dir * 2. * (ratio * ratio);

      transformed += shift;
    }

  `
  );
};

var plane = new THREE.Plane(new THREE.Vector3(0, 0, 1), 0);
var raycaster = new THREE.Raycaster();
var mouse = new THREE.Vector2();
window.addEventListener("mousemove", (event) => {
  mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
  mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;

  raycaster.setFromCamera(mouse, camera);

  raycaster.ray.intersectPlane(plane, uniforms.mouse.value);
});

看起来像 raycaster.ray.intersectPlane(plane, Uniforms.mouse.value); 不工作。这就是我的问题。

任何帮助/建议将不胜感激。

I am learning Three.js and trying to reproduce some cool effects as a training method.

I have a Obj file globe which I want to add some particles interaction to.

my work so far : https://codepen.io/Imsenji/pen/QWOBMWN?editors=0010

What I'm trying to do: https://dala.craftedbygc.com/ ( or similar)

this is my code :

// OBJ model

const obj = new OBJLoader();
obj.load("https://res.cloudinary.com/dltqzyazm/raw/upload/v1648118569/2dgame/globe2_gl4laq.obj", function (object) {
  let material = new THREE.PointsMaterial({
    color: colour,
    size: 0.035,
    // map: cross,
  });
  let mesh = new THREE.Points(object.children[0].geometry, material);

  mesh.scale.multiplyScalar(0.025);
  mesh.rotation.y = 2 * Math.PI * 0.7;
  mesh.position.x = objectsDistance * 0.5;
  mesh.position.y = -objectsDistance * 0.1;
  scene.add(mesh);
});
//----------------------


 * Particles
 */
// Geometry
const particlesCount = 1000;
const positions = new Float32Array(particlesCount * 3);

for (let i = 0; i < particlesCount; i++) {
  positions[i * 3 + 0] = (Math.random() - 0.5) * 10;
  positions[i * 3 + 1] =
    objectsDistance * 0.5 -
    Math.random() * objectsDistance * sectionMeshes.length;
  positions[i * 3 + 2] = (Math.random() - 0.5) * 10;
}

const particlesGeometry = new THREE.BufferGeometry();
particlesGeometry.setAttribute(
  "position",
  new THREE.BufferAttribute(positions, 3)
);

// Material
const particlesMaterial = new THREE.PointsMaterial({
  color: "#c0a43c",
  sizeAttenuation: true,
  size: 0.2,
  transparent: true,
  map: cross,
});

// Points
const particles = new THREE.Points(particlesGeometry, particlesMaterial);
scene.add(particles);

//   // Interaction
var uniforms = {
  mouse: {
    value: new THREE.Vector3(),
  },
  radius: {
    value: 3.5,
  },
};

material.onBeforeCompile = (shader) => {
  shader.uniforms.mouse = uniforms.mouse;
  shader.uniforms.radius = uniforms.radius;
  // console.log(shader.vertexShader);
  shader.vertexShader =
    `
    uniform vec3 mouse;
  uniform float radius;
` + shader.vertexShader;
  shader.vertexShader = shader.vertexShader.replace(
    `#include <begin_vertex>`,
    `#include <begin_vertex>

    vec3 dir = transformed - mouse;

    float dist = length(dir);

    if (dist < radius){
      float ratio = 1. - dist / radius;

      vec3 shift = dir * 2. * (ratio * ratio);

      transformed += shift;
    }

  `
  );
};

var plane = new THREE.Plane(new THREE.Vector3(0, 0, 1), 0);
var raycaster = new THREE.Raycaster();
var mouse = new THREE.Vector2();
window.addEventListener("mousemove", (event) => {
  mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
  mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;

  raycaster.setFromCamera(mouse, camera);

  raycaster.ray.intersectPlane(plane, uniforms.mouse.value);
});

it seems like raycaster.ray.intersectPlane(plane, uniforms.mouse.value); not working. that's my question.

any help/advice would be appreciated.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文