Skip to content

Latest commit

 

History

History
383 lines (312 loc) · 8.36 KB

File metadata and controls

383 lines (312 loc) · 8.36 KB

@wix/interact

A powerful, declarative interaction library for creating engaging web animations and effects. Built on top of @wix/motion, it provides a configuration-driven approach to adding triggers, animations, and state transitions to web applications.

Features

  • 🎯 Declarative Configuration - Define complex interactions through simple JSON configuration
  • 🎨 Rich Animation Support - Integration with @wix/motion for high-performance animations
  • 🖱️ Multiple Trigger Types - Support for hover, click, scroll, viewport, and custom triggers
  • 📱 Responsive Conditions - Media query and container-based conditional interactions
  • 🔧 Custom Elements - Web Components API for easy framework integration
  • Performance Optimized - Efficient event handling and animation management
  • 🧩 Framework Agnostic - Works with React, vanilla JS, and other frameworks

Installation

npm install @wix/interact

Quick Start

Using Custom Elements

1. Basic Setup

import { Interact } from '@wix/interact/web';

// Define your interaction configuration
const config = {
  interactions: [
    {
      trigger: 'viewEnter',
      key: '#my-element',
      effects: [
        {
          effectId: 'fade-in',
        },
      ],
    },
  ],
  effects: {
    'fade-in': {
      duration: 1000,
      keyframeEffect: {
        name: 'fade',
        keyframes: { opacity: [0, 1] },
      },
    },
  },
};

// Initialize the interact instance
const interact = Interact.create(config);

2. HTML Setup

<!-- Wrap your target element with interact-element -->
<interact-element data-interact-key="my-element">
  <div>This will fade in when it enters the viewport!</div>
</interact-element>

Using React

1. Basic Setup

import { Interact } from '@wix/interact/react';

// Define your interaction configuration
const config = {
  interactions: [
    {
      trigger: 'viewEnter',
      key: '#my-element',
      effects: [
        {
          effectId: 'fade-in',
        },
      ],
    },
  ],
  effects: {
    'fade-in': {
      duration: 1000,
      keyframeEffect: {
        name: 'fade',
        keyframes: { opacity: [0, 1] },
      },
    },
  },
};

// Initialize the interact instance
const interact = Interact.create(config);

2. HTML Setup

import { Interaction } from '@wix/interact/react';

function MyComponent() {
  return (
    <Interaction tagName="div" interactKey="my-element" className="animated-content">
      Hello, animated world!
    </Interaction>
  );
}

Vanilla usage

1. Basic Setup

import { Interact, add } from '@wix/interact';

// Define your interaction configuration
const config = {
  interactions: [
    {
      trigger: 'viewEnter',
      key: '#my-element',
      effects: [
        {
          effectId: 'fade-in',
        },
      ],
    },
  ],
  effects: {
    'fade-in': {
      duration: 1000,
      keyframeEffect: {
        name: 'fade',
        keyframes: { opacity: [0, 1] },
      },
    },
  },
};

// add element
add(document.querySelector('[data-interact-key="my-element"]'), 'my-element');

// Initialize the interact instance
const interact = Interact.create(config);

2. HTML Setup

<div data-interact-key="my-element" class="animated-content">Hello, animated world!</div>

Core Concepts

Triggers

Define when interactions should occur:

  • viewEnter - When element enters viewport
  • click - On element click
  • hover - On element hover
  • viewProgress - Scroll-driven animations based on progress of element in viewport
  • pointerMove - On pointer/mouse movement over an element or viewport
  • animationEnd - When another animation completes

Effects

Define what should happen:

  • Time-based animations - Duration-based effects with easing
  • Scroll-driven animations - Progress-based effects tied to scroll
  • Pointer-driven animations - Progress-based effects linked to pointer position
  • CSS transitions - Style property transitions
  • Custom effects - Integration with @wix/motion

Configuration Structure

{
  interactions: [    // Define trigger → effect relationships
    {
      trigger: 'viewEnter',
      key: 'source-element',
      effects: [{ effectId: 'my-effect' }]
    }
  ],
  effects: {         // Define reusable effect definitions
    'my-effect': {
      duration: 1000,
      keyframeEffect: {
        name: 'fade',
        keyframes: { opacity: [0, 1] }
      }
    }
  },
  conditions: {      // Define conditional logic
    'mobile-only': {
      type: 'media',
      predicate: '(max-width: 768px)'
    }
  }
}

Basic API Reference

Interact Class

Static Methods

// Create a new instance with configuration
Interact.create(config: InteractConfig): Interact

Standalone Functions

// Add interactions to an element
add(element: IInteractElement, key: string): boolean

// Remove all interactions from an element
remove(key: string): void

Examples

Entrance Animation

{
  interactions: [{
    trigger: 'viewEnter',
    key: 'hero',
    effects: [{ effectId: 'slide-up' }]
  }],
  effects: {
    'slide-up': {
      duration: 800,
      easing: 'ease-out',
      keyframeEffect: {
        name: 'slide-up',
        keyframes: {
          transform: ['translateY(20px)', 'translateY(0)'],
          opacity: [0, 1]
        }
      }
    }
  }
}

Click Interaction

{
  interactions: [{
    trigger: 'click',
    key: 'button',
    effects: [{ effectId: 'bounce' }]
  }],
  effects: {
    'bounce': {
      duration: 600,
      namedEffect: {
        type: 'Bounce'
      }
    }
  }
}

Scroll-driven Animation

{
  interactions: [{
    trigger: 'viewProgress',
    key: 'parallax-card',
    effects: [{ effectId: 'parallax-scroll' }]
  }],
  effects: {
    'parallax-scroll': {
      keyframeEffect: {
        name: 'parallax-1',
        keyframes: [
          { transform: 'translateY(200px)' },
          { transform: 'translateY(-200px)' }
        ]
      },
      rangeStart: { name: 'cover', offset: { value: 0, type: 'percentage' } },
      rangeEnd: { name: 'cover', offset: { value: 100, type: 'percentage' } },
      fill: 'both',
      easing: 'linear'
    }
  }
}

Responsive Interactions

{
  interactions: [{
    trigger: 'hover',
    key: 'card',
    conditions: ['desktop-only'],
    effects: [{ effectId: 'lift' }]
  }],
  conditions: {
    'desktop-only': {
      type: 'media',
      predicate: '(min-width: 1024px)'
    }
  },
  effects: {
    'lift': {
      duration: 200,
      keyframeEffect: {
        name: 'lift',
        keyframes: {
          transform: ['translateY(0)', 'translateY(-8px)'],
          boxShadow: ['0 2px 4px rgb(0 0 0 / 0.1)', '0 8px 16px rgb(0 0 0 / 0.15)']
        }
      }
    }
  }
}

Documentation

AI / LLM Support

This package ships with documentation optimized for AI coding assistants following the llms.txt standard:

  • llms.txt — Structured overview with links to detailed docs
  • llms-full.txt — Comprehensive single-file reference for AI consumption

When using an AI assistant, point it to node_modules/@wix/interact/llms-full.txt for complete usage guidance.

Development

# Install dependencies
yarn install

# Run tests
yarn test

# Run playground
yarn playground

# Build package
yarn build

Browser Support

  • ✅ Modern browsers with Web Components support
  • ⚠️ If using setting styles via JS in transition or transitionProerties - which use adoptedStyleSheets, browser support is: Chrome 73+, Firefox 101+, Safari 16.4+, Edge 79+

Related Packages

  • @wix/motion - Core animation engine
  • fizban - For polyfilling scroll-driven animations
  • kuliso - For polyfilling pointer-driven animations

License

MIT