You are currently viewing Text Switcher Sequence –  Elementor and GSAP Tutorial

Text Switcher Sequence – Elementor and GSAP Tutorial

(This page includes affiliate links. If you click and purchase, I receive a small commission at no extra cost from you and that way you can support me. I only recommend tools that I have personally used and loved.)

Don’t want to make from scratch? Get the template instead 🙂

Introduction – Text Switcher Sequence using Elementor, Javascript, CSS and GSAP

In this tutorial, we will learn to create a text sequence that loops and changes text with different animations. Please watch the video for in-depth explanation or read for below for base explanation.

Before Line

You can Replace

Replace Any Text

Automatically Adjusts Width

Disable Width Adjustment?

Highly Customizable

You can Replace

After Lines

1 – Move Up (Translate Y) for text reveals

  1. dm-switcher-1 is the CSS class of the container that contains all the text.
  2. dm-switcher-text-1 is the CSS class of all the texts widgets/div. Make sure to add duplicate of the first text at the end.
  3. Make the height and min-height to your required height. Anything outside this is invisible.
  4. Change duration to control the speed of text moving.
  5. Change delay to define how long the text is shown before switching.
  6. Remove Line 80 and Line 105 – 117 if you don’t want the size of the container to switch based on the text size.
				
					<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.13.0/gsap.min.js" integrity="sha512-NcZdtrT77bJr4STcmsGAESr06BYGE8woZdSdEgqnpyqac7sugNO+Tr4bGwGF3MsnEkGKhU2KL2xh6Ec+BqsaHA==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

<style>


    .dm-switcher-1 {
        
        height: 40px;
        overflow: hidden;
        transition: none !important;
        
       
    }
    
    .dm-switcher-text-1 {
        
        min-height: 40px; 
        transition: none !important;
        white-space: nowrap;
        max-width: none !important;
    }
    
   /*Tablet*/
   
   @media(max-width:1024px) {
       
      .dm-switcher-1 {
        
        height: 30px;
       
    }
    
    .dm-switcher-text-1 {
        
        min-height: 30px; 
        
    }
       
   }
   
   
    /*Mobile*/
   
   @media(max-width:767px) {
       
      .dm-switcher-1 {
        
        height: 25px;
       
    }
    
    .dm-switcher-text-1 {
        
        min-height: 25px; 
        
    }
       
   }
    
    
    
</style>

<script>

document.addEventListener("DOMContentLoaded", (event) => {

  const dmSwitcher1 = document.querySelector('.dm-switcher-1');
  const dmSwitcher1Texts = document.querySelectorAll('.dm-switcher-text-1');
  
  //Store Widths of the TExts
   
    const textWidths = [];
    
    dmSwitcher1Texts.forEach(el => {
      textWidths.push(el.offsetWidth);
    });  
  console.log(textWidths);
  
  dmSwitcher1.style.width =`${textWidths[0]}px`;
  
  //Get min-height of the first text element
  
  const textHeight = parseFloat(getComputedStyle(dmSwitcher1Texts[0]).minHeight);
  
  //Duration of switching and delay to show the text for a while
  
  const duration = 1;
  const delay = 2;

  //Timeline Repeat after Ending
  const dmSwitcherTL1 = gsap.timeline({ repeat: -1 });
 
  for (let i = 1; i < dmSwitcher1Texts.length; i++) {
      
    const yVal = i * -textHeight;
    
    dmSwitcherTL1.to(dmSwitcher1Texts, {
        
      y: yVal,
      duration: duration,
      ease: "power1.inOut",
      
      
      onStart: () => {
          
          console.log(textWidths[i]);
          
          gsap.to(dmSwitcher1, {
              
             width: textWidths[i],
             duration:0.5
              
          });
          
          
      }
      
    }, "+=" + delay);
    
  }

  // Reset instantly after last slide (duplicate), no delay
  dmSwitcherTL1.set(dmSwitcher1Texts, { y: 0 });
  
});
  
</script>

				
			

At DMmotionarts, We Provide

Elementor Templates

WordPress Tutorials

Full Code

Youtube Videos

Like and Subscribe

Elementor Templates

2 – Move Left (Translate X) for text reveals

  1. dm-switcher-3 is the CSS class of the container that contain the wrapper container.
  2. dm-switcher-text-3-wrapper is the CSS class of the container that contains all the texts.
  3. dm-switcher-text-3 is the CSS class of all the texts widgets/div. Make sure to add duplicate of the first text at the end.
  4. Make the height and min-height to your required height. Anything outside this is invisible.
  5. Change duration to control the speed of text moving.
  6. Change delay to define how long the text is shown before switching.
				
					<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.13.0/gsap.min.js" integrity="sha512-NcZdtrT77bJr4STcmsGAESr06BYGE8woZdSdEgqnpyqac7sugNO+Tr4bGwGF3MsnEkGKhU2KL2xh6Ec+BqsaHA==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

