After tinkering with the underline animation while scrolling down on Codepen using Javascript, I successfully implemented it. You can check out the working version on Codepen. This animation utilizes Intersection Observer and a generated svg for the underlining effect.
Explanation of how it functions:
This visual effect is achieved by positioning an SVG relative to the text that needs emphasis and animating it in and out accordingly.
The targeted words are wrapped within a span
element so that they can be accessed directly for styling purposes.
To enable CSS styling on the path element of the SVG, the SVG code itself is directly embedded within the HTML, specifically inside the span wrapping the text to be underlined.
A class name is assigned to the SVG element (squiggle
) to facilitate CSS targeting.
The inline properties such as squiggle position
, width
, and height
are directly set on the SVG element to ensure precise placement of the underline.
With these configurations in place, the underline appears correctly. The animation is executed by manipulating the stroke of an SVG path through a combination of stroke-dasharray
and stroke-dashoffset
properties.
For the initial setup, values for stroke-dasharray
and stroke-dashoffset
must be large enough to keep the stroke hidden initially.
.squiggle path {
stroke-dasharray: 1600;
stroke-dashoffset: 1600;
}
When the container element comes into view, the animation properties like name, duration, iteration-count, and fill-mode can be specified:
.text-effect.in-view .squiggle path {
animation-name: underline;
animation-duration: 1s;
animation-iteration-count: 1;
animation-fill-mode: forwards;
}
An additional @keyframes underline-out
rule controls the reverse animation when the element exits the viewport.
Attempting to replicate it in React Typescript:
I first tried replicating the animation in React Typescript as a styled component and then planned to integrate the Intersection Observer from the original Codepen demo. However, I faced challenges with the animation execution despite setting inline styles as required.
Here's a snippet of my App.tsx
:
// Code snippet here