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

anime-cursor

v2.1.3

Published

A lightweight JavaScript library for animated custom cursors

Readme

AnimeCursor v2

[简体中文]

Visit the official website for more informations

Read documents to get started with AnimeCursor

AnimeCursor is a lightweight JavaScript library for frame-by-frame animated custom cursors.

AnimeCursor has no dependencies on any frameworks, making it suitable for personal websites, creative portfolios, and experimental UI projects.


✨ Features

  • Native CSS Cursor – Uses the browser's native cursor, no simulated elements, high performance and accuracy.
  • Independent Frame Images – Supports multi-frame animations using separate image files (PNG, SVG, etc.).
  • Smart Frame Detection – Automatically detects numeric suffixes in image filenames (e.g., cursor_01.png, cursor (02).png, cursor[3].png). Just provide the first frame, and AnimeCursor will generate all frames.
  • Variable Speed Animation – Use arrays for frames and duration to create complex timing patterns (e.g., frames: [2, 3], duration: [0.2, 1] means 2 frames in 0.2s, then 3 frames in 1s).
  • Static Cursor Support – If frames or duration is missing or invalid, the cursor is treated as static (single image).
  • Automatic Cursor Switching – Define cursor styles for specific HTML tags or via data-cursor attributes.
  • Lightweight & Zero Dependencies – Built with vanilla JavaScript, no external libraries required.

📦 Installation

CDN

<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/anime-cursor.umd.min.js"></script>

npm

npm i anime-cursor
import AnimeCursor from 'anime-cursor';
new AnimeCursor({...});

Host Yourself

<script src="anime-cursor.umd.min.js"></script>

🚀 How to use

Here is an example of how to use AnimeCursor:

IMPORTANT

  • Ensure the initialization code is placed within the <body> tag of your HTML document.
  • For optimal performance, it is recommended to initialize AnimeCursor before the DOM has fully loaded, as certain features require execution prior to the completion of DOM loading.
new AnimeCursor({
    debug: true, // optional, shows debug overlay
    enableTouch: false, // optional, enable on touch devices
    fallbackCursor: 'auto', // optional, fallback cursor type
    excludeSelectors: 'input, textarea, [contenteditable]', // optional, restore native text cursor
    cursors: {
        // each cursor type must have an image and frames/duration
        idle: {
            image: 'https://example.com/cursor_default.png', // static cursor (no animation)
            default: true // set as default cursor
        },
        // variable speed animation with independent frames
        pointer: {
            tags: ['a', 'button'], // apply to these HTML tags
            image: 'https://example.com/pointer_001.png', // AnimeCursor will automatically find pointer_002.png, pointer_003.png, etc.
            frames: 4,               // total frames (uniform animation)
            duration: 0.4,           // total duration in seconds
            offset: [15, 25],        // hotspot offset (x, y) for url()
            pingpong: true           // enable alternate loop
        },
        // array-based variable speed animation
        custom: {
            image: 'https://example.com/custom_01.png',
            frames: [2, 3, 1],        // first 2 frames, then 3 frames, then 1 frame
            duration: [0.2, 1.0, 0.5], // each segment duration
            offset: [8, 8],
            pingpong: false
        },
        // static cursor (no frames or duration)
        text: {
            tags: ['p', 'h1', 'h2', 'span'],
            image: 'https://example.com/cursor_text.png'
        }
    }
});

For non-default cursors, if you need a specific element to trigger the cursor, manually add the data-cursor attribute to the element. For example: <div class="custom-div" data-cursor="pointer"></div>.

⚙️ Configuration Options

cursors (Required)

An object that defines all cursor types. Each key is a cursor name (any string).

Cursor Configuration Parameters

