Easily Create an Interactive Custom Cursor With JS — Custom-Cursor.JS

Sean Grindal
The Startup
Published in
3 min readOct 11, 2020

Before we dive in you can check out this simple live example of the type of custom-cursor I’m referring to.

The web is evolving at an incredible pace, yet the web cursor has remained unchanged for decades. I think it’s about time we not only add some flair to the cursor but also add to its UI capabilities.

However, simply because the mouse cursor has been a constant for so long, changing it up can be jarring and irritating to users if implemented incorrectly. But let’s not let that stop us! Let’s forge ahead and do it right.

I’ve implemented a lot of custom cursors in personal and client projects in the past few years. I initially imagined custom cursors as simply glorified divs forced to follow the user’s cursor — something easily achieved with the following few lines of code:

Set your cursor to position fixed, style it up, and you are good to go if all you want is some added flair for your site.

But a custom cursor can and should be so much more!

Achieving a custom cursor that not only looks cool but adds to the user interactions in a seamless and intuitive way is much more difficult to implement and time-consuming to write from scratch across multiple projects.

I wrote custom-cursor.js to help developers easily implement custom-cursors with interaction across the web.

custom-cursor.js

Let’s get started by installing the package.

npm i custom-cursor.js

Before we write any JS, we need to set up some basic markup and styles for our cursor to function correctly. As the custom cursor will be following behind our true cursor we need to make sure pointer events are disabled and user-select is turned off so we can still interact with the webpage. We also need to fix the element so it can move freely.

custom cursor’s core markup

With the core styles ready to go, JS is up next! Import the package and initialize it with some basic options.

custom cursor’s core markup

In the options object, focus-elements are an array of selectors that will apply the focus-class on hover. We then create a new CustomCursor class and initialize it right away. That sets up all our required event listeners and starts an animation frame loop that updates the cursor when we move our mouse.

Right now we don’t see the custom cursor because it has no visible styles — let’s add them now in a sub-element of the cursor.

Bonus Styles

If you are curious we style the sub-element to make use of the transform property — the wrapper’s transform property is being overridden on mouse move. Without transform: translate(-50%, -50%), the true cursor would sit at the top left of our custom cursor but we want it in the center.

But wait! We still need to add the interaction styles. A simple size increase on hover should do just fine for this example:

cursor basic interaction styles

With this, we have a functional custom cursor that has some basic UI interaction.

But we can still do a whole lot better!

Let’s have a little more fun!

Custom-cursor.js allows us to specify different focus classes and custom interactions for each different focus element. For example, we can apply ‘cursor — link-hovered’ when hoving links, and ‘cursor — button-hovered’ when hoving buttons.

Classes are also added to the cursor in the background which gives us some extra control. We are also exposed to .disable() and .enable() functions, allowing us to kill the cursor over specific elements if it gets in the way

  • “cursor — initialized” (when initialized)
  • “cursor — off-screen” (when the true cursor has left window)
  • “cursor — disabled” (when the cursor has been disabled)

Using everything above, here is an example that disables the cursor when hovering over images so it doesn’t get in the way.

Check this example version out live:

--

--