利用border-radius属性及动画属性制作圆饼loading动画

百度前端技术学院2017于2月24日开始进行,一共有6个学院可供学习,分别是小薇学院(html/css基础)、斌斌学院(js基础)、耀耀学院(小游戏/交互)、商业平台学院(web/ios/android)、ECharts & WebVR学院(VR相关)和糯米学院(css3/vue等),从百度前端技术学院今年推出的各学院任务看来,目前互联网行业对从事前端行业的程序员要求越发高了。转行前端或是才开始学习前端的同学任重而道远,大家一起加油,共勉。

《CSS3圆饼loading效果》作为糯米学院中的进阶任务,目的主要是让学员通过完成任务,掌握border-radius属性的使用以及旋转动画的设置。在已经完成鼠标悬浮效果任务之后,相对来说本任务要简单很多。以下是总结。

任务分解:该任务要达到的效果。如网页中显示情况,可将任务分解为两个小任务:

1.制作四分之三圆环并旋转;
2.制作圆饼,圆饼内有两种颜色,分别交替旋转扩大其扇形区域(从0deg到到360deg),以达到圆饼loading效果。

通过完成任务,使用到如下一些重要属性:

1.制作圆环,使用伪元素,使用border(包括其transparent值);
2.制作圆饼过程中,使用到animation-timing-function属性的steps()曲线;
3.圆饼及圆环的旋转,使用animation系列属性,并使用transform设置旋转角度,使用transform-origin属性设置旋转中心。

以下是完成本任务后的html结构:

<header>
  <h1><a href="http://smallstarz.com/">小星的博客|Small Star's Blog</a></h1>
  <ul>
    <li><a href="#top-bottom1">点我</a></li>
    <li><a href="#top-bottom2">快点我</a></li>
      <li><a href="#top-bottom3">点我吧</a></li>
      <li><a href="#top-bottom4">点我啦</a></li>
  </ul>
</header>
<article>
  <p class="round1">
    <span class="bgcircle">
      <span class="left"><span class="spining"></span></span>
      <span class="right"><span class="spining"></span></span>
    </span>
  </p>
  <p class="round2">
    <span class="bgcircle">
      <span class="inner">
        <span class="spiner"></span>
        <span class="filler"></span>
        <span class="masker"></span>
      </span>
      <span class="inner2">
        <span class="spiner"></span>
        <span class="filler"></span>
        <span class="masker"></span>
      </span>
    </span>
  </p>
</article>
<footer>
  <p>版权所有 &copy 小星</p>
</footer>
</body>
</html>

其中,round1为使用第一种方法制作圆饼时的loading整体结构,round2为使用第二种方法制作圆饼时的loading整体结构。可以明显发现round2方法结构复杂,实际上其实现方法也较round1方法笨拙。结构样式代码请见文末demo代码地址。页面图如下:

页面图

圆环及圆饼制作原理如下:

1.四分之三圆环的旋转:
  实现原理:首先将上文html结构中的类名为bgcircle的span元素设置为圆形(将其border-radius设置为50%即可),其宽高大于两个子元素span,以便圆环与圆饼分开。在.bgcircle上设置伪元素,同样设置为圆形,大小与.bgcircle相同,再设置伪元素边框,其中任一边框设置为transparent即可。最后利用animotion和transform设置旋转动画。css代码如下:

/*2-1-1.制作大圆背景*/
.bgcircle{
  position:relative;
  display:inline-block;
  height:80px;
  width:80px;
  margin:50% 0 0 50%;
  top:-30px;
  left:-30px;
  border-radius:50%;
  overflow:hidden;
}
/*2-2.loading圆环*/
.bgcircle::before{
  content:"";
  position:absolute;
  width:100%;
  height:100%;
  box-sizing:border-box;
  border:4px solid #BD50A3;
  border-top:4px solid transparent;
  border-radius:50%;
  -webkit-animation:circle-spining 4s infinite linear;
  animation:circle-spining 4s infinite linear;
  -webkit-transform-origin:50% 50% 0;
  transform-origin:50% 50% 0;
}
@keyframes circle-spining{
  0%{transform:rotate(0deg);}
  50%{transform:rotate(-180deg);}
  100%{transform:rotate(-360deg);}
}
@-webkit-keyframes circle-spining{
  0%{-webkit-transform:rotate(0deg);}
  50%{-webkit-transform:rotate(-180deg);}
  100%{-webkit-transform:rotate(-360deg);}
}

2.圆饼旋转:
  (1)方法一:主要参考codepen网站中Geoffrey CrofteCSS Loaderdemo,其中也写了一些其他loading效果。总体来说,这些loading效果的主要原理都是:在.bgcircle之下,设置.left、.right为左右半圆,拼接为一个圆饼,对.left,设置其子元素.spining往右移至.right区域,并形成半圆与.right区域重叠,此时只有.spining旋转至.left区域时才能显示出来。同理,设置了.right的子元素.spining。最后,对两个.spining子元素设置不同的旋转动画已达到要求效果。css代码过长,请见文末demo代码地址,其旋转过程如下步骤表述:

a.初始状态下,两个.spining都没有旋转(图中深紫色圆饼):此时.left.spining围绕圆心开始逆时针旋转,至-180deg:

