# Realizing the wave effect of CSS

Time：2020-2-18

All along, it is very difficult to use pure CSS to achieve wave effect. Because the realization of the wave curve requires the aid of Bezier curve.

However, there is no good way to realize Bezier curve by using pure CSS.

Of course, with the help of other forces (SVG, canvas), the so-called wave effect can be easily achieved.

Let’s take a look at the wave effect of non CSS implementation

Svg for wave effect

With the help of SVG, it is easy to draw cubic Bezier curve. ``````
<svg width="200px" height="200px" version="1.1" xmlns="http://www.w3.org/2000/svg">
<text class="liquidFillGaugeText" text-anchor="middle" font-size="42px" transform="translate(100,120)" style="fill: #000">50.0%</text>
<!-- Wave -->
<g id="wave">
<path id="wave-2" fill="rgba(154, 205, 50, .8)" d="M 0 100 C 133.633 85.12 51.54 116.327 200 100 A 95 95 0 0 1 0 100 Z">
<animate dur="5s" repeatCount="indefinite" attributeName="d" attributeType="XML" values="M0 100 C90 28, 92 179, 200 100 A95 95 0 0 1 0 100 Z;
M0 100 C145 100, 41 100, 200 100 A95 95 0 0 1 0 100 Z;
M0 100 C90 28, 92 179, 200 100 A95 95 0 0 1 0 100 Z"></animate>
</path>
</g>
<circle cx="100" cy="100" r="80" stroke-width="10" stroke="white" fill="transparent"></circle>
<circle cx="100" cy="100" r="90" stroke-width="20" stroke="yellowgreen" fill="none" class="percentage-pie-svg"></circle>
</svg>``````

The core of drawing a cubic Bezier curve is the section < path id = “wave-2” fill = “RGBA (154, 205, 50, 8)” d = “M0100 C 133.633 85.12 51.54 116.327200 100 a 95 500 100 Z” >. Interested people can study on their own

Canvas for wave effect

The principle of using canvas to achieve wave effect is the same as SVG, which uses path to draw cubic Bezier curve and give animation effect. ``````\$(function() {
let canvas = \$("canvas");
let ctx = canvas.getContext('2d');
let radians = (Math.PI / 180) * 180;
let startTime = Date.now();
let time = 2000;
let clockwise = 1;
let cp1x, cp1y, cp2x, cp2y;

//Initial state
// ctx.bezierCurveTo(90, 28, 92, 179, 200, 100);
//End state
// ctx.bezierCurveTo(145, 100, 41, 100, 200, 100);

requestAnimationFrame(function waveDraw() {
let t = Math.min(1.0, (Date.now() - startTime) / time);

if(clockwise) {
cp1x = 90 + (55 * t);
cp1y = 28 + (72 * t);
cp2x = 92 - (51 * t);
cp2y = 179 - (79 * t);
} else {
cp1x = 145 - (55 * t);
cp1y = 100 - (72 * t);
cp2x = 41 + (51 * t);
cp2y = 100 + (79 * t);
}

ctx.clearRect(0, 0, 200, 200);
ctx.beginPath();
ctx.moveTo(0, 100);
//Drawing cubic Bezier curve
ctx.bezierCurveTo(cp1x, cp1y, cp2x, cp2y, 200, 100);
//Draw an arc
ctx.arc(100, 100, 100, 0, radians, 0);
ctx.fillStyle = "rgba(154, 205, 50, .8)";
ctx.fill();
ctx.save();

if( t == 1 ) {
startTime = Date.now();
clockwise = !clockwise;
}

requestAnimationFrame(waveDraw);
});
})``````

It mainly uses the dynamic drawing of CTX. Beziercurveto() cubic Bezier curve to realize the motion effect of waves, which can be researched by yourself.

CSS for wave effect

Didn’t you say that CSS couldn’t be implemented at first? Yes, we can’t draw the cubic Bezier curve directly, but we can use some handy methods to simulate the effect of wave motion. Let’s see this method.

principle

The principle is very simple, we all know that a square, add border radius to it: 50%, will get a circle. ``````
width: 240px;
height: 240px;
background: #f13f84;

OK, if border radius is less than 50%, but close to 50%, we will get a figure like this (pay attention to the corners, the whole figure feels a little round, but not very round). ) ``````
width: 240px;
height: 240px;
background: #f13f84;

OK, what’s the use of the whole figure? Can we make waves?

Let’s scroll the graph above to see the effect: CSS for wave effect

``````
@keyframes rotate{
from{transform: rotate(0deg)}
to{transform: rotate(359deg)}
}
.ripple{
width: 240px;
height: 240px;
background: #f13f84;
animation: rotate 3s linear infinite;
}``````

Maybe many people see that they don’t understand the intention of rotating. If they stare at one side carefully, it will have a wave like effect.

And our goal is to use this dynamic transformation of the ups and downs animation, simulation to create a wave like effect.

Realization

Of course, this is a panoramic implementation map, so it’s not obvious. OK, let’s use examples to see what kind of effect can be achieved.

We can use the above principle to achieve a wave motion background rendering: The wave effect floating in the back actually uses the border radius above: 40% of the ellipse, just magnified many times, the figures outside the field of view are hidden, leaving only one side of the field of view, and added some corresponding transform transforms.

Some students may have some questions. OK, let’s hide the above effects and display them, and supplement the animation outside the field of vision. In fact, the principle of generating waves is as follows: The red box in the picture is our actual field of view.

It is worth noting that we do not use the rotating ellipse itself to generate waves here, but use it to cut the background to produce wave effect.