#182 - Disable Animations Using cookies v0.1

Instantly disable or enable all Webflow animations with a toggle, cookies, and reduced-motion support.

Demo ansehen

<!-- 💙 MEMBERSCRIPT #182 v.01 - DISABLE ANIMATIONS USING COOKIES & PREFERS-REDUCED-MOTION 💙 -->
<script>
// Run immediately to catch animations before they start
(function() {
  console.log('Animation Disable Script loaded!');
  
  // Configuration - Customize these values as needed
  const config = {
    // Cookie settings
    cookieName: 'animationsDisabled',
    cookieExpiryDays: 365, // How long to remember the preference
    
    // Universal animation attribute - use this on ANY animated element
    animationAttribute: 'data-ms-animate',
    
    // Toggle control settings
    showToggle: true, // Set to false to hide the toggle button
    togglePosition: 'bottom-right', // 'top-right', 'bottom-right', 'top-left', 'bottom-left'
    toggleText: {
      disable: 'Disable Animations',
      enable: 'Enable Animations'
    }
  };
  
  // Cookie management functions
  function setCookie(name, value, days) {
    let expires = "";
    if (days) {
      const date = new Date();
      date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000));
      expires = "; expires=" + date.toUTCString();
    }
    document.cookie = name + "=" + (value || "") + expires + "; path=/; SameSite=Lax";
  }
  
  function getCookie(name) {
    const nameEQ = name + "=";
    const ca = document.cookie.split(';');
    for (let i = 0; i < ca.length; i++) {
      let c = ca[i];
      while (c.charAt(0) === ' ') c = c.substring(1, c.length);
      if (c.indexOf(nameEQ) === 0) return c.substring(nameEQ.length, c.length);
    }
    return null;
  }
  
  function deleteCookie(name) {
    document.cookie = name + "=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/;";
  }
  
  // Check if user prefers reduced motion
  function prefersReducedMotion() {
    return window.matchMedia('(prefers-reduced-motion: reduce)').matches;
  }
  
  // Check if animations should be disabled
  function shouldDisableAnimations() {
    const cookieDisabled = getCookie(config.cookieName) === 'true';
    const systemPrefersReduced = prefersReducedMotion();
    
    console.log('Animation check:', {
      cookieDisabled,
      systemPrefersReduced,
      shouldDisable: cookieDisabled || systemPrefersReduced
    });
    
    return cookieDisabled || systemPrefersReduced;
  }
  
  // Disable animations on page
  function disableAnimations() {
    console.log('Disabling animations...');
    
    // Find all elements with the animation attribute
    const animatedElements = document.querySelectorAll(`[${config.animationAttribute}]`);
    console.log(`Found ${animatedElements.length} animated elements`);
    
    animatedElements.forEach(element => {
      // Remove Webflow animation ID to prevent interactions
      const webflowId = element.getAttribute('data-w-id');
      if (webflowId) {
        element.setAttribute('data-w-id-disabled', webflowId);
        element.removeAttribute('data-w-id');
        console.log('Disabled Webflow animation for:', element);
      }
      
      // Mark as animation disabled
      element.setAttribute('data-animation-disabled', 'true');
    });
    
    // Disable Webflow interactions globally
    if (window.Webflow && window.Webflow.require) {
      try {
        const ix2 = window.Webflow.require('ix2');
        if (ix2 && ix2.store) {
          ix2.store.dispatch({ type: 'ix2/STORE_DISABLE' });
          console.log('Disabled Webflow interactions globally');
        }
      } catch (e) {
        console.log('Could not disable Webflow interactions:', e);
      }
    }
    
    // Override Webflow animation styles
    const style = document.createElement('style');
    style.id = 'webflow-animation-disable';
    style.textContent = `
      [data-animation-disabled="true"] {
        animation: none !important;
        transition: none !important;
        transform: none !important;
        opacity: 1 !important;
        visibility: visible !important;
      }
    `;
    
    if (!document.getElementById('webflow-animation-disable')) {
      document.head.appendChild(style);
    }
    
    console.log('Animations disabled successfully');
  }
  
  // Enable animations on page
  function enableAnimations() {
    console.log('Enabling animations...');
    
    // Find all elements with the animation attribute
    const animatedElements = document.querySelectorAll(`[${config.animationAttribute}]`);
    
    animatedElements.forEach(element => {
      if (element.getAttribute('data-animation-disabled') === 'true') {
        // Restore Webflow animation ID
        const disabledId = element.getAttribute('data-w-id-disabled');
        if (disabledId) {
          element.setAttribute('data-w-id', disabledId);
          element.removeAttribute('data-w-id-disabled');
          console.log('Re-enabled Webflow animation for:', element);
        }
        
        // Remove disabled marker
        element.removeAttribute('data-animation-disabled');
      }
    });
    
    // Re-enable Webflow interactions globally
    if (window.Webflow && window.Webflow.require) {
      try {
        const ix2 = window.Webflow.require('ix2');
        if (ix2 && ix2.store) {
          ix2.store.dispatch({ type: 'ix2/STORE_ENABLE' });
          console.log('Re-enabled Webflow interactions globally');
        }
      } catch (e) {
        console.log('Could not re-enable Webflow interactions:', e);
      }
    }
    
    // Remove override styles
    const style = document.getElementById('webflow-animation-disable');
    if (style) {
      style.remove();
    }
    
    console.log('Animations enabled successfully');
  }
  
  // Create toggle button
  function createToggleButton() {
    if (!config.showToggle) return;
    
    // Double check that body exists
    if (!document.body) {
      console.log('Body not ready, retrying toggle creation...');
      setTimeout(createToggleButton, 100);
      return;
    }
    //CUSTOMIZE THE TOGGLE COLORS
    const toggle = document.createElement('button');
    toggle.id = 'animation-toggle';
    toggle.type = 'button';
    toggle.setAttribute('data-ms-code', 'animation-toggle');
    toggle.style.cssText = `
      position: fixed;
      ${config.togglePosition.includes('top') ? 'top: 20px;' : 'bottom: 20px;'}
      ${config.togglePosition.includes('right') ? 'right: 20px;' : 'left: 20px;'}
      z-index: 10000;
      background: #2d62ff; 
      color: white;
      border: none;
      padding: 10px 15px;
      border-radius: 25px;
      cursor: pointer;
      font-size: 12px;
      font-weight: 500;
      box-shadow: 0 2px 10px rgba(0, 0, 0, 0.2);
      transition: all 0.3s ease;
      opacity: 0.8;
    `;
    
    // Add hover effects
    toggle.addEventListener('mouseenter', function() {
      this.style.opacity = '1';
      this.style.transform = 'scale(1.05)';
    });
    
    toggle.addEventListener('mouseleave', function() {
      this.style.opacity = '0.8';
      this.style.transform = 'scale(1)';
    });
    
    // Add click handler
    toggle.addEventListener('click', function() {
      console.log('Toggle clicked!');
      const currentlyDisabled = shouldDisableAnimations();
      console.log('Currently disabled:', currentlyDisabled);
      
      if (currentlyDisabled) {
        // Enable animations
        console.log('Enabling animations...');
        deleteCookie(config.cookieName);
        enableAnimations();
        updateToggleButton(false);
        showMessage('Animations enabled', 'success');
      } else {
        // Disable animations
        console.log('Disabling animations...');
        setCookie(config.cookieName, 'true', config.cookieExpiryDays);
        disableAnimations();
        updateToggleButton(true);
        showMessage('Animations disabled', 'info');
      }
    });
    
    document.body.appendChild(toggle);
    updateToggleButton(shouldDisableAnimations());
    
    console.log('Toggle button created');
  }
  
  // Update toggle button text and state
  function updateToggleButton(disabled) {
    const toggle = document.getElementById('animation-toggle');
    if (!toggle) return;
    
    toggle.textContent = disabled ? config.toggleText.enable : config.toggleText.disable;
    toggle.style.background = disabled ? '#28a745' : '#2d62ff';
  }
  
  // Show message to user, CUSTOMIZE THIS
  function showMessage(message, type = 'info') {
    const messageDiv = document.createElement('div');
    messageDiv.className = 'animation-message';
    messageDiv.textContent = message;
    
    const colors = {
      success: '#28a745',
      error: '#dc3545',
      info: '#2d62ff',
      warning: '#ffc107'
    };
    
    messageDiv.style.cssText = `
      position: fixed;
      top: 20px;
      left: 50%;
      transform: translateX(-50%);
      background: ${colors[type] || colors.info};
      color: white;
      padding: 12px 20px;
      border-radius: 25px;
      box-shadow: 0 2px 10px rgba(0, 0, 0, 0.2);
      z-index: 10001;
      font-size: 14px;
      font-weight: 500;
      opacity: 0;
      transition: opacity 0.3s ease;
    `;
    
    document.body.appendChild(messageDiv);
    
    // Fade in
    setTimeout(() => {
      messageDiv.style.opacity = '1';
    }, 100);
    
    // Fade out and remove
    setTimeout(() => {
      messageDiv.style.opacity = '0';
      setTimeout(() => {
        if (document.body.contains(messageDiv)) {
          document.body.removeChild(messageDiv);
        }
      }, 300);
    }, 2000);
  }
  
  // Listen for system preference changes
  function setupPreferenceListener() {
    const mediaQuery = window.matchMedia('(prefers-reduced-motion: reduce)');
    
    function handlePreferenceChange(e) {
      console.log('System preference changed:', e.matches);
      
      if (e.matches && !getCookie(config.cookieName)) {
        // User now prefers reduced motion and hasn't manually set a preference
        disableAnimations();
        updateToggleButton(true);
      } else if (!e.matches && !getCookie(config.cookieName)) {
        // User no longer prefers reduced motion and hasn't manually set a preference
        enableAnimations();
        updateToggleButton(false);
      }
    }
    
    // Modern browsers
    if (mediaQuery.addEventListener) {
      mediaQuery.addEventListener('change', handlePreferenceChange);
    } else {
      // Fallback for older browsers
      mediaQuery.addListener(handlePreferenceChange);
    }
  }
  
  // Initialize the script
  function initialize() {
    console.log('Initializing animation disable script...');
    
    // Check if animations should be disabled
    if (shouldDisableAnimations()) {
      disableAnimations();
    }
    
    // Setup preference listener
    setupPreferenceListener();
    
    console.log('Animation disable script initialized successfully');
  }
  
  // Initialize animations immediately
  initialize();
  
  // Create toggle button when body is ready
  function createToggleWhenReady() {
    if (document.body) {
      createToggleButton();
    } else {
      setTimeout(createToggleWhenReady, 10);
    }
  }
  
  // Run when DOM is ready
  document.addEventListener('DOMContentLoaded', function() {
    initialize();
    createToggleWhenReady();
  });
  
  // Debug function
  window.debugAnimationDisable = function() {
    console.log('=== Animation Disable Debug Info ===');
    console.log('Cookie value:', getCookie(config.cookieName));
    console.log('Prefers reduced motion:', prefersReducedMotion());
    console.log('Should disable animations:', shouldDisableAnimations());
    console.log('Animation elements found:', document.querySelectorAll(`[${config.animationAttribute}]`).length);
    console.log('Toggle button:', document.getElementById('animation-toggle'));
    console.log('Config:', config);
  };
})();
</script>