b.“.left.spining”围绕圆心开始逆时针旋转,至-180deg(图中浅紫色半圆):

c.“.left.spining”停止旋转,“.right.spining”开始旋转至-180deg,此时两个.spining都显示出来了,形成浅紫色圆饼:

d.“.right.spining”停止旋转,“.left.spining”又开始旋转,从-180deg旋转至-360deg,此时只剩下“.right.spining”形成的浅紫色右半圆:

e.“.left.spining”一周的旋转动画结束,停止旋转;“.right.spining”开始最后半周的旋转,至-360deg停止。整个一周的动画结束。对此动画设置无限循环次数,即可达到最终效果。

(2)方法二:参考张鑫旭博客的文章CSS3实现鸡蛋饼饼状图loading等待转转转,在张鑫旭前辈的这篇文章里,利用比喻把他的方法原理表述的很清楚,简单来说:他将动画分成了两半,如果以本文前面页面图中右边的圆饼作为例子的话,前半动画是深蓝色由12点钟位置开始逆时针旋转至-360deg,最后将橙色覆盖;后半动画刚好相反,橙色由12点钟位置开始逆时针旋转至-360deg,最后将深蓝色覆盖。由于两半部分动画的过程是相同的,所以将前半部分动画制作完成后,将该动画过程复制一份,将颜色对调,重新套入相同结构的新元素中,再将新的一套重叠在旧一套元素所占区域,设置前半段时间第一套元素显示、第二套元素透明,后半段时间第二套元素显示、第一套元素透明。这样就完成了圆饼loading效果。
下面以前半部分动画为例表述下动画过程:

首先需要了解html结构(以本文开始所列html结构为例),设置类名为inner的span作为父元素,该元素背景为深蓝色,其下同列三个span作为子元素,类名分别为:spiner、filler、masker。以上四者中,按照原理,.filler、.masker的z-index应该设置得高于.spiner,但在实际设置中,张鑫旭前辈没有设置z-index值,而是利用在html结构中将需要优先显示的元素并列在后面的方式(如果在html结构中将.masker与.spiner对调,就会出现错误),规避了这点。.masker为左半圆,深蓝色;.filler为右半圆,橙色;.spiner为旋转半圆,橙色,初始位置位于左半部分。

a.初始状态:.masker透明,此时由.spiner和.filler分别位于左右方拼接成橙色圆饼:

b.此时,.spiner开始围绕圆心逆时针旋转,则作为父元素的.inner开始从12点钟方向逆时针显露(深蓝色),到.spiner旋转-180deg时,.masker由透明变为显示,.filler由显示变为透明:

c.之后,.spiner继续逆时针旋转,由于.filler已经透明,则.inner从6点钟方向逆时针显露,而左半圆区域由于.masker已经显示(z-index值比.spiner大),也为深蓝色,这样,当.spiner旋转一周之后,就由橙色全部变为蓝色:

以上为动画原理,css代码过长,请见文末demo代码地址。在实现这个方法的过程中,还需要注意,要变化透明度的元素(.inner/.inner2/.masker/.filler),其透明度变化并不是渐变,而是突变,所以需要设置animation-timing-function为steps()突变曲线,steps(n,start/end)主要有两个值,简单来说,n设置突变次数(整数),start/end设置在动画开始还是结束突变。

思考:

1.利用steps()曲线,可以制作一些更炫酷的css3动画。并且,在同一个方向上连续渐变的动画,由于渐变位置不同,通常需要两个以上元素实现,但利用steps()曲线突变位置,就能通过一个元素实现了;
2.完成以上任务之后,可以优化的地方:第一个方法中的.spining子元素,可以使用伪元素替代;同理,第二个方法中的子元素,也可用伪元素替代;
3.圆环除了定长旋转,也可根据圆饼loading旋转的方法,实现变长旋转loading效果。

具体参考已在文中引出,不再单列,以下为我的demo及demo代码:

我的demo;
  demo代码;

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 219,366评论 6 508
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,521评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 165,689评论 0 356
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,925评论 1 295
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,942评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,727评论 1 305
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,447评论 3 420
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,349评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,820评论 1 317
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,990评论 3 337
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 40,127评论 1 351
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,812评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,471评论 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 32,017评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,142评论 1 272
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,388评论 3 373
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 45,066评论 2 355

推荐阅读更多精彩内容

  • 发现 关注 消息 iOS 第三方库、插件、知名博客总结 作者大灰狼的小绵羊哥哥关注 2017.06.26 09:4...
    肇东周阅读 12,107评论 4 62
  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 172,182评论 25 707
  • 原文地址:→看过来 写在前面 (附录有源码及效果) 之前碰到一个小练习,就是用纯CSS3来写饼状的loading效...
    楼心漫阅读 3,224评论 10 29
  • 如果这样真的算是失眠的话,已经好多年。最喜欢深夜。年少轻狂的时候,喜欢这种没有伪装虚妄的夜幕,肆意的享受着难得的自...
    Maxdiane阅读 314评论 0 0
  • 2017.6.21写简书的第12天 前几天在微博上看搞笑视屏,那个微博博主转载了一篇文章,标题是习惯可以成就你也可...
    隔壁小志龙阅读 318评论 0 1