main.main
    header
        h1
            strong Mutant
            | Cursor
        p SVG + JS + MicroInteractions
    svg#svg-cursor.svg-cursor(width='1em' height='1em')
        g.svg-cursor__lines(stroke-width='2px' stroke='black')
            line(x1='0' y1='.5em' x2='1em' y2='.5em')
            line(x1='0' y1='.5em' x2='1em' y2='.5em')
            line(x1='0' y1='.5em' x2='1em' y2='.5em')
    ul.actions
        li.actions__item
            a.custom-cursor.custom-cursor--action(href='javascript:void(0)' title='Fire action cursor') Action cursor
        li.actions__item
            a.custom-cursor.custom-cursor--close(href='javascript:void(0)' title='Fire close cursor') Close cursor
        li.actions__item
            a.custom-cursor.custom-cursor--action(href='#modal' title='Help') Help
    article#modal.modal
        .modal__content
            header.modal__header
                h2 How the hell it works?
            p.space It's simple, jus drop this JavaScript in your HTML:
            ul.code.space
                li.code__line document.body.addEventListener("mousemove", function(event) {
                li.code__line.code__push1 moveCursor(event);
                li.code__line.space });
                li.code__line.space var svgCursor = document.getElementById('svg-cursor');
                li.code__line function moveCursor(e) {
                li.code__line.code__push1 var x = e.clientX - 5,
                li.code__line.code__push3.space y = e.clientY - 5;
                li.code__line.code__push1.space svgCursor.setAttribute('style', 'left: ' + x + 'px; top: ' + y + 'px');
                li.code__line.code__push1 if (e.target.className.indexOf('custom-cursor') > -1) {
                li.code__line.code__push3 switch (e.target.className) {
                li.code__line.code__push5 case 'custom-cursor custom-cursor--action':
                li.code__line.code__push8 svgCursor.setAttribute('class', 'svg-cursor svg-cursor__action')
                li.code__line.code__push8 break;
                li.code__line.code__push5 case 'custom-cursor custom-cursor--close':
                li.code__line.code__push8 svgCursor.setAttribute('class', 'svg-cursor svg-cursor__close')
                li.code__line.code__push8 break;
                li.code__line.code__push3 }
                li.code__line.code__push1 } else {
                li.code__line.code__push3 svgCursor.setAttribute('class', 'svg-cursor');
                li.code__line.code__push1 }
                li.code__line }
            p.space Now add these classes to some DOM elements and check it out!
            ul.code.space
                li.code__line custom-cursor custom-cursor--hover
                li.code__line.code__comment // or
                li.code__line custom-cursor custom-cursor--close
            p Remember... 
                strong IE Sucks!
            .modal__close
                a.custom-cursor.custom-cursor--close(href='#' title='Close modal')
                    svg(width='2em' height='2em')
                        circle(cx='1em' cy='1em' r='.8em' fill='#ff6a6a')
        .modal__background
View Compiled
@charset 'utf-8';
@import 'compass/reset';
@import 'https://fonts.googleapis.com/css?family=Open+Sans:300,700';
@import 'https://fonts.googleapis.com/css?family=Bitter:400,700';
@import 'https://fonts.googleapis.com/css?family=Anonymous+Pro:400';
$yellow: #f1c40f;
$lime: #76c900;
$navy: #0a4069;
$cyan: #57caf4;
$red: #ec008c;
$white: #fefefe;
$gray: #444;
$lightGray: lighten($gray, 30);

$fastDuration: .3s;
$normalDuration: .6s;
$slowDuration: 1s;
$bezier: cubic-bezier(0.76, -0.53, 0.32, 1.4);
html,
body,
main {
    height: 100%;
    width: 100%;
    box-sizing: border-box;
}

h1
{
    font-size: 2.5em;
    margin: 2em 0 .5em;
    font-family: 'Bitter', serif;
    font-weight: 400;
}

em,
strong
{
    font-weight: 700;
}

.main {
    display: flex;
    align-items: center;
    justify-content: flex-start;
    flex-direction: column;
}

body {
    font-family: 'Open Sans', sans-serif;
    font-weight: 400;
    font-size: 1em;
    line-height: 2em;
    color: $gray;
    background-color: #d0d0d0;
    text-align: center;
}

*,
*:hover {
    cursor: none;
}

a {
    &:hover {
        color: red;
    }
    svg {
        pointer-events: none;
    }
}

.space
{
    margin-bottom: 1em;
}

