PK Creative Spring Festival, I am participating in the “Spring Festival Creative Submission Contest”, please see: Spring Festival Creative Submission Contest”
Results show
Let’s start with the renderings:
Online preview address: firecracker animation
Ps: animation is one-time, refresh each time to see the effect, after all, firecrackers after the discharge of no (goof -_-)
implementation
Reference pictures
The static display page of firecrackers in this paper is achieved by referring to the above picture. Technically, vUE + SCSS is used, and the animation effect is CSS animation, without JS.
Implement a single firecracker
A single firecracker is actually a cylinder, so let’s draw a cylinder first and then perfect the details.
- Let me draw the outer surface of a cylinder
linear-gradient
Property to a gradient background color
.item{
margin: 10px;
position: relative;
width: 40px;
height: 100px;
background: linear-gradient(90deg.#6e0009.#e64743.#6e0009);
}
Copy the code
- Use false elements to paint the bottom and top, for a little layering at the bottom, here
border
Set it to a darker layer and use it againoutline
Set to light color:
.item{
// ...
&::before, &::after{
content: ' ';
position: absolute;
display: inline-block;
width: 38px;
height: 20px;
border-radius: 50%;
}
&::before{
width: 40px;
top: -10px;
background: linear-gradient(90deg.#6e0009.#e64743.#6e0009);
}
&::after{
left: 1px;
bottom: -9px;
background: #9f6f2d;
border: 1px solid #58301b;
outline: 1px solid #9f6f2d; }}Copy the code
- Finally draw a yellow line up and down
The yellow line is actually the effect of two ellipses stacked together, and then placed on the cylinder by positioning, because it is the same as the background color, so it has this effect:
.cicle{
position: absolute;
top: -6px;
width: 100%;
height: 20px;
background: linear-gradient(90deg.#9f6f2d.#dfa351.#9f6f2d);
border-radius: 50%;
&::before{
content: ' ';
position: absolute;
display: inline-block;
top: 3px;
width: 100%;
height: 20px;
border-radius: 50%;
background: linear-gradient(90deg.#6e0009.#e64743.#6e0009);
}
&.cicle1{
top: 82px; }}Copy the code
- Details to adjust
Color I used the color of the picture, but the effect looked a little dull, so I added a filter:
.container{
filter: contrast(120%);
}
Copy the code
In order to adjust the effect of painting a single picture of a little big, combined into a string of firecrackers when the appropriate reduction on the line.
The complete code for a single firecracker code: one.vue
To form a string of firecrackers
- Write containers and lines
This should make sense, all firecrackers are emitted relative to the line, so the line sets the attribute position: relative
<div class="bianpao">
<div class="main">
</div>
</div>
Copy the code
Corresponding CSS:
.bianpao {
position: relative;
width: 400px;
height: 380px;
margin: 0 auto;
transform-origin: top;
padding: 20px;
}
.main {
width: 2px;
height: 52.6%;
background: black;
margin: 40px auto;
position: relative;
box-shadow: 0 0 1px black;
}
Copy the code
- Introducing the Firecracker component
<template>
<div class="bianpao">
<div class="main">
<One v-for="item in 40" :key="item" />
<One class="last-one" />
</div>
</div>
</template>
<script>
import One from './one.vue'
export default {
components: {
One
}
}
</script>
Copy the code
- Discharge of firecrackers
Singular on one side, even on the other, something like this:
- Spin off firecrackers
As can be seen from the picture, the rotation Angle of firecrackers is 0-90 degrees. We also let the firecrackers rotate randomly by an Angle. Positive rotation in the singular, negative rotation in the even:
The traversal and random functions of SCSS are used in steps 3 and 4, and the relevant SCSS codes are as follows:
.container:nth-child(2n) {
left: -28px;
}
.container:nth-child(2n + 1) {
right: -28px;
}
.last-one {
transform: scale(0.4) rotate(10deg);
bottom: -120px;
}
@for $i from 1 through 20 {
$angle: #{random(70) + 20}deg;
@if ($i % 2= =0) {
$angle: -#{random(70) + 20}deg;
}
.container:nth-child(#{$i}) {
top: 14px + $i * 8px;
transform: scale(0.4) rotate($angle); }}@for $i from 20 through 40 {
$angle: #{random(70) + 7}deg;
@if ($i % 2= =0) {
$angle: -#{random(70) + 7}deg;
}
.container:nth-child(#{$i}) {
top: 14px + ($i - 20) * 8px;
transform: scale(0.4) rotate($angle); }}Copy the code
You’ll notice that I split the 40 firecrackers into two groups, because I found it a little bit more interesting randomly.
- The last firecracker
Since the random function generates different values every time the code is changed, and the generated firecrackers rotate at different angles and have different shapes, we may have the following effect:
The following part is too big not too good, so add the last firecrackers to coordinate once, the position looked at the tune on the line
Realize the light spot
Speckles are an effect created when setting off firecrackers. Individual speckles are achieved with a gradient background and box-shadow.
$yellow: #fdf410;
background: radial-gradient(rgba($yellow, 0.6), rgba($yellow, 0.1));
box-shadow: 0 0 20px rgba($yellow, 0.6);
Copy the code
The light spot has the following characteristics: random size, random position. The random() function mentioned above can be used again, and the complete code is as follows:
<div class="spot-wrap">
<div v-for="item in 50" :key="item" class="spot" />
</div>
Copy the code
$yellow: #fdf410;
.spot-wrap {
position: absolute;
bottom: -160px;
left: 50%;
transform: translateX(-50%);
width: 200px;
height: 200px;
.spot {
position: absolute;
background: radial-gradient(rgba($yellow.0.6), rgba($yellow.0.1));
box-shadow: 0 0 20px rgba($yellow.0.6);
border-radius: 50%;
animation: twikle 1.2 s infinite alternate;
}
@for $i from 1 through 50 {
.spot:nth-child(#{$i}) {
width: #{random($limit: 20) + 20}px;
height: #{random($limit: 20) + 16}px;
top: #{random($limit: 150) + 10}px;
left: #{random($limit: 160) + 10}px;
animation-delay: -#{random($limit: 4)}s; }}@keyframes twikle {
0% {
opacity: 1; 100%} {opacity: 0.2; }}}Copy the code
Add flicker animation to each spot to make it look more vivid.
The effect is this
Realize the debris after the explosion
It’s similar to a spot of light, but the difference is that in addition to size and location, each fragment is also different in color and shape. Size randomness and position randomness we’ve already talked about how to implement this, but what are the other differences
- Pieces of different colors
Color we use the RGBA function for random numbers, but limit the range of each value because we only want to use red colors:
background: rgba(random(100) + 155.random(100), random(100), 1);
Copy the code
- Different shapes
Shapes are implemented using the clip-path property, and the Polygon () function allows us to implement various shapes.
We divided each div into 3n, 4n, 10n and others, and each group was set to a different shape, so as to ensure randomness of fragment shape. Relevant SCSS codes are as follows:
@for $i from 1 through 50 {
.suipian:nth-child(#{$i}) {
width: #{random($limit: 6) + 8}px;
height: #{random($limit: 6) + 8}px;
top: #{random($limit: 120) + 6}px;
left: #{random($limit: 120) + 6}px;
/* animation-delay: -#{random($limit: 4)}s; * /
background: rgba(random(100) + 155, random(100), random(100), 1);
@if ($i % 3= =0) {
clip-path: polygon(#{random($limit: 100)} %0%, #{random($limit: 100)} %10%, #{random($limit: 100)} %80%.0% 60%);
} @else if($i % 4= =0) {
clip-path: polygon(#{random($limit: 100)} %0%, #{random($limit: 100)} %10%, #{random($limit: 100)} %40%.0% 20%);
} @else if($i % 10= =0) {
clip-path: circle(24%);
} @else {
clip-path: polygon(#{random($limit: 40)} %0%, #{random($limit: 100)} %10%, #{random($limit: 100)} %80%, #{random($limit: 80)} %60%.0% 20%); }}}Copy the code
- Animation of shards
The animation of the shard is added to each shard, and the trajectory is similar to the following:
Singular numbers move up to the left first and then down, and even numbers move up to the right first and then down. The delay time of each animation is random, and the distance of movement is also random.
@for $i from 1 through 50 {
.suipian:nth-child(#{$i}) {
// ...
animation: move#{$i}.8s infinite;
animation-delay: -#{random($limit: 4)}s;
$der: #{random($limit: 100)}px;
@if ($i % 2= =0) {
$der: -#{random($limit: 100)}px;
}
@keyframes move#{$i30%} {{transform: translate($der,-#{random($limit: 100)}px);
opacity: 0.8;
}
100%{
transform: translate($der,#{random($limit: 200) + 10}px);
opacity: 0; }}}}Copy the code
The effect is this
Realization of animation
The static effect is now complete:
The whole animation includes two aspects, one is the falling of firecrackers, one is the burning of lines
- The fall of firecrackers
.container{/ /...animation: drop 1s forwards;
}
@keyframes drop{
80%.100%{
transform: scale(0.3) rotate(0deg) translateY(1600px);
opacity: 0; }}Copy the code
Set the animation delay for each firecracker to be different, note that the firecracker below should fall first, so it should look like this:
@for $i from 1 through 20 {
animation-delay: # {(20 - $i) *0.1}s;
}
@for $i from 20 through 40 {
animation-delay: # {(40 - $i) *0.1}s;
}
Copy the code
- Line of combustion
All you need to do is decrease the height of the line, because the spot and debris are located relative to the bottom of the line, so they automatically move up.
.main {
// ...
animation: ranshao 2s forwards;
@keyframes ranshao {
84%{
opacity: 1;
height: 80px;
}
100%{
opacity: 0;
height: 80px; }}}Copy the code
Bianpao. Vue
conclusion
The effect of the first edition is like this, from the idea of development to implementation has been more satisfied with ~~
Other animations: CSS to achieve pseudo-3D rubik’s cube dynamic effects