| Parameter | Type | Required | Description | | ---------- | ------------------ | -------- | ------------------------------------------------------------ | | image | string | Yes | URL of the first frame image. AnimeCursor will automatically detect numeric suffixes to generate subsequent frames (e.g., image_001.pngimage_002.png, image_003.png). If you want a single static image, just provide one image. | | frames | number | number[] | Yes | Number of frames (for uniform animation) or an array of segment lengths (for variable speed). Total frames = sum of array elements. If not provided, the cursor is static. | | duration | number | number[] | Yes | Total duration in seconds (for uniform) or array of segment durations (must match frames array length). | | tags | string[] | No | HTML tag names (e.g., ['a', 'button']) that should use this cursor. If omitted, the cursor can only be applied via data-cursor attribute. | | offset | [number, number] | No | Hotspot offset (x, y) in pixels. Default: [0, 0]. The offset defines where the actual click point is relative to the top-left of the image. | | pingpong | boolean | No | If true, the animation plays forward then backward alternately. Default: false. | | fallback | string | No | Fallback cursor type (e.g., auto, pointer). Default: value of fallbackCursor in root options. | | default | boolean | No | Set this cursor as the default cursor (used when no other cursor applies). Only one cursor can be default. |

Root Options

| Option | Type | Default | Description | | ------------------ | ------- | -------------------------------------- | ------------------------------------------------------------ | | combineAnimations | boolean | false | Automatically merges cursor animations with element‑defined animations (via data-ac-animation). When enabled, any element with the data-ac-animation attribute will have its own CSS animation combined with the cursor animation, allowing both to run simultaneously without overriding each other. | | debug | boolean | false | Enables a debug overlay showing current cursor type and coordinates. | | enableTouch | boolean | false | Allow animated cursors on touch devices (detected automatically, disabled by default). | | fallbackCursor | string | 'auto' | Global fallback cursor for all animated cursors (e.g., 'auto', 'pointer'). | | excludeSelectors | string | 'input, textarea, [contenteditable]' | CSS selectors that should always use the native text cursor. |

📝 Notes

🖼️ Independent Frame Images

  • AnimeCursor expects the first frame file to contain a numeric suffix (e.g., cursor_001.png). It will automatically generate URLs for subsequent frames by incrementing the number while preserving formatting (leading zeros, parentheses, brackets).
  • Supported patterns:
    • cursor_01.pngcursor_02.png, cursor_03.png, …
    • cursor(01).pngcursor(02).png, cursor(03).png, …
    • cursor[1].pngcursor[2].png, cursor[3].png, …
    • cursor_1.pngcursor_2.png, cursor_3.png, … (no padding)
    • If no number is found, the library will append _%d (e.g., cursor.pngcursor_1.png, cursor_2.png).
  • Important: All frames must be the same size. The actual cursor size is the natural size of the images; scale them beforehand if needed.

🎞️ Animation Rules

  • Uniform Animation: frames and duration are both numbers. The animation cycles through all frames evenly over the total duration.
  • Variable Speed Animation: frames and duration are arrays of equal length. Each segment defines a number of frames and the time to play them. The frames are evenly distributed within each segment.
  • Static Cursor: If frames or duration is missing, or if they are invalid (e.g., non-positive numbers, mismatched array lengths), the cursor is treated as static (only the first image is used). A warning will be logged in the console.

🎞️ Combining Animations

If your elements already have their own CSS animations (e.g., animation: spin 2s infinite), they may override AnimeCursor's cursor animations. To make both play together, enable the combineAnimations global option and add a data-ac-animation attribute to the element with your animation definition(s). AnimeCursor will then automatically combine them.

Example:

<button data-ac-animation="mySpin 2s linear infinite">Click Me</button>
new AnimeCursor({
    combineAnimations: true,
    cursors: { ... }
});

Multiple animations can be listed, separated by commas.

🧩 Tagging Mechanism

AnimeCursor automatically adds the appropriate cursor style to elements based on tags and data-cursor attributes:

  • If an element's tag name matches a tags list, the corresponding cursor will be applied.
  • You can also manually set data-cursor="cursorName" on any element to force a specific cursor.
  • The default cursor is used when no other rule matches.

🔧 Performance

Because v2 uses native CSS cursor property and CSS animations, there is no JavaScript mousemove listener (except when debug mode is enabled). This yields optimal performance and smooth cursor movement.

❌ Error Handling

  • Missing required configuration will throw an error and stop initialization.
  • Invalid optional configuration (e.g., mismatched array lengths) will log a warning and treat the cursor as static.
  • All errors and warnings are prefixed with [AnimeCursor].

AnimeCursor v2

