Smithery Logo
MCPsSkillsDocsPricing
Login
Smithery Logo

Accelerating the Agent Economy

Resources

DocumentationPrivacy PolicySystem Status

Company

PricingAboutBlog

Connect

© 2026 Smithery. All rights reserved.

    tadams95

    threejs-interaction

    tadams95/threejs-interaction
    Design
    1 installs

    About

    SKILL.md

    Install

    Install via Skills CLI

    or add to your agent
    • Claude Code
      Claude Code
    • Codex
      Codex
    • OpenClaw
      OpenClaw
    • Cursor
      Cursor
    • Amp
      Amp
    • GitHub Copilot
      GitHub Copilot
    • Gemini CLI
      Gemini CLI
    • Kilo Code
      Kilo Code
    • Junie
      Junie
    • Replit
      Replit
    • Windsurf
      Windsurf
    • Cline
      Cline
    • Continue
      Continue
    • OpenCode
      OpenCode
    • OpenHands
      OpenHands
    • Roo Code
      Roo Code
    • Augment
      Augment
    • Goose
      Goose
    • Trae
      Trae
    • Zencoder
      Zencoder
    • Antigravity
      Antigravity
    ├─
    ├─
    └─

    About

    Three.js interaction - raycasting, controls, mouse/touch input, object selection...

    SKILL.md

    Three.js Interaction

    Raycasting

    const raycaster = new THREE.Raycaster();
    const mouse = new THREE.Vector2();
    
    function onClick(event) {
      mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
      mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;
    
      raycaster.setFromCamera(mouse, camera);
      const intersects = raycaster.intersectObjects(clickableObjects);
    
      if (intersects.length > 0) {
        const { object, point, face, uv } = intersects[0];
        console.log("Clicked:", object.name, "at", point);
      }
    }
    
    window.addEventListener("click", onClick);
    

    Touch Support

    function onTouchStart(event) {
      if (event.touches.length === 1) {
        const touch = event.touches[0];
        mouse.x = (touch.clientX / window.innerWidth) * 2 - 1;
        mouse.y = -(touch.clientY / window.innerHeight) * 2 + 1;
    
        raycaster.setFromCamera(mouse, camera);
        const intersects = raycaster.intersectObjects(clickableObjects);
        // Handle intersects...
      }
    }
    

    OrbitControls

    import { OrbitControls } from "three/examples/jsm/controls/OrbitControls.js";
    
    const controls = new OrbitControls(camera, renderer.domElement);
    controls.enableDamping = true;
    controls.dampingFactor = 0.05;
    controls.minDistance = 2;
    controls.maxDistance = 50;
    controls.maxPolarAngle = Math.PI / 2;
    controls.autoRotate = true;
    
    function animate() {
      controls.update(); // Required for damping
    }
    

    Other Controls

    // Fly controls
    import { FlyControls } from "three/examples/jsm/controls/FlyControls.js";
    const controls = new FlyControls(camera, renderer.domElement);
    controls.movementSpeed = 10;
    controls.update(clock.getDelta());
    
    // Pointer lock (FPS)
    import { PointerLockControls } from "three/examples/jsm/controls/PointerLockControls.js";
    const controls = new PointerLockControls(camera, document.body);
    document.addEventListener("click", () => controls.lock());
    

    TransformControls

    import { TransformControls } from "three/examples/jsm/controls/TransformControls.js";
    
    const transformControls = new TransformControls(camera, renderer.domElement);
    scene.add(transformControls);
    
    transformControls.attach(selectedMesh);
    transformControls.setMode("translate"); // "rotate", "scale"
    
    transformControls.addEventListener("dragging-changed", (event) => {
      orbitControls.enabled = !event.value;
    });
    

    Hover Effects

    let hoveredObject = null;
    
    function onMouseMove(event) {
      mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
      mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;
    
      raycaster.setFromCamera(mouse, camera);
      const intersects = raycaster.intersectObjects(hoverableObjects);
    
      if (hoveredObject) {
        hoveredObject.material.emissive.set(0x000000);
      }
    
      if (intersects.length > 0) {
        hoveredObject = intersects[0].object;
        hoveredObject.material.emissive.set(0x333333);
        document.body.style.cursor = "pointer";
      } else {
        hoveredObject = null;
        document.body.style.cursor = "default";
      }
    }
    

    World-Screen Conversion

    // World to screen
    function worldToScreen(position, camera) {
      const vector = position.clone().project(camera);
      return {
        x: ((vector.x + 1) / 2) * window.innerWidth,
        y: (-(vector.y - 1) / 2) * window.innerHeight,
      };
    }
    
    // Screen to world (on plane)
    function screenToWorld(screenX, screenY, camera, targetZ = 0) {
      const vector = new THREE.Vector3(
        (screenX / window.innerWidth) * 2 - 1,
        -(screenY / window.innerHeight) * 2 + 1,
        0.5
      ).unproject(camera);
    
      const dir = vector.sub(camera.position).normalize();
      const distance = (targetZ - camera.position.z) / dir.z;
      return camera.position.clone().add(dir.multiplyScalar(distance));
    }
    
    Recommended Servers
    Browser tool
    Browser tool
    Svelte
    Svelte
    Browserbase
    Browserbase
    Repository
    tadams95/kardashev-network
    Files