From 8e1a819cb5e86099c780c88b9d40f3c88d49fd71 Mon Sep 17 00:00:00 2001 From: Vincent Fretin Date: Mon, 30 Mar 2026 19:08:19 +0200 Subject: [PATCH 1/3] Set raycaster.camera to the active camera in order to raycast against sprites --- src/components/raycaster.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/components/raycaster.js b/src/components/raycaster.js index f13a5c1d957..c936d60e754 100644 --- a/src/components/raycaster.js +++ b/src/components/raycaster.js @@ -228,7 +228,9 @@ export var Component = registerComponent('raycaster', { // Raycast. this.updateOriginDirection(); rawIntersections.length = 0; + this.raycaster.camera = this.el.sceneEl.camera; this.raycaster.intersectObjects(this.objects, true, rawIntersections); + this.raycaster.camera = null; // Only keep intersections against objects that have a reference to an entity. intersections.length = 0; From 612e81965bf2dbf842f2b93bbc4093ada91acaf9 Mon Sep 17 00:00:00 2001 From: Vincent Fretin Date: Tue, 31 Mar 2026 10:18:27 +0200 Subject: [PATCH 2/3] Add example of raycaster on sprites --- examples/index.html | 1 + examples/test/raycaster/sprite.html | 74 +++++++++++++++++++++++++++++ 2 files changed, 75 insertions(+) create mode 100644 examples/test/raycaster/sprite.html diff --git a/examples/index.html b/examples/index.html index ce761d70987..11b0dec522f 100644 --- a/examples/index.html +++ b/examples/index.html @@ -207,6 +207,7 @@

Tests

  • Primitive: Torus
  • Raycaster
  • Raycaster (Simple)
  • +
  • Raycaster (Sprite)
  • Shaders
  • Shadows
  • Text
  • diff --git a/examples/test/raycaster/sprite.html b/examples/test/raycaster/sprite.html new file mode 100644 index 00000000000..e35c3ded647 --- /dev/null +++ b/examples/test/raycaster/sprite.html @@ -0,0 +1,74 @@ + + + + + Raycaster - Sprites + + + + + +

    Look at a sprite, it should turn red. Look away, it turns back to blue.

    + + + + + + + + + + + + + From ee13405c768a6cf1507252406e6a4bebd4b3dd98 Mon Sep 17 00:00:00 2001 From: Vincent Fretin Date: Tue, 31 Mar 2026 10:32:19 +0200 Subject: [PATCH 3/3] Add unit test for sprite raycasting --- tests/components/raycaster.test.js | 41 ++++++++++++++++++++++++++++++ 1 file changed, 41 insertions(+) diff --git a/tests/components/raycaster.test.js b/tests/components/raycaster.test.js index c1765223a71..36d2f2532a1 100644 --- a/tests/components/raycaster.test.js +++ b/tests/components/raycaster.test.js @@ -394,6 +394,47 @@ suite('raycaster', function () { }); }); + suite('sprite raycasting', function () { + var spriteEl; + + setup(function (done) { + spriteEl = document.createElement('a-entity'); + el.setAttribute('position', '0 0 1'); + el.setAttribute('raycaster', {near: 0.1, far: 10}); + + spriteEl.addEventListener('loaded', function () { + var material = new THREE.SpriteMaterial({color: 0x6699ff}); + var sprite = new THREE.Sprite(material); + spriteEl.setObject3D('mesh', sprite); + spriteEl.object3D.position.set(0, 0, -1); + setTimeout(() => { done(); }); + }); + sceneEl.appendChild(spriteEl); + }); + + test('can intersect sprites', function (done) { + spriteEl.addEventListener('raycaster-intersected', function () { + done(); + }); + sceneEl.object3D.updateMatrixWorld(); + component.refreshObjects(); + component.tock(); + }); + + test('emits intersection-cleared when looking away from sprite', function (done) { + spriteEl.addEventListener('raycaster-intersected', function () { + el.setAttribute('rotation', '90 0 0'); + spriteEl.addEventListener('raycaster-intersected-cleared', function () { + done(); + }, {once: true}); + component.tock(); + }, {once: true}); + sceneEl.object3D.updateMatrixWorld(); + component.refreshObjects(); + component.tock(); + }); + }); + suite('updateOriginDirection', function () { test('updates ray origin if position changes', function () { var origin;