放着我来——CSS3、jQuery的动画效果

最近做了一个网站界面,里面用了不少动画效果,有的直接用CSS3的特性,有的用jQuery实现,让我深刻体会到CSS3的博大精深。话说:”有总结才有进步“,这里规整一下,便于未来翻阅。

开发环境:
Bootstrap v4.0.0
jQuery v3.2.1
Swiper 4.2.6

动画效果一:图片轮播

1.轮播单个图片

Bootstrap下的carousel,很容易就实现这个功能。

但是客户有个小需求,就是图片上的prev、next的两个按钮要在鼠标移动到图片上才渐显,鼠标离开图片就隐藏这两个按钮,同时prev、next要用客户提供的图片。通常我们会通过display来控制图片的显示与否,使用display的缺点是需要设置img之外的div的宽高,否则img的display为none的时候,样式会乱。这里我使用CSS3中的“隐身术”—— opacity,img一直都在,只是“隐身”了。

//html、js代码还是Bootstrap的标准代码。
<section id="banner" class="carousel slide" data-ride="carousel">
    <ol class="carousel-indicators">
      <li data-target="#banner" data-slide-to="0" class="active"></li>
      <li data-target="#banner" data-slide-to="1"></li>
      <li data-target="#banner" data-slide-to="2"></li>
    </ol>
    <div class="carousel-inner">
      <div class="carousel-item active">
        <img class="d-block w-100" src="images/banner01.png" >
      </div>
      <div class="carousel-item">
        <img class="d-block w-100" src="images/banner02.png" >
      </div>
      <div class="carousel-item">
        <img class="d-block w-100" src="images/banner03.png" >
      </div>
    </div>
    <a class="carousel-control-prev" href="#banner" role="button" data-slide="prev">
      <img src="images/left.png">
    </a>
    <a class="carousel-control-next" href="#banner" role="button" data-slide="next">
      <img src="images/right.png">
    </a>
</section> 
<script>
    $('#banner').carousel({
      interval: 3000 //banner 停留3秒
    })
</script>

<style>
    /*关键是CSS的代码*/
    .carousel .carousel-control-prev , .carousel .carousel-control-next { 
      opacity: 0;  /*隐身了*/
    }
    .carousel:hover .carousel-control-prev,.carousel:hover .carousel-control-next {  
      opacity: 1;  /*现身*/
      -moz-transition: opacity 4s; /* 渐显效果 Firefox 4 */ 
      -webkit-transition: opacity 4s; /* Safari 、 Chrome  */ 
      -o-transition: opacity 4s; /* Opera  */ 
    }
</style>

2.轮播多个图片

Bootstrap下的carousel能够非常方便的实现轮播单图,但是这个网页还需要轮播多图,就是一屏显示多图,单击next,向右滚动一张图片;单击prev,向左滚动一张图。carousel就不中了。

在谷歌上找到不少jQuery的插件,都不满意,无意间找到 Swiper这个工具,在基础演示中发现210这个示例离我的要求比较贴近,果断的使用之。

无奈的是,估计是Swiper要支持移动端,故为了节省界面空间,把prev和next按钮缺省都放在了图片上,这对于我那眼里揉不得沙子的客户可是接受不了的。又求助谷歌,发现还真有不少伙计问Swiper如何把这两个按钮放在图片外面,不过没有得到明确的解决方案,看来只能依靠自己了。

看了Swiper的代码,发现prev、next按钮是在js中指定的,这就意味着你想用哪个按钮控制图片的轮播,prev、next按钮放哪里,都随你。

这里需要注意slidesPerGroup参数,如果希望图片分组显示,就是1、2、3、4显示,按下next,显示5、6、7、8,可以使用slidesPerGroup,注意图片总数必须是slidesPerGroup设置数字的整数倍,否则最后一页就让你崩溃了;如果不设置这个参数,显示方式就是 1、2、3、4;2、3、4、5;就是我的这个需求。

<div class="col-md-1" id="myswiper-next">
  <span class="span-vertical"></span>
  <img class="vertical"  src="images/left.png"/>