<style>

  .dm-switcher-text-3-wrapper {
      
      transition: none !important;
      
  }

  .dm-switcher-3 {
   
    overflow: hidden;
    transition: none !important;
  }

  .dm-switcher-text-3{
   
    transition: none !important;
    white-space: nowrap ;
    max-width: none !important;
    
  }

</style>

<script>
  document.addEventListener("DOMContentLoaded", (event) => {
    const dmSwitcher3 = document.querySelector('.dm-switcher-3');
    
    const dmSwitcher3Texts = document.querySelectorAll('.dm-switcher-text-3');
    
    const dmSwitcherWrapper3 = document.querySelector('.dm-switcher-text-3-wrapper');

    // Store Widths of the Texts
    const textWidths = [];

    dmSwitcher3Texts.forEach(el => {
      textWidths.push(el.offsetWidth);
    });
    console.log(textWidths);

    dmSwitcher3.style.width = `${textWidths[0]}px`;

    // Duration of switching and delay to show the text for a while
    const duration = 1;
    const delay = 2;
    
    let totalX = 0;

    // Timeline Repeat after Ending
    const dmSwitcherTL3 = gsap.timeline({ repeat: -1 });

    for (let i = 1; i < dmSwitcher3Texts.length; i++) {
        
     totalX -= textWidths[i - 1];

      dmSwitcherTL3.to(dmSwitcherWrapper3, {
          
        x: totalX,
        duration: duration,
        ease: "power1.inOut",

        onStart: () => {
          console.log(textWidths[i]);

          gsap.to(dmSwitcher3, {
            width: textWidths[i],
            duration: 0.5
          });
        }

      }, "+=" + delay);
    }

    // Reset instantly after last slide (duplicate), no delay
    dmSwitcherTL3.set(dmSwitcherWrapper3, { y: 0 });
  });
</script>

				
			

At DMmotionarts, We Provide

Elementor Templates

Youtube Tutorials

Quality Content

3 – Fade Effect with Left, Right, Up and Down Direction Option

  1. dm-switcher-text-4 is the CSS class of the container that contains all the texts.
  2. dm-switcher-text-3 is the CSS class of all the texts widgets/div. Make sure to add duplicate of the first text at the end.
  3. Line 31-50 decides the direction for text moving for desktop and mobile(767px).
  4. You can change 767 to different breakpoint to include tablet too. For Elementor tablet breakpoint is 1024px.
  5. Line 33 – 34 decides for mobile. TranslateX moves towards left or right. Change 500 to your desired moving distance. 300 moves it left and -300 moves it right (It is opposite because in the code later, I used minus but too lazy to change it)
  6. If you want to move it up or down, simply change the TranslateY to your desired value and make TranslateX to be 0.
  7. dmEnterDuration controls the time it takes for text to reach center after entering. 
  8. dmExitDuration controls the time it takes for text to go from center to exit.
  9. dmSwitchSpeed controls when the next text to show. It is in ms i.e 5s is 5000.
				
					<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.13.0/gsap.min.js" integrity="sha512-NcZdtrT77bJr4STcmsGAESr06BYGE8woZdSdEgqnpyqac7sugNO+Tr4bGwGF3MsnEkGKhU2KL2xh6Ec+BqsaHA==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

<style>
    
    .dm-switcher-text-4 {
       
        transition: none !important;
        opacity: 0;
        max-width: none !important;
        
    }
  
    .dm-switcher-4 {
        
        transition: none !important;
        
    }
    
</style>
  

