Pen Settings

HTML

CSS

CSS Base

Vendor Prefixing

Add External Stylesheets/Pens

Any URLs added here will be added as <link>s in order, and before the CSS in the editor. You can use the CSS from another Pen by using its URL and the proper URL extension.

+ add another resource

JavaScript

Babel includes JSX processing.

Add External Scripts/Pens

Any URL's added here will be added as <script>s in order, and run before the JavaScript in the editor. You can use the URL of any other Pen and it will include the JavaScript from that Pen.

+ add another resource

Packages

Add Packages

Search for and use JavaScript packages from npm here. By selecting a package, an import statement will be added to the top of the JavaScript editor for this package.

Behavior

Auto Save

If active, Pens will autosave every 30 seconds after being saved once.

Auto-Updating Preview

If enabled, the preview panel updates automatically as you code. If disabled, use the "Run" button to update.

Format on Save

If enabled, your code will be formatted when you actively save your Pen. Note: your code becomes un-folded during formatting.

Editor Settings

Code Indentation

Want to change your Syntax Highlighting theme, Fonts and more?

Visit your global Editor Settings.

HTML

              
                <svg xmlns="http://www.w3.org/2000/svg" version="1.1" width="800">
			  <defs>
			    <filter id="goo">
			      <feGaussianBlur in="SourceGraphic" stdDeviation="6" result="blur" />
			      <feColorMatrix in="blur" mode="matrix" values="1 0 0 0 0  0 1 0 0 0  0 0 1 0 0  0 0 0 35 -15" result="goo" />
			      <feComposite in="SourceGraphic" in2="goo" operator="atop"/>
			    </filter>
			  </defs>
			</svg>

<div class="page">
	
	<div class="page-bg">
		<p>M</p>
		<div class="noise"></div>
	</div>
	
	<div class="lines">
		<div class="line1"></div>
		<div class="line2"></div>
		<div class="line3"></div>
		<div class="line4"></div>
		<div class="line5"></div>
	</div>
	
	<div class="container">
		<div class="child">
			<div class="content">
				<div>
				<div id="button" class="HoverButton">
					<div class="bg"></div>
					<h1>Hover Me</h1>
				</div>
				</div>
			</div>
		</div>
	</div>
	
	<div class="images">
		<img src="https://foo-exp.s3.amazonaws.com/morph_mouse/img_big.png" class="big" id="bigImg">
		<img src="https://foo-exp.s3.amazonaws.com/morph_mouse/img_small.png" class="small" id="smallImg">
	</div>
	
	<div class="stamp">
		<div class="circle">
			<p id="circle-content">EXPERIMENTS . EXPERIMENTS .</p>
		</div>
		<p>2018</p>
	</div>
	
	<div class="design">
		<p>Best viewed on Chrome</p>
		<a href="https://dribbble.com/eaamst" target="blank">Designed by: Eder Anaya</a>
	</div>
	
</div>
<div id="cursor" class="Cursor">
</div>
              
            
!

CSS

              
                *
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;

body
html
    cursor none
    width 100%
    height 100%
    font-family 'Roboto', sans-serif
    background-color #e0dad5
    overflow hidden

svg
    display none

.page
    width 100%
    height 100%
    background-color #e0dad5
    display block

.page-bg
    width 100%
    height 100%
    display block
    position absolute
    overflow hidden
    top 0
    left 0
    z-index 1
    background-color #e0dad5

    p
        font-family 'Asul', sans-serif
        color #dbd6d1
        opacity 0.8
        font-size 85vmin
        margin 0
        text-align center
        line-height 100vh

.noise
    background-image url('https://foo-exp.s3.amazonaws.com/morph_mouse/noise_pattern.png')
    background-size 200px 200px
    background-repeat repeat
    position absolute
    top 0
    left 0
    width 100%
    height 100%
    mix-blend-mode hard-light

.container
    width 100%
    height 100%
    display table
    z-index 100

.child
    display table-row

.content
    display table-cell
    vertical-align middle
    text-align center