</div>
<div class="col-md-10">
    <div class="swiper-container" id="myswiper">
        <div class="swiper-wrapper">
            <div class="swiper-slide">
              <img src="images/img01.png"/>
            </div>
            <div class="swiper-slide">
              <img src="images/img02.png"/>
            </div>
            <div class="swiper-slide">
              <img src="images/img03.png"/>
            </div>
            <div class="swiper-slide">
              <img src="images/img04.png"/>
            </div>
            <div class="swiper-slide">
              <img src="images/img05.png"/>
            </div>
            <div class="swiper-slide">
              <img src="images/img06.png"/>
            </div>
            <div class="swiper-slide">
              <img src="images/img07.png"/>
            </div>
        </div>
    </div>
</div>
<div class="col-md-1" id="myswiper-prev">
    <span class="span-vertical"></span>
    <img class="vertical"  src="images/right.png"/>
</div>

<script>
  new Swiper('#myswiper', {
    slidesPerView: 5,
    spaceBetween: 3,
    //slidesPerGroup: 4, //如果要分组显示,图片的总数必须是4的倍数
    loop: true,
    loopFillGroupWithBlank: true,
    navigation: {
      nextEl: '#myswiper-next',  //指定next按钮
      prevEl: '#myswiper-prev', //指定prev按钮
    }
  });
</script>

3.走马灯

这个需求有点类似轮播单图,只是图片要“犹抱琵琶半遮面”的从左边慢慢的往右移动。这个可以在网上找到很多现成代码,但都不能满足要求,为啥呢?“上帝”要求,图片显示完整后,要停留数秒钟,再继续移动。

在简书上找到了无缝向上、向左滚动--间歇性滚动,文中的向左滚动的代码跟我的需求契合度高,代码借过来使使。

对于停留数秒钟,有人推荐使用setTimeout,我试了一下,在这个场景中不行,图片的移动控制有问题。于是采用“耗费CPU”的方法,用while循环。

<script>
//js代码
//停留程序
var sleep = function(n){
  var start=new Date().getTime();
  while(true) if(new Date().getTime()-start>n) break;
}
var scrollleft =  function(){
  var timer = null;
  var speed = 1000/40;
  var html = $("#scrollwrap").html();
  var container = $("#scrollcontent");
  $("#scrollwrap").html(html + html);
  var len = $("#scrollwrap").children('li').length;
  var width = $("#scrollwrap").children('li').eq(0).innerWidth();
  var index = 0;
  $("#scrollwrap").width(len * width);
  timer = setInterval(function(){
    //每幅图的宽度为700
    //第一幅图显示完全后,停留2秒后,继续走
    if(container.scrollLeft() == 700){   
      sleep(2000)
      container.scrollLeft(index++)
    }else{
      //第二幅图显示完全后,停留2秒,回到原地,重新来过
      if(container.scrollLeft() == 1400){
        sleep(2000)
        index = 0
        container.scrollLeft(index);
      }else{  
        container.scrollLeft(index++)
      }
    }
  },speed);
}
</script>
<div id="scrollcontent">
    <ul id="scrollwrap">
        <li><img src="images/img01.png"></li>
        <li><img src="images/img02.png"></li>
    </ul>
</div>
<script>
  scrollleft();   //调用
</script>

注意:我的需求中仅显示两张图片,在js代码中判断ul的位置判断了两次,如果是更多的图,js代码需要根据实际需求优化。

动画效果二:给图片添加说明文字

鼠标移动到图片上时显示说明文字,鼠标移走时文字消失。“隐身术”——opacity可以很容易实现,文字的显示和消失,关键点在于说明文字的position。

<div class="img-group" style="background:url(images/img1.png)">
  <div class="img-tip">
    <p>我是图片的解释文字</p>
  </div>
</div>

<style>
    .img-group {
      position: relative;
      width:100%;
      height:140px;
    }
    .img-tip {
      position: absolute;
      bottom: 0;
      padding:5px 10px;
      color:white;
      font-size:10px;
      width:100%;
      opacity: 0;
      height :70px
      background: rgba(0,0,0,.3);
    }
    .img-group:hover div{
      opacity: 1;
      -webkit-transition: all 1s;
      -moz-transition: all 1s;
      transition: all 1s;
    }
</style>

鼠标掠过,给图片加上蒙层

这个需求就是鼠标移动到图片上时,图片加上透明的蒙层。这个有两种实现方式:

  1. 参考上述方法,多添加一个div,div中无内容,需要注意的是这种方式适用于图片尺寸是固定的。

  2. 对于图片尺寸是自适应的,也可以使用 opacity 实现,参见如下代码:

    img:hover{
      filter:alpha(opacity=10);
      opacity:.1
    }
    

动画效果三:鼠标移动到图片,图片变换

