这里主要是使用CSS的animation和伪类来构建,分析设定关键帧的执行顺序和时间段。
效果
动画分析
首先通过效果对动画执行进行一下分析:
- 边框的四条边进行按顺序动画加载 。
- 矩形边框变为圆行边框。
- 太极图内部图案渐渐出现。
- 太极图旋转。
- 整个动画逆序执行。
针对上面的1效果是需要思考一下的,其他都比较容易实现。5效果只需设置属性animation-direction: alternate
即可,整体动画加入animation-iteration-count: infinite
来保证无限循环。
静态效果实现
首先将静态效果做出来。
html结构:
<div id="loader"><div class="logo"><div class="left"></div><div class="right"></div></div> <p>Loading...</p>
</div>
CSS(LESS)部分:
@border-width:2px;
@loader-width:150px;
@loader-insider-width:@loader-width * 0.15;
@animate-time:4s;*{margin: 0;padding: 0;border: 0;
}html, body{width: 100%;height: 100%;
}#loader{position: absolute;top: 0;left: 0;bottom: 0;right: 0;display: flex;flex-direction: column;justify-content: center;align-items: center;p {padding: 1.5em;font-family: Arial;}.logo{width: @loader-width;height: @loader-width;position: relative;&:before{position: absolute;content: '';left: 0;top: 0;border-color: transparent;border-width: @border-width;border-style: solid;border-top-color: #000;border-right-color: #000;width: 100%;height: 100%;}&:after{position: absolute;content: '';bottom: -2 * @border-width;right: -2 * @border-width;border-color: transparent;border-width: @border-width;border-style: solid;border-bottom-color: #000;border-left-color: #000;width: 100%;height: 100%;}.left{position: absolute;width: 50%;height: 100%;top: @border-width;right: 50%;background-color: #000;border-top-left-radius: 100% 50%;border-bottom-left-radius: 100% 50%;&:before{position: absolute;content: '';width: 100%;height: 50%;bottom: 0;left: 50%;border-radius: 50%;background-color: #000;}&:after{position: absolute;content: '';width: @loader-insider-width;height: @loader-insider-width;background-color: #fff;bottom: ~'calc(25% - @{loader-insider-width} / 2)';left: ~'calc(100% - @{loader-insider-width} / 2)';border-radius: 50%;} }.right{position: absolute;width: 50%;height: 100%;top: @border-width;left: 50%;border-top-right-radius: 100% 50%;border-bottom-right-radius: 100% 50%;&:before{position: absolute;content: '';width: 100%;height: 50%;top: 0;right: 50%;border-radius: 50%;background-color: #fff;}&:after{position: absolute;content: '';width: @loader-insider-width;height: @loader-insider-width;background-color: #000;top: ~'calc(25% - @{loader-insider-width} / 2)';right: ~'calc(100% - @{loader-insider-width} / 2)';border-radius: 50%;} } }
}
效果:
动画实现
上面已经把静态的效果实现了,现在将动画部分抽离出来。
动画关键帧时间段
根据效果,做如下时间段划分:
边框效果实现
将.logo
的两个伪类的宽高设置为0,然后添加动画效果:
.logo{width: @loader-width;height: @loader-width;position: relative;animation: spin @animate-time infinite;animation-direction: alternate;animation-timing-function:ease;&:before{position: absolute;content: '';left: 0;top: 0;border-color: transparent;border-width: @border-width;border-style: solid;animation: line-before @animate-time infinite;animation-direction: alternate;}&:after{position: absolute;content: '';bottom: -2 * @border-width;right: -2 * @border-width;border-color: transparent;border-width: @border-width;border-style: solid;animation: line-after @animate-time infinite;animation-direction: alternate;}
}
keyframes:
@keyframes line-before {0% {width: 0;height: 0;border-top-color: #000;}9.9% {border-right-color: transparent;}10% {width: 100%;border-right-color: #000;border-top-color: #000;height: 0;}20%,100% {width: 100%;border-right-color: #000;border-top-color: #000;height: 100%;}40% {width: 100%;border-right-color: #000;border-top-color: #000;height: 100%;border-radius: 0;}//在执行到50%的时候变圆50%, 100% {width: 100%;border-right-color: #000;border-top-color: #000;height: 100%;border-radius: 50%;}
}@keyframes line-after {0%,19.9% {border-color: transparent;width: 0;height: 0;}20% {width: 0;height: 0;border-bottom-color: #000;}29.9% {border-left-color: transparent;}30% {width: 100%;border-left-color: #000;border-bottom-color: #000;height: 0;}40% {width: 100%;border-left-color: #000;border-bottom-color: #000;height: 100%;border-radius: 0;}//在执行到50%的时候变圆50%, 100% {border-radius: 50%;width: 100%;border-left-color: #000;border-bottom-color: #000;height: 100%;}
}
内部图案出现效果
这个直接调一下透明度即可:
@keyframes left-right-fade {0%, 50%{opacity: 0;}75%, 100% {opacity: 1;}
}
旋转效果
@keyframes spin {0%, 75%{transform:rotate(0deg);}90%, 100% {transform:rotate(360deg);}
}
所有样式代码
//author: 王乐平
//date: 2017.8.1
//blog: http://blog.csdn.net/lecepin@border-width:2px;
@loader-width:150px;
@loader-insider-width:@loader-width * 0.15;
@animate-time:4s;*{margin: 0;padding: 0;border: 0;
}html, body{width: 100%;height: 100%;
}#loader{position: absolute;top: 0;left: 0;bottom: 0;right: 0;display: flex;flex-direction: column;justify-content: center;align-items: center;p {padding: 1.5em;font-family: Arial;}.logo{width: @loader-width;height: @loader-width;position: relative;animation: spin @animate-time infinite;animation-direction: alternate;animation-timing-function:ease;&:before{position: absolute;content: '';left: 0;top: 0;border-color: transparent;border-width: @border-width;border-style: solid;animation: line-before @animate-time infinite;animation-direction: alternate;}&:after{position: absolute;content: '';bottom: -2 * @border-width;right: -2 * @border-width;border-color: transparent;border-width: @border-width;border-style: solid;animation: line-after @animate-time infinite;animation-direction: alternate;}.left{position: absolute;width: 50%;height: 100%;top: @border-width;right: 50%;background-color: #000;border-top-left-radius: 100% 50%;border-bottom-left-radius: 100% 50%;animation: left-right-fade @animate-time infinite;animation-direction: alternate;&:before{position: absolute;content: '';width: 100%;height: 50%;bottom: 0;left: 50%;border-radius: 50%;background-color: #000;}&:after{position: absolute;content: '';width: @loader-insider-width;height: @loader-insider-width;background-color: #fff;bottom: ~'calc(25% - @{loader-insider-width} / 2)';left: ~'calc(100% - @{loader-insider-width} / 2)';border-radius: 50%;} }.right{position: absolute;width: 50%;height: 100%;top: @border-width;left: 50%;border-top-right-radius: 100% 50%;border-bottom-right-radius: 100% 50%;animation: left-right-fade @animate-time infinite;animation-direction: alternate;&:before{position: absolute;content: '';width: 100%;height: 50%;top: 0;right: 50%;border-radius: 50%;background-color: #fff;}&:after{position: absolute;content: '';width: @loader-insider-width;height: @loader-insider-width;background-color: #000;top: ~'calc(25% - @{loader-insider-width} / 2)';right: ~'calc(100% - @{loader-insider-width} / 2)';border-radius: 50%;} } }
}@keyframes line-before {0% {width: 0;height: 0;border-top-color: #000;}9.9% {border-right-color: transparent;}10% {width: 100%;border-right-color: #000;border-top-color: #000;height: 0;}20%,100% {width: 100%;border-right-color: #000;border-top-color: #000;height: 100%;}40% {width: 100%;border-right-color: #000;border-top-color: #000;height: 100%;border-radius: 0;}50%, 100% {width: 100%;border-right-color: #000;border-top-color: #000;height: 100%;border-radius: 50%;}
}@keyframes line-after {0%,19.9% {border-color: transparent;width: 0;height: 0;}20% {width: 0;height: 0;border-bottom-color: #000;}29.9% {border-left-color: transparent;}30% {width: 100%;border-left-color: #000;border-bottom-color: #000;height: 0;}40% {width: 100%;border-left-color: #000;border-bottom-color: #000;height: 100%;border-radius: 0;}50%, 100% {border-radius: 50%;width: 100%;border-left-color: #000;border-bottom-color: #000;height: 100%;}
}@keyframes left-right-fade {0%, 50%{opacity: 0;}75%, 100% {opacity: 1;}
}@keyframes spin {0%, 75%{transform:rotate(0deg);}90%, 100% {transform:rotate(360deg);}
}
博客名称:王乐平博客
CSDN博客地址:http://blog.csdn.net/lecepin
