Loading...

Animated cursor

Checkout the cursor pointer. This is a Cursor link, Which change the cursor size
                
<!--cursor-->
<div class="cursor">
  <div class="cursor__inner"></div>
</div>

                
  <!-- Bootstrap + Vendor + Theme -->
  <link href="assets/css/theme.min.css" rel="stylesheet">

                
  <!-- Bootstrap + Vendor + Theme -->
  <script src="assets/css/theme.bundle.js"></script>
  <!-- Cursor Js -->
  <script src="assets/vendor/node_modules/js/gsap.min.js"></script>
  <script>
    //cursor
    var element = document.querySelector('.cursor');
    let mouse = { x: 0, y: 0 };
    window.addEventListener('mousemove', ev => mouse = getMousePos(ev));
    const lerp = (a, b, n) => (1 - n) * a + n * b;
    const getMousePos = e => {
        return {
            x: e.clientX,
            y: e.clientY
        };
    };
    class Cursor {
        constructor(el) {
            this.DOM = { el: el };
            this.DOM.el.style.opacity = 0;
            this.bounds = this.DOM.el.getBoundingClientRect();
            this.renderedStyles = {
                tx: { previous: 0, current: 0, amt: 0.2 },
                ty: { previous: 0, current: 0, amt: 0.2 },
                scale: { previous: 1, current: 1, amt: 0.2 },
                opacity: { previous: 1, current: 1, amt: 0.2 }
            };
            this.onMouseMoveEv = () => {
                this.renderedStyles.tx.previous = this.renderedStyles.tx.current = mouse.x - this.bounds.width / 2;
                this.renderedStyles.ty.previous = this.renderedStyles.ty.previous = mouse.y - this.bounds.height / 2;
                gsap.to(this.DOM.el, { duration: 0.9, ease: 'Power3.easeOut', opacity: 1 });
                requestAnimationFrame(() => this.render());
                window.removeEventListener('mousemove', this.onMouseMoveEv);
            };
            window.addEventListener('mousemove', this.onMouseMoveEv);
        }
        enter() {
            element.classList.add('cHover');
        }
        leave() {
            this.renderedStyles['scale'].current = 1;
            this.renderedStyles['opacity'].current = 1;
            element.classList.remove('cHover');
        }
        render() {
            this.renderedStyles['tx'].current = mouse.x - this.bounds.width / 2;
            this.renderedStyles['ty'].current = mouse.y - this.bounds.height / 2;

            for (const key in this.renderedStyles) {
                this.renderedStyles[key].previous = lerp(this.renderedStyles[key].previous, this.renderedStyles[key].current, this.renderedStyles[key].amt);
            }
            this.DOM.el.style.transform = `translateX(${(this.renderedStyles['tx'].previous)}px) translateY(${this.renderedStyles['ty'].previous}px) scale(${this.renderedStyles['scale'].previous})`;
            this.DOM.el.style.opacity = this.renderedStyles['opacity'].previous;
            requestAnimationFrame(() => this.render());
        }
    }
    const cursor = new Cursor(document.querySelector('.cursor'));
    [...document.querySelectorAll('a,.btn')].forEach(link => {
        link.addEventListener('mouseenter', () => cursor.enter());
        link.addEventListener('mouseleave', () => cursor.leave());
    });
</script>

Let's start building stunning websites

Lorem ipsum is placeholder text commonly used in the graphic, print, and publishing industries for previewing layouts and visual mockups.