<script>

 document.addEventListener("DOMContentLoaded", (event) => {
     
  const dmSwitcherTexts4 = document.querySelectorAll('.dm-switcher-text-4');
  const dmSwitcher4 = document.querySelector('.dm-switcher-4');

  let dmSwitcherTranslateX, dmSwitcherTranslateY, dmEnterDuration, dmExitDuration, dmSwitchSpeed;

  /*Mobile*/
  if (window.innerWidth <= 767) {
    dmSwitcherTranslateX = 500;
    dmSwitcherTranslateY = 0;
    
    dmEnterDuration = 3; //Entry to center
    dmExitDuration = 3; //center to exit
    dmSwitchSpeed = 2000; //in ms
    
  } 
  
  /*Desktop/Tablet*/
  else
  
  {
    dmSwitcherTranslateX = 0;
    dmSwitcherTranslateY = -100;
    
    dmEnterDuration = 2; //Entry to center
    dmExitDuration = 2; //center to exit
    dmSwitchSpeed = 1500; //in ms
  }

  dmSwitcher4Anim(0);

  function dmSwitcher4Anim(index) {
    const nextIndex = (index + 1) % dmSwitcherTexts4.length;
    const current = dmSwitcherTexts4[index];

    // Reset current element to initial position
    gsap.set(current, {
      transform: `translate(${dmSwitcherTranslateX}px, ${dmSwitcherTranslateY}px)`,
      opacity: 0
    });

    const tl = gsap.timeline({
      onComplete: () => {
        dmSwitcher4.appendChild(current);
        gsap.set(current, {
          transform: `translate(${dmSwitcherTranslateX}px, ${dmSwitcherTranslateY}px)`,
          opacity: 0
        });
      }
    });

    // Animate from: start position -> center
    tl.to(current, {
      transform: `translate(0px, 0px)`,
      opacity: 1,
      duration: dmEnterDuration,
      ease: 'none'
    });

    // Animate from: center -> out (opposite direction)
    tl.to(current, {
      transform: `translate(${-dmSwitcherTranslateX}px, ${-dmSwitcherTranslateY}px)`,
      opacity: 0,
      duration: dmExitDuration,
      ease: 'none'
    });

    // Call next animation after first half (so they overlap smoothly)
    setTimeout(() => {
      dmSwitcher4Anim(nextIndex);
    }, dmSwitchSpeed);
  }
  
 }); 
</script>


				
			

At DMmotionarts, We Provide

Elementor Templates

Youtube Tutorials

Quality Content

4 – Color Reveal Switcher (Left, Right, Up or Down Direction)

  1. dm-switcher-text-5 is the CSS class of all the texts.
  2. dm-switcher-text-5-overlay is the CSS class of the widget used for our color.
  3. animation is set to 2s at line 15 in CSS. You can increase it or lower for different speed.
  4. @keyframes use clip-path inset to create the reveal effect. Change the inset values at 0% time and 100% time to change the direction of reveal. You can make it go right to left, up to down or vice versa. 
  5. At Line 64, we decide when to switch the text. For this example, it is set to 1000 i.e 1s. As our animation is 2s long, we want to change the text right at middle of the animation. If you decide to change the animation timing, then use half of its value here.
  6. At Line 67, we decide when to play the logic again. In our example: animation takes 2s, so we have decided to use 3000 i.e 3s to do the logic again. This means our Text is shown for 1s before doing animation again.
				
					<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.13.0/gsap.min.js" integrity="sha512-NcZdtrT77bJr4STcmsGAESr06BYGE8woZdSdEgqnpyqac7sugNO+Tr4bGwGF3MsnEkGKhU2KL2xh6Ec+BqsaHA==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

<style>
    
    .dm-switcher-text-5 {
        
        display: none;
        max-width: none !important;
        
    }
    
 
     /* Animation class that gets toggled */
  .dm-switcher-animate {
    animation: dm-overlay-reveal-5 2s linear forwards;
  }
   
    @keyframes dm-overlay-reveal-5 {
	
	0% {
	    
	    clip-path: inset(0% 100% 0% 0%);
	    
	}
	
	50% {
	    
	    clip-path: inset(0% 0% 0% 0%);
	    
	}
	
	100% {
	    
	    
	    clip-path: inset(0% 0% 0% 100%);
	    
	}
}

    
    
</style>
  
<script>
document.addEventListener("DOMContentLoaded", () => {
  const texts = document.querySelectorAll('.dm-switcher-text-5');
  const overlay = document.querySelector('.dm-switcher-text-5-overlay');
  let currentIndex = 0;

  // Show first text
  texts[currentIndex].style.display = 'block';

  function playAnimation() {
    // Reset animation class
    overlay.classList.remove('dm-switcher-animate');
    void overlay.offsetWidth; // force reflow
    overlay.classList.add('dm-switcher-animate');

    // Switch text at 50% (1 second)
    setTimeout(() => {
      texts[currentIndex].style.display = 'none';
      currentIndex = (currentIndex + 1) % texts.length;
      texts[currentIndex].style.display = 'block';
    }, 1000);

    // After 2s (animation) + 1s (pause), restart loop
    setTimeout(playAnimation, 3000);
  }

  playAnimation();
});
</script>

				
			

At DMmotionarts, We Provide

Elementor Templates