.HoverButton
    position relative
    display inline-block
    z-index 20
    padding 0 2%
    overflow hidden
    //overflow-x hidden
    &:after
        content "01"
        display block
        position absolute
        color #ee3d3d
        top 5%
        right 3%
        mix-blend-mode difference
        font-family 'Asul', sans-serif
        font-size 1.2vmax
        font-weight bold

    .bg
        pointer-events none
        position absolute
        background-color #ee3d3d
        height 100%
        width: 125%
        display block
        //z-index 1
        transform translateX(-112%) skew(-10deg)

h1
    color #ee3d3d
    position relative
    font-weight normal
    font-family 'Asul', sans-serif
    z-index 1
    margin 0
    font-size 11vmax
    mix-blend-mode difference

.images
    position absolute
    left 50%
    top 64vh
    transform translate(-50%, 0);
    z-index 10
    pointer-events none
    .big
        width 36vmax
    .small
        width 27vmax
        position absolute
        left 50%
        top 50%
        transform translate(-50%, -50%)

.Cursor
    pointer-events none
    position fixed
    display block
    border-radius 0
    transform-origin center center
    mix-blend-mode difference
    top 0
    left 0
    z-index 1000
    filter url("#goo")
    span
        position absolute
        display block
        width: 26px
        height 26px
        border-radius 20px
        background-color: white
        transform-origin center center
        transform: translate(-50%, -50%)


.stamp
    position absolute
    right 6vmax
    top 6vmax
    z-index 10
    p
        color #ee3d3d
        font-size 2vmax
        font-family 'Asul', sans-serif
        margin 0
    .circle
        position absolute
        width 1px
        height 1px
        display block
        left 50%
        top 50%
        background-color transparent
        animation rotating 9.5s linear infinite
        span
            font-family: 'Rubik', sans-serif;
            font-weight bold
            font-size 0.8vmax
            color #ee3d3d
            height 5vmax
            position absolute
            display inline-block
            left 0
            bottom 0
            transform-origin: bottom center

for i in (1..28)
    .char{i}
        transform rotate((i*13)deg)

@keyframes rotating {
    from {
        transform: rotate(0deg);
    }
    to {
        transform: rotate(360deg);
    }
}

.line
    position absolute
    background-color #ede8e5

.line-vertical
    @extends .line
    width 2px
    height 100%
    top 0

.line-horizontal
    @extends .line
    width 100%
    height 2px
    left 0


.lines
    position absolute
    width 100%
    height 100%
    left 0
    top 0
    z-index 2
    .line1
        @extends .line-horizontal
        top 36vh

    .line2
        @extends .line-horizontal
        top 64vh

    .line3
        @extends .line-vertical
        left 22vw

    .line4
        @extends .line-vertical
        left 78vw

    .line5
        @extends .line-vertical
        left 50vw



.design
    position absolute
    left 10px
    top 10px
    z-index 5
    color black
    font-family: 'Work Sans', sans-serif;
    font-size 10px
    a
        color black

              
            
!

JS

              
                const cursor = document.getElementById("cursor");
const amount = 20;
const sineDots = Math.floor(amount * 0.3);
const width = 26;
const idleTimeout = 150;
let lastFrame = 0;
let mousePosition = {x: 0, y: 0};
let dots = [];
let timeoutID;
let idle = false;
let hoverButton;
let hoverTL;

class HoverButton {
    constructor(id) {
        this.hovered = false;
        this.animatingHover = false;
        this.forceOut = false;
        this.timing = 0.65;
        this.el = document.getElementById(id);
        this.bg = this.el.getElementsByClassName("bg")[0];
        this.el.addEventListener("mouseenter", this.onMouseEnter);
        this.el.addEventListener("mouseleave", this.onMouseLeave);
    }

    onMouseEnter = () => {
        this.hoverInAnim();
    };

    hoverInAnim = () => {
        if (!this.hovered) {
            this.hovered = true;
            this.animatingHover = true;
            this.forceOut = false;
            TweenMax.fromTo(
                this.bg,
                this.timing,
                {x: "-112%"},
                {
                    x: "-12%",
                    ease: Power3.easeOut,
                    onComplete: () => {
                        this.animatingHover = false;
                        if (this.forceOut) {
                            this.foceOut = false;
                            this.hoverOutAnim();
                        }
                    }
                }
            );
        }
    };

