loading动效实现"/>
loading动效实现
在站上闲逛发现一个非常有意思的loading效果,跟着大佬仿写了一下Vue版本的。
直接放源码
<script setup>
import {ref, defineProps, watch} from "vue";const props = defineProps({isShow: {type: Boolean,default: false},leafNum: {type: Number,default: 5} // 叶子数量
})const isLoading = ref(false);
const progressNum = ref(0);
let progress;
let leafIntervalArr; // 保存leaf的定时器watch(() => props.isShow, () => {if (!props.isShow) {// 触发关闭loading的时候延迟1.4s关闭,确保动画完整progressNum.value = 100;clearInterval(progress);setTimeout(() => {isLoading.value = false;progressNum.value = 0;// 结束动画后清空定时器for (let i = 0; i < leafIntervalArr.length; i++) {clearInterval(leafIntervalArr[i]);}}, 1400)} else {isLoading.value = true;setInterval(() => {if (progressNum.value <= 90) {progressNum.value += 1;}}, 300);setTimeout(() => {randomLeaf();}, 1000)}
})function randomLeaf() {leafIntervalArr = new Array(props.leafNum);for (let i = 0; i < props.leafNum; i++) {let leaf = document.createElement('img');leaf.className = 'leaf';leaf.src = '/src/assets/images/loading/leaf.png';leaf.alt = '叶子';console.log(document.querySelector('.loading-progress'));document.querySelector('.loading-progress').appendChild(leaf);// 随机时间 1~5ssetTimeout(() => {let activeLeaf = document.querySelectorAll('.leaf')[i];let x = 260, y = 0;activeLeaf.style.left = x + "px"; //初始坐标xactiveLeaf.style.top = y + "px"; //初始坐标yleafIntervalArr[i] = setInterval(function () {x = x - 5; //运动速度y = Math.floor(Math.sin(x / 260 * 2 * Math.PI) * Math.floor(Math.random() * 10)) + Math.floor(Math.random() * 10); //运动的高度if (x < 0) x = 260;activeLeaf.style.left = x + "px";activeLeaf.style.top = y + "px";activeLeaf.style.transform = "rotate(" + Math.floor(Math.random() * 360) + "deg)";}, 100);}, Math.floor(Math.random() * 5000) + 1);}
}
</script><template><transition><div class="loading-container" v-if="isLoading"><div class="loading-text">loading...</div><div class="loading-wrapper"><div class="loading-progress"><div class="loading-progress-content" :style="{width: progressNum + '%'}"></div><!-- 叶子区域 --></div><div class="loading-fan fan-container"><img class="fan" :class="{'fan-close':progressNum === 100}"src="../../assets/images/loading/fan.png" alt="风扇"><img class="max" v-if="progressNum === 100" src="../../assets/images/loading/100.png"alt="100%"></div></div></div></transition>
</template><style scoped>
.loading-container {width: 100vw;height: 100vh;background-color: #E3B12FD0;display: flex;justify-content: center;align-content: center;align-items: center;flex-wrap: wrap;position: fixed;top: 0;right: 0;
}.loading-text {width: 100%;text-align: center;font-size: 20px;font-weight: bold;color: rgb(255, 168, 0);margin-bottom: 20px;
}.loading-wrapper {width: 300px;height: 48px;background-color: #EED385D2;border-radius: 24px;position: relative;z-index: 9;
}.loading-progress {width: 260px;height: 36px;background-color: #EED385D2;border-top-left-radius: 16px;border-bottom-left-radius: 16px;margin: 6px 0 6px 6px;overflow: hidden;position: absolute;top: 0;left: 0;
}.loading-progress-content {width: 0;height: 36px;background-color: rgb(255, 168, 0);transition: all 0.5s;position: relative;z-index: 9;
}.loading-fan {width: 48px;height: 48px;border-radius: 50%;background-color: rgb(251, 205, 81);border: 3px solid rgba(255, 255, 255, 0.6);box-sizing: border-box;position: absolute;top: 0;right: 0;z-index: 9;
}.fan {width: 36px;height: 36px;position: absolute;top: 3px;left: 4px;animation: spin 2s infinite linear;
}.fan-close {animation: fanClose 1.3s 1 linear;animation-fill-mode: forwards;
}.max {width: 36px;height: 36px;position: absolute;top: 3px;left: 3px;animation: maxFont 1.3s 1 linear;animation-fill-mode: forwards;
}@keyframes spin {from {transform: rotate(360deg);}to {transform: rotate(0deg);}
}@keyframes fanClose {from {transform: rotate(360deg) scale(1);}to {transform: rotate(0deg) scale(0);}
}@keyframes maxFont {from {transform: scale(0);}to {transform: scale(1);}
}
</style>
<style>
.leaf {width: 15px;height: 15px;position: absolute;top: 0;left: 260px;z-index: 5;transition: all 0.01s;
}
</style>
核心思想:
- css动画旋转风扇,根据时间慢慢增加进度条的宽度。
- 生成最大数量的叶子,随机事件、随机振幅、随机旋转角度从右向左沿正弦曲线运动
更多推荐
loading动效实现
发布评论