5 – Scramble Text to Switch (For more effects and in-depth details, watch my Scramble Text Video or Blog)

  1. dm-switcher-text-switcher is the CSS class given to the heading widget.
  2. duration controls how long it should take to reveal characters.
  3. text controls what text should it switch to.
  4. chars controls what should be shown when doing scrambling. Use your custom string, or type “lowerCase”, “upperCase” or “upperAndLowerCase” to use all alphabets in the respective format.
  5. revealDelay controls how long the scrambling should show before starting to reveal. Make sure to keep it less than duration.
  6. speed defines how quickly the scrambling should happen.
  7. delimiter allows you to de-scramble word by word instead of char by char. Simply add space between the quotation marks. Example : ‘ ‘
  8. Simply copy line 44 – 54 to add more lines.
  9. It is important to add the same text at the end as your original text for seamless loop.
				
					<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.13.0/gsap.min.js" integrity="sha512-NcZdtrT77bJr4STcmsGAESr06BYGE8woZdSdEgqnpyqac7sugNO+Tr4bGwGF3MsnEkGKhU2KL2xh6Ec+BqsaHA==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.13.0/ScrambleTextPlugin.min.js" integrity="sha512-EVIYaMR2tIn6veV5jmP0M0DFBSBt5rAhRPsW0zwC9LyPzAIHNeWiZ4B5orgYeWbNq55vIwk8fOKCtTHwiCBvaw==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

<style>
  .dm-scramble-text-switcher {
    transition: none !important;
  }
</style>

<script>
document.addEventListener("DOMContentLoaded", () => {
  gsap.registerPlugin(ScrambleTextPlugin);

  const dmScrambleTLSwitcher = gsap.timeline({
    onComplete: () => {
      dmScrambleTLSwitcher.restart();
    }
  });

  dmScrambleTLSwitcher.to('.dm-scramble-text-switcher .elementor-heading-title', {
    duration: 2,
    delay: 2,
    scrambleText: {
      text: "Quality Products",
      chars: "!@#$%^&*()-_=+<>?/[]{}",
      revealDelay: 1,
      speed: 0.8,
      delimiter: ''
    }
  });

  dmScrambleTLSwitcher.to('.dm-scramble-text-switcher .elementor-heading-title', {
    duration: 2,
    delay: 2,
    scrambleText: {
      text: "Consider Subscribing",
      chars: "!@#$%^&*()-_=+<>?/[]{}",
      revealDelay: 1,
      speed: 0.8,
      delimiter: ''
    }
  });

  dmScrambleTLSwitcher.to('.dm-scramble-text-switcher .elementor-heading-title', {
    duration: 2,
    delay: 2,
    scrambleText: {
      text: "Elementor Templates",
      chars: "!@#$%^&*()-_=+<>?/[]{}",
      revealDelay: 0,
      speed: 0.8,
      delimiter: ''
    }
  });
});
</script>
				
			

At DMmotionarts, We Provide

Elementor Templates

Youtube Tutorials

Quality Content

6 – Switch based on CSS properties

  1. dm-switcher-text-7 is the CSS class of all the texts.
  2. .dmActive is the CSS class for the text that is shown
  3. Any CSS property you add in dm-switcher-text-7 is added to inactive/hidden texts.
  4. Any CSS property you add in dm-switcher-text-7.dmActive is added to active/shown text only.
  5. This allows you to create any effect like fade, translate, scale easily.
  6. transition controls the time it takes to change its state. Both dm-switcher-text-7 and dmActive has transition and transition-delay, this allows to for both entry and exit transitions.
  7. transition-delay controls how long it should wait before changing.
  8. Line 51, 3000 i.e 3s defines when to change the text.
  9. If the transition is not working, then add !important after 1s. This would force CSS to use it.
				
					<style>
    
    /*Default/Exit State*/
    .dm-switcher-text-7 {
       
        transition: 1s; //if doesn't work, then add !important after 1s
        transition-delay:0s;
        opacity: 0;
        pointer-events: none;
        filter:blur(20px);
        
    }
    
    
    /*Entry State*/
    .dm-switcher-text-7.dmActive {
        
        transition: 1s;
        transition-delay:0s;
        filter:blur(0px);
        opacity: 1;
        pointer-events: auto;
    }

    
    
</style>
  
<script>
document.addEventListener("DOMContentLoaded", () => {
  const texts = document.querySelectorAll('.dm-switcher-text-7');
  let currentIndex = 0;

  function showNextText() {
    // Remove active class and hide all
    texts.forEach(text => {
      text.classList.remove('dmActive');
      
    });
    
    texts[currentIndex].classList.add('dmActive');

    // Advance index
    currentIndex = (currentIndex + 1) % texts.length;
  }

  // Initial show
  showNextText();

  // Loop every 3 seconds
  setInterval(showNextText, 3000);
});
</script>

				
			

Leave a Reply