npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@uptimizr/aframe

v1.0.4

Published

A-Frame (WebXR) connector for Uptimizr — registers the `uptimizr` component over @uptimizr/three and adds XR controller/gaze capture.

Readme

@uptimizr/aframe

The A-Frame (WebXR) connector for Uptimizr.

A-Frame renders three.js under the hood — sceneEl.object3D is the THREE.Scene, sceneEl.camera the active THREE.Camera, and sceneEl.renderer the THREE.WebGLRenderer. So this package is a thin A-Frame layer over @uptimizr/three — it does not re-implement capture. A declarative component grabs those three objects and hands them to the three connector, which captures:

  • camera pose (position + forward direction) → view-direction heatmap
  • pointer move / click (normalized screen + optional raycast hit) → screen heatmaps
  • mesh picks → object-engagement analytics
  • FPS → performance
  • mesh visibility / hover dwell / gaze / resource sample (opt-in) → attention & footprint
  • camera gestures → navigation-intent analytics

three is a peer dependency; A-Frame itself is supplied by the host page (the connector never imports aframe — it registers against the global AFRAME and reads the host page's three.js instances, so it bundles neither). Capture starts when the component initializes and stops on teardown, tearing down every listener, timer, and animation-frame callback (no cookies, no persistent ids).

World-space data is normalized to the canonical wire frame by @uptimizr/three; sessions are attributed to the aframe connector while keeping three's native right-handed coordinate frame.

Install

npm install @uptimizr/aframe three

three is a peer dependency. A-Frame itself is supplied by the host page (load it from the official CDN or your own bundle) — see the note at the end of this README on why aframe is not an npm dependency.

Usage

Load A-Frame, then import this package (it registers the uptimizr component), and add the attribute to your <a-scene>:

<head>
  <script src="https://aframe.io/releases/1.7.0/aframe.min.js"></script>
  <script type="module">
    import "@uptimizr/aframe";
  </script>
</head>
<body>
  <a-scene uptimizr="projectId: your-project; collector: https://collect.example.com">
    <a-box position="0 1 -3" color="#4db4e6"></a-box>
    <a-sky color="#0b0e14"></a-sky>
  </a-scene>
</body>

A bare import "@uptimizr/aframe" is enough — the entry point registers the component against the global AFRAME. (To register against an explicit instance, call registerUptimizrComponent(AFRAME).)

WebXR — the differentiator

A-Frame is WebXR-first, so the connector adds the one thing the three.js desktop path does not: it maps XR input onto the existing source-neutral schema events with no new event types or fields:

| XR signal | Emitted as | | -------------------------------------- | ---------------------------------------------------- | | Controller / gaze pose (per frame) | pointer_move with a world-space ray + source | | Controller handedness | handedness: "left" \| "right" (+ sourceId) | | Tracked controller | source: "xr-controller" | | Articulated hand | source: "hand" | | Gaze target-ray | source: "gaze" | | Transient / screen tap | source: "transient" | | select (trigger) | pointer_click (+ mesh_interaction kind:select) | | squeeze (grip) | mesh_interaction kind:squeeze |

The head/headset pose is already captured as camera_sample by @uptimizr/three (in XR, three's active camera is the headset). XR capture is on by default; disable it with uptimizr="...; xr: false". In-scene XR hits (hitPoint/hitMesh on the ray samples and mesh_interaction on select/squeeze) are resolved by default with three's raycaster over the live scene graph (createXrRaycaster from @uptimizr/three); set xrRaycast: false to capture controller/gaze rays and pointer_click only. Programmatic hosts using the re-exported trackScene can supply their own probe via xr: { raycast }. The only id emitted is the ephemeral, session-local handedness disambiguator — never a persistent device/user id.

Options

The component schema maps onto the three connector's TrackSceneOptions:

| Attribute | Meaning | | -------------------------------------------------- | ------------------------------------------------- | | projectId | Project identifier (public, non-secret) | | collector | Collector endpoint base URL | | sampleCameraMs / samplePerfMs | Sampling intervals (0 ⇒ connector default) | | pointerMoveThrottleMs | Pointer-move throttle (0 ⇒ default) | | sceneDescription | Free-text scene label | | sceneId | Scene/area id on every event (ADR 0010) | | cameraType | Camera-kind override (arc-rotate, free, …) | | meshVisibility / hoverDwell / resourceSample | Opt-in capture channels (off by default) | | gaze | Opt-in world-space gaze hits (off by default) | | cameraGesture | Navigation gesture capture (default true) | | xr | WebXR controller/gaze capture (default true) | | xrSampleMs | XR pose sampling interval (0 ⇒ 250 ms) | | xrRaycast | Resolve XR rays to in-scene hits (default true) | | disabled | Collect nothing | | debug | Console debug logs |

Replay

A-Frame sessions replay through the existing @uptimizr/replay three driver — the captured payload is three.js data, only the connector name differs. Replay drivers are selected by the host's engine, not by connector name, so no A-Frame-specific driver is needed.

Boundary

Depends only on @uptimizr/three, @uptimizr/sdk-core, and @uptimizr/schema. @uptimizr/three is the one connector dependency this package has — by design, since A-Frame is three.js.

aframe is intentionally not declared as an npm (peer) dependency: the connector is fully structural (it never imports aframe), and A-Frame's published package pulls a git-resolved subdependency (three-bmfont-text) that the repo's supply-chain policy blocks. The host page provides A-Frame — load it from the official CDN or your own bundle.

License

Apache-2.0 © Uptimizr.