Customer Showcase

Have you used a Memberscript in your project? We’d love to highlight your work and share it with the community!

Erstellen des Make.com-Szenarios

1. Laden Sie den JSON-Blaupause unten, um angegeben zu bekommen.

2. Navigieren Sie zu Make.com und erstellen Sie ein neues Szenario...

3. Klicken Sie auf das kleine Kästchen mit den 3 Punkten und dann auf Blaupause importieren...

4. Laden Sie Ihre Datei hoch und voila! Sie sind bereit, Ihre eigenen Konten zu verknüpfen.

Brauchen Sie Hilfe mit diesem MemberScript?

Alle Memberstack-Kunden können im 2.0 Slack um Unterstützung bitten. Bitte beachten Sie, dass dies keine offiziellen Funktionen sind und der Support nicht garantiert werden kann.

Treten Sie dem 2.0 Slack bei
Anmerkungen zur Version
Attribute
Beschreibung
Attribut
Keine Artikel gefunden.
Leitfäden / Tutorials
Keine Artikel gefunden.
Tutorial
Was ist Memberstack?

Autorisierung und Zahlungen für Webflow-Websites

Fügen Sie Ihrer Webflow-Website Logins, Abonnements, Gated Content und vieles mehr hinzu - einfach und vollständig anpassbar.