访问官网以获取更多信息

阅读文档快速上手 AnimeCursor

AnimeCursor 是一个轻量级自定义逐帧动画光标 JavaScript 库。

AnimeCursor 无需依赖任何框架,适合个人网站、创意作品集以及实验性 UI 项目。


✨ 特性

  • 原生 CSS 光标 – 使用浏览器原生光标,无需模拟元素,性能更高,定位更精准。
  • 独立帧图片支持 – 支持使用多张独立图片(PNG、SVG 等)制作逐帧动画。
  • 智能帧识别 – 自动识别文件名中的数字序号(如 cursor_01.pngcursor (02).pngcursor[3].png),只需提供第一帧,库会自动生成后续帧。
  • 变速动画framesduration 可设置为数组,实现复杂的时间节奏(例如 frames: [2, 3], duration: [0.2, 1] 表示前 2 帧 0.2 秒,后 3 帧 1 秒)。
  • 静态光标 – 如果不设置 framesduration,或设置无效,则视为静态光标(仅使用第一帧)。
  • 自动光标切换 – 通过 HTML 标签或 data-cursor 属性自动切换光标样式。
  • 轻量无依赖 – 原生 JavaScript 编写,不依赖任何第三方库。

📦 部署方法

CDN

<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/anime-cursor.umd.min.js"></script>

npm

npm i anime-cursor
import AnimeCursor from 'anime-cursor';
new AnimeCursor({...});

本地部署

<script src="anime-cursor.umd.min.js"></script>

🚀 基础用法

下面是一个 AnimeCursor 使用示例:

重要提示

  • 请务必将初始化代码置于HTML文档的 <body> 标签内部。
  • 为获得最佳性能,建议在DOM完全加载之前初始化AnimeCursor,因其部分功能需在DOM加载完成前执行。
new AnimeCursor({
    debug: true, // 可选,显示调试浮层
    enableTouch: false, // 可选,在触屏设备上启用
    fallbackCursor: 'auto', // 可选,备用光标类型
    excludeSelectors: 'input, textarea, [contenteditable]', // 可选,恢复原生文本光标
    cursors: {
        // 每种光标必须有 image 和 frames/duration
        idle: {
            image: 'https://example.com/cursor_default.png', // 静态光标(无动画)
            default: true // 设为默认光标
        },
        // 变速动画 + 独立帧图片
        pointer: {
            tags: ['a', 'button'], // 应用到这些标签
            image: 'https://example.com/pointer_001.png', // 自动识别后续帧
            frames: 4,               // 总帧数(匀速动画)
            duration: 0.4,           // 总时长(秒)
            offset: [15, 25],        // 热点偏移 (x, y)
            pingpong: true           // 开启乒乓循环
        },
        // 数组形式的变速动画
        custom: {
            image: 'https://example.com/custom_01.png',
            frames: [2, 3, 1],        // 前2帧,接着3帧,最后1帧
            duration: [0.2, 1.0, 0.5], // 对应时长
            offset: [8, 8],
            pingpong: false
        },
        // 静态光标(无 frames/duration)
        text: {
            tags: ['p', 'h1', 'h2', 'span'],
            image: 'https://example.com/cursor_text.png'
        }
    }
});

对于非默认光标,如果需要某元素触发该光标,请手动为该元素添加 data-cursor。例如:<div class="custom-div" data-cursor="pointer"></div>

⚙️ 配置项说明

cursors(必填)

用于定义所有光标类型的对象。每一个 key 代表一种光标类型(名称可以自由定义)。

光标配置参数