    onMouseLeave = () => {
        if (!this.animatingHover) {
            this.hoverOutAnim();
        } else {
            this.forceOut = true;
        }
    };

    hoverOutAnim = () => {
        this.hovered = false;
        TweenMax.to(this.bg, this.timing, {
            x: "100%",
            ease: Power3.easeOut,
            onComplete: () => {
            }
        });
    };
}

class Dot {
    constructor(index = 0) {
        this.index = index;
        this.anglespeed = 0.05;
        this.x = 0;
        this.y = 0;
        this.scale = 1 - 0.05 * index;
        this.range = width / 2 - width / 2 * this.scale + 2;
        this.limit = width * 0.75 * this.scale;
        this.element = document.createElement("span");
        TweenMax.set(this.element, {scale: this.scale});
        cursor.appendChild(this.element);
    }

    lock() {
        this.lockX = this.x;
        this.lockY = this.y;
        this.angleX = Math.PI * 2 * Math.random();
        this.angleY = Math.PI * 2 * Math.random();
    }

    draw(delta) {
        if (!idle || this.index <= sineDots) {
            TweenMax.set(this.element, {x: this.x, y: this.y});
        } else {
            this.angleX += this.anglespeed;
            this.angleY += this.anglespeed;
            this.y = this.lockY + Math.sin(this.angleY) * this.range;
            this.x = this.lockX + Math.sin(this.angleX) * this.range;
            TweenMax.set(this.element, {x: this.x, y: this.y});
        }
    }
}

class Circle {
    constructor(id) {
        const el = document.getElementById(id);
        const parent = el.parentElement;
        parent.removeChild(el);
        const chars = el.innerText.split("");
        chars.push(" ");
        for (let i = 0; i < chars.length; i++) {
            const span = document.createElement("span");
            span.innerText = chars[i];
            span.className = `char${i + 1}`;
            parent.appendChild(span);
        }
    }
}

function init() {
    window.addEventListener("mousemove", onMouseMove);
    window.addEventListener("touchmove", onTouchMove);
    hoverButton = new HoverButton("button");
    // eslint-disable-next-line no-new
    new Circle("circle-content");
    lastFrame += new Date();
    buildDots();
    render();
}

/*function limit(value, min, max) {
    return Math.min(Math.max(min, value), max);
}*/

function startIdleTimer() {
    timeoutID = setTimeout(goInactive, idleTimeout);
    idle = false;
}

function resetIdleTimer() {
    clearTimeout(timeoutID);
    startIdleTimer();
}

function goInactive() {
    idle = true;
    for (let dot of dots) {
        dot.lock();
    }
}

function buildDots() {
    for (let i = 0; i < amount; i++) {
        let dot = new Dot(i);
        dots.push(dot);
    }
}

const onMouseMove = event => {
    mousePosition.x = event.clientX - width / 2;
    mousePosition.y = event.clientY - width / 2;
    resetIdleTimer();
};

const onTouchMove = () => {
    mousePosition.x = event.touches[0].clientX - width / 2;
    mousePosition.y = event.touches[0].clientY - width / 2;
    resetIdleTimer();
};

const render = timestamp => {
    const delta = timestamp - lastFrame;
    positionCursor(delta);
    lastFrame = timestamp;
    requestAnimationFrame(render);
};

const positionCursor = delta => {
    let x = mousePosition.x;
    let y = mousePosition.y;
    dots.forEach((dot, index, dots) => {
        let nextDot = dots[index + 1] || dots[0];
        dot.x = x;
        dot.y = y;
        dot.draw(delta);
        if (!idle || index <= sineDots) {
            const dx = (nextDot.x - dot.x) * 0.35;
            const dy = (nextDot.y - dot.y) * 0.35;
            x += dx;
            y += dy;
        }
    });
};

init();

              
            
!
999px

Console