36 frames — one every 10° — loaded from a local sequence

Basic Setup

Everything ease360° needs is an ordered image sequence and three options. This example goes from install to a working viewer — no loader, no callbacks, just the minimum viable setup.

In this example you will learn the following:

1. Install

ease360° ships as a UMD bundle — it works in any environment without a build step. Pick the approach that fits your stack.

<!-- Script tag — no build tools required -->
<script src="lib/ease360-1.0.0.min.js"></script>
<link  rel="stylesheet" href="lib/ease360.css">
# npm
npm install ease360
// ESM
import ease360 from 'ease360';

// CommonJS
const ease360 = require('ease360');

Always include ease360.css alongside the script — it sets the grab cursor on the viewer so users immediately know it's interactive. Without it the cursor stays as the default arrow and the affordance is lost.

2. Add a container

ease360° injects a <canvas> element into whichever container you point it at. Give the container a size in CSS — the canvas fills it. You don't create the canvas yourself.

<div id="myEase360"></div>
#myEase360 {
    width:  100%;
    height: 480px;
}

3. Build the frames sequence

ease360° needs an ordered array of image paths — one per angle step, covering a full 360° rotation. The frame count must divide evenly into 360: 18 frames (every 20°) is lightweight with visible stepping at slow speeds; 36 frames (every 10°) is the sweet spot for most product work; 72 frames (every 5°) is silky at any speed with a heavier payload.

The teapot used here has 36 frames shot every 10°, named sequentially: teapot_0.jpg through teapot_35.jpg. That naming convention — a zero-based index stepping by 1 — is the most portable: easy to generate, easy to validate, no ambiguity about order.

// Build the sequence from a local image folder.
// Array index = frame order. ease360° renders them in this exact sequence.
const imgPath    = 'images/teapot_green_36/';
const greenTeapot = Array.from(
    { length: 36 },
    (_, i) => `${imgPath}teapot_${i}.jpg`
);

// For CDN-served assets (recommended for production) see Example 5 — CDN & Cloudinary,
// or pass any valid URL array here directly.

4. Initialize

ease360(selector, options) — first argument is a CSS selector or DOM element. Only one option is truly required: frames. sourceWidth and sourceHeight are optional — see the next section for when to provide them and why it matters.

const myEase360 = ease360('#myEase360', {
    frames:         greenTeapot, // required — ordered array of image paths
    sourceWidth:    540,         // optional — see below for the trade-offs
    sourceHeight:   540,         // optional — omit to let ease360° detect automatically
    backgroundSize: 'cover'      // fill the container, preserve aspect ratio
});

That's it — drag to spin, physics damping on release. The canvas fades in automatically once the first frame loads. For loading indicators, callbacks, and controls see Example 2 — Callbacks & Control.

5. sourceWidth and sourceHeight

Tell ease360° the pixel dimensions of the delivered image — what the browser actually receives, not the master file. These drive all canvas math: scaling, aspect ratio, cover positioning, and crop offsets. They are optional. When omitted, ease360° probes frames[0] automatically. Provide them to skip the probe for synchronous init, no CORS dependency, and no async delay (typically 50–200ms on a CDN).

// Probe — convenient, small async delay, requires CORS headers on your server
ease360('#myEase360', { frames: greenTeapot, backgroundSize: 'cover' });

// Explicit — synchronous init, no probe, no CORS dependency
ease360('#myEase360', {
    frames:         greenTeapot,
    sourceWidth:    540,  // pixel width the browser receives — not the master
    sourceHeight:   540,  // must match the delivered size, not the original upload
    backgroundSize: 'cover'
});

For CDN assets with URL-based resizing, see Example 5 — CDN & Cloudinary for the full pattern. If anything goes wrong — black canvas, nothing rendering — open the console. ease360° logs a [ease360] message for every failure including CORS blocks and probe failures. See Common Errors & Debugging.