| 参数 | 类型 | 必填 | 描述 | | ---------- | ------------------ | ------ | ------------------------------------------------------------ | | image | string | | 第一帧图片的 URL。库会自动识别数字后缀生成后续帧(如 image_001.pngimage_002.pngimage_003.png)。如果只需要静态光标,则只需提供一张图片。 | | frames | number | number[] | | 帧数(匀速动画时为一个数字)或帧段数组(变速动画)。总帧数 = 数组元素之和。若不设置,则视为静态光标。 | | duration | number | number[] | | 总时长(秒)(匀速动画)或时长数组(必须与 frames 数组长度一致)。 | | tags | string[] | 否 | HTML 标签名数组(如 ['a', 'button']),应用该光标的标签。若不提供,则只能通过 data-cursor 属性应用。 | | offset | [number, number] | 否 | 热点偏移 (x, y),单位像素。默认为 [0, 0]。偏移定义了相对于图片左上角的实际点击位置。 | | pingpong | boolean | 否 | 若为 true,动画会正向播放再反向播放,循环交替。默认为 false。 | | fallback | string | 否 | 备用光标类型(如 autopointer)。默认使用根选项中的 fallbackCursor。 | | default | boolean | 否 | 将此光标设为默认光标(当没有其他光标匹配时使用)。只能有一个光标设为 true。 |

根选项

| 选项 | 类型 | 默认值 | 描述 | | ------------------ | ------- | -------------------------------------- | ------------------------------------------------------------ | | combineAnimations | boolean | false | 自动将光标动画与元素自身定义的动画(通过 data-ac-animation)合并。开启后,任何带有 data-ac-animation 属性的元素,其光标动画与用户动画会同时播放,互不覆盖。 | | debug | boolean | false | 启用调试浮层,显示当前光标类型和坐标。 | | enableTouch | boolean | false | 允许在触屏设备上显示动画光标(默认自动检测并禁用)。 | | fallbackCursor | string | 'auto' | 全局备用光标类型,用于所有动画光标(如 'auto''pointer')。 | | excludeSelectors | string | 'input, textarea, [contenteditable]' | 始终使用原生文本光标的 CSS 选择器。 |

📝 注意事项

🖼️ 独立帧图片

  • AnimeCursor 期望第一帧图片的文件名包含数字序号(如 cursor_001.png)。它会自动递增该数字并保留格式(前导零、括号、方括号等)来生成后续帧的 URL。
  • 支持的格式示例:
    • cursor_01.pngcursor_02.pngcursor_03.png……
    • cursor(01).pngcursor(02).pngcursor(03).png……
    • cursor[1].pngcursor[2].pngcursor[3].png……
    • cursor_1.pngcursor_2.pngcursor_3.png……(无前导零)
    • 如果没有找到数字,库会自动添加 _%d(例如 cursor.pngcursor_1.pngcursor_2.png)。
  • 重要:所有帧的图片尺寸必须相同。光标实际大小即为图片的原始尺寸,如需缩放请预先处理好图片。

🎞️ 动画判定

  • 匀速动画framesduration 均为数字。总帧数均匀分布到总时长中。
  • 变速动画framesduration 均为等长数组。每个片段指定帧数和该片段的时长,片段内的帧均匀分布。
  • 静态光标:如果缺少 framesduration,或者设置无效(如非正数、数组长度不匹配),则光标被视为静态(仅使用第一帧图片)。控制台会输出警告。

🎞️ 组合动画

如果元素自身已经拥有 CSS 动画(例如 animation: spin 2s infinite),这些动画可能会覆盖 AnimeCursor 的光标动画。要让两者同时播放,请启用 combineAnimations 全局选项,并为元素添加 data-ac-animation 属性,将你的动画定义写入其中。AnimeCursor 会自动将两者组合。

示例:

<button data-ac-animation="mySpin 2s linear infinite">点我</button>
new AnimeCursor({
    combineAnimations: true,
    cursors: { ... }
});

多个动画可用逗号分隔。

🧩 标记机制

AnimeCursor 会根据 tagsdata-cursor 自动应用光标样式:

  • 若元素标签名匹配某个 tags,则应用对应的光标。
  • 你也可以手动给任意元素添加 data-cursor="光标名称" 来强制指定光标。
  • 当没有其他规则匹配时,使用默认光标。

🔧 性能表现

v2 版本使用原生 CSS cursor 属性和 CSS 动画,除了 debug 模式外,不再需要 JavaScript 监听鼠标移动。因此性能极佳,光标移动流畅。

❌ 错误处理

  • 缺少必填配置会抛出错误并停止初始化。
  • 无效的可选配置(如数组长度不匹配)会输出警告并将该光标视为静态。
  • 所有错误和警告均以 [AnimeCursor] 前缀输出到控制台。