Mehr erfahren

"Wir verwenden Memberstack schon seit langem, und Es hat uns geholfen, Dinge zu erreichen, die wir mit Webflow nie für möglich gehalten hätten. Es hat uns ermöglicht, Plattformen mit großer Tiefe und Funktionalität zu bauen, und das Team dahinter war immer sehr hilfsbereit und offen für Feedback.

Jamie Debnam
39 Digital

"Ich habe eine Mitgliedschaftsseite mit Memberstack und Jetboost für einen Kunden erstellt. Es fühlt sich wie Magie an, mit diesen Tools zu bauen. Als jemand, der in einer Agentur gearbeitet hat, wo einige dieser Anwendungen von Grund auf neu programmiert wurden, verstehe ich jetzt endlich den Hype. Das ist viel schneller und viel billiger."

Félix Meens
Webflix-Studio

"Eines der besten Produkte, um eine Mitgliederseite zu starten - ich mag die Benutzerfreundlichkeit von Memberstack. Ich war in der Lage, meine Mitgliederseite innerhalb eines Tages einzurichten und zu betreiben.. Einfacher geht's nicht. Außerdem bietet es die Funktionalität, die ich brauche, um die Benutzererfahrung individueller zu gestalten."

Eric McQuesten
Gesundheitstechnologie-Nerds
Off World Depot

"Mein Geschäft wäre ohne Memberstack nicht das, was es ist. Wenn Sie denken, dass $30/Monat teuer sind, versuchen Sie mal, einen Entwickler zu engagieren, der für diesen Preis individuelle Empfehlungen in Ihre Website integriert. Unglaublich flexible Tools für diejenigen, die bereit sind, einige minimale Anstrengungen zu unternehmen und die gut zusammengestellte Dokumentation zu lesen."

Riley Brown
Off World Depot

"Die Slack-Community ist eine der aktivsten, die ich kenne, und andere Kunden sind bereit, Fragen zu beantworten und Lösungen anzubieten. Ich habe ausführliche Bewertungen von alternativen Tools durchgeführt und wir kommen immer wieder auf Memberstack zurück - sparen Sie sich die Zeit und probieren Sie es aus."

Abtei Burtis
Gesundheitstechnologie-Nerds
Slack

Brauchen Sie Hilfe mit diesem MemberScript? Treten Sie unserer Slack-Community bei!

Treten Sie der Memberstack-Community Slack bei und fragen Sie los! Erwarten Sie eine prompte Antwort von einem Team-Mitglied, einem Memberstack-Experten oder einem anderen Community-Mitglied.

Unserem Slack beitreten