1.变换前后的图片大小相同

客户希望ul li的黑点变成自选图片,鼠标移动到图片上变换图片。这个可以用background直接实现。

<ul class="changebg">
    <li>hover可以换背景1</li>
    <li>hover可以换背景2</li>
    <li>hover可以换背景3</li>
    <li>hover可以换背景4</li>
</ul>

<style>
    .changebg{
      list-style-type:none;
      padding:0px
    }
    .changebg li{
      background:url(../images/bg1.png) no-repeat 0px 17px;
      padding-left:15px;
    }
    .changebg li:hover{
      background:url(../images/bg2.png) no-repeat 0px 17px;
      padding-left:15px;
    }
</style>

2.变换前后的图片大小不同

网页右侧的工具栏中的图片,鼠标移动到图片上,展现出图片向左推出(即两个图片的内容是一样的,只是推出的图片右边的边框长了点)的效果。对于这个效果,我本想用background的方法,但是两个图片大小不同,变换的时候样式乱了;也想过用一个图片,通过改CSS效果,但是也不成功。于是尝试用jQuery的hover来改变img标签的内容,进行两个图片的切换,搞定!

<div class="rapid-tools">
  <div>
    <a href="tojianshu" >
        <img src="images/jianshu.png" class="rapid-img" id="img_jianshu" imagename="jianshu">
    </a>
  </div>
  <div>
    <a href="tobaidu" >
        <img  src="images/baidu.png"  class="rapid-img" id="img_baidu" imagename="baidu">
    </a>
  </div>
</div>

<script>
  $("img[id^='img_']").hover(function(){
    $(this).attr('src' , "images/"+$(this).attr('imagename')+"_l.png") ;
  },function(){
    $(this).attr('src' , "images/"+$(this).attr('imagename')+".png") ;
  })
</script>

动画效果四:鼠标掠过,元素放大

这个CSS3已经替我们想到了 —— transform,它可以实现旋转、放大、移动等特效,详情可以参考 CSS3 transform

myimg:hover{
  transform: scale(1.2,1.2); //原图放大1.2倍
  cursor: pointer;
  transition: 0.5s ease;  //效果柔和点
} 

浏览器兼容性

这个问题是让所有前端工程师头痛的问题,尤其是面对早期IE的兼容,简直是欲哭无泪。好在我的客户这次没有这么强硬,要求只要支持IE10就可以,但是如果用户使用IE10以下的浏览器访问,要给出一个友好的提示。这就涉及到对浏览器的判定问题。谷歌上可以找到很多检测浏览器版本的方法,如用navigator或者特殊的函数。对于各浏览器对CSS3的支持,可速查CSS3 浏览器支持参考手册

我用的后者,因为只需要判断IE10一下的版本,用特殊的函数简单些。

<script>
//如果低于IE10,定向到提示界面
if(!window.FormData){
    window.location.href("alarm.html")
}
</script>

//需要注意,alarm.html是在IE10以下浏览器中显示,所以只能用低版本的jQuery
<html>
  <head>
    <!--[if lte IE 9]>
        <script src="js/jQuery-1.12.4.min.js"></script>
    <![endif]-->
  </head>
</html>

总结

虽然被客户的需求整得几近崩溃,但是还是在骂完之后耐着性子干完了活儿,事后总结还是学到了不少东西。

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

推荐阅读更多精彩内容

  • 框架一 :: Animate.css Animate.css是一个css动画样式库,可以减少我们的开发时间.它预设...
    西巴撸阅读 2,625评论 0 5
  • 转载请声明 原文链接 关注公众号获取更多资讯 这篇文章主要总结H5的一些新增的功能以及一些基础归纳,这里只是一个提...
    程序员poetry阅读 9,073评论 22 225
  • 一片雪花飞舞着 凋谢 一树黄叶坠落了 成泥 我也曾紧闭双眼 不知向何处来 不知往何处去 也想在虚无中寂灭 借死亡来...
    唯如风_阅读 137评论 0 1
  • “小队长,”眼前人笑的依旧温文尔雅,“我要走了。”少年一下子有点慌了神。 他揉了揉那个毛茸茸的脑袋,耐心的嘱咐。 ...
    Kaname阅读 301评论 0 3
  • 看盘常见的10个知识要点(七) 市盈率和市净率是衡量市场估值水平的重要指标,在炒股软件中十分常见。 ...
    小炒怡情阅读 403评论 0 0