.actions {
    margin-top: 2em;
    display: flex;
    &__item
    {
        text-align: center;
        a {
            display: inline-block;
            width: 9em;
            padding: 1em 0;
            color: $gray;
            text-decoration: none;
        }
        &:last-child
        {
            margin: 0 1em;
            background-color: #fafafa;
        }
    }
}

.svg-cursor {
    position: absolute;
    pointer-events: none;
    z-index: 1000;
    font-size: 1.5em;
    &__lines {
        transform: scale(.8) rotate(0);
        transform-origin: .5em .5em;
        transition: all $normalDuration $bezier;
        line {
            transition: all $normalDuration $bezier;
            transform-origin: .5em .5em;
            &:nth-of-type(1) {
                transform: rotate(45deg);
            }
            &:nth-of-type(2) {
                transform: scaleX(.65) translateY(-.35em);
            }
            &:nth-of-type(3) {
                transform: scaleY(.65) rotate(90deg) translateY(.35em);
            }
        }
    }
    &__action {
        animation: bounce $slowDuration linear infinite;
    }
    &__close {
        .svg-cursor__lines {
            transform: scale(.8) rotate(360deg);
            line {
                transform-origin: .5em .5em;
                &:nth-child(1) {
                    transform: rotate(45deg);
                }
                &:nth-child(2) {
                    transform: scaleX(0) translateY(0);
                }
                &:nth-child(3) {
                    transform: scaleY(1) rotate(-45deg) translateY(0);
                }
            }
        }
    }
}

@keyframes bounce {
    30% {
        transform: translate(.5em, .5em);
    }
    40% {
        transform: translate(0, 0);
    }
    50% {
        transform: translate(.25em, .25em);
    }
    60%,
    100% {
        transform: translate(0, 0);
    }
}


.modal {
    display: flex;
    align-items: center;
    justify-content: center;
    position: fixed;
    width: 100vw;
    height: 100vh;
    z-index: 10;
    transform: scale(0);
    transition: transform $fastDuration ease-in-out;
    &__header {
        font-weight: 700;
        font-size: 2em;
        margin-bottom: .5em;
        font-family: 'Bitter', serif;
    }
    &__content {
        position: relative;
        z-index: 2;
        box-sizing: border-box;
        padding: 2em 2.4em 2.4em;
        background-color: #fafafa;
        max-height: 80vh;
        display: flex;
        flex-direction: column;
        align-items: flex-start;
    }
    &__background {
        width: 100vw;
        height: 100vh;
        z-index: 1;
        position: absolute;
        left: 0;
        top: 0;
        background-color: rgba(black, .15);
        opacity: 0;
        transition: opacity $normalDuration linear;
        transition-delay: 0s;
    }
    &__close {
        position: absolute;
        top: 0;
        right: 0;
        transform: translate(50%, -50%);
        height: 2em;
        a
        {
            display: inline-block;
        }
    }
    &:target {
        .modal__background {
            opacity: 1;
            transition-delay: $normalDuration;
        }
        transform: scale(1);
    }
}

.code {
    width: 100%;
    max-height: 15em;
    padding: .8em 1em 1em;
    box-sizing: border-box;
    font-family: 'Anonymous Pro';
    background-color: #f0f0f0;
    overflow: auto;
    box-shadow: inset 0 -1em 2em -1em rgba(black, .2);
    &__line {
        font-size: .8em;
        line-height: 1.75em;
        text-align: left;
    }
    @for $i from 1 to 9 {
        &__push#{$i}
        {
            padding-left: 1em * $i;
        }
    }
    &__comment {
        color: gray;
    }
}
View Compiled
document.body.addEventListener("mousemove", function(event) {
    moveCursor(event);
});
var svgCursor = document.getElementById('svg-cursor');
function moveCursor(e) {
    var x = e.clientX - 5,
        y = e.clientY - 5;
    svgCursor.setAttribute('style', 'left: ' + x + 'px; top: ' + y + 'px');
    if (e.target.className.indexOf('custom-cursor') > -1) {
        switch (e.target.className) {
            case 'custom-cursor custom-cursor--action':
                svgCursor.setAttribute('class', 'svg-cursor svg-cursor__action')
                break;
            case 'custom-cursor custom-cursor--close':
                svgCursor.setAttribute('class', 'svg-cursor svg-cursor__close')
                break;
        }
    } else {
        svgCursor.setAttribute('class', 'svg-cursor');
    }
}

External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

This Pen doesn't use any external JavaScript resources.