• 图片上下左右的无缝滚动的实现


    在网上浏览网页的时候,我们常常会看看无缝滚动的各种图片广告,但那是怎么实现的呢,今天我们就来说说如何实现图片的无缝滚动。

    首先,我们来看看结构层,也就是html,大家把src替换成自己的图片,图片的大小不要求一样大,代码会自动调整图片的大小,使其铺满整个容器。

    <ul id="marquee">
        <li>
          <img id="index1" src="img/1.png" />
          <img id="index2" src="img/2.png" />
          <img id="index2" src="img/3.png" />
          <img id="index2" src="img/4.png" />
          <img id="index2" src="img/5.png" />
          <img id="index2" src="img/6.png" />
        </li>
    </ul>

    总的思路基本是这样,让图片整体向某个方向移动,当图片移动到某一个距离后就回到原点。为了防止图片移着移着就没有了,我们需要两套相同的图片。

    首先大家肯定有个疑惑,图片大小不一致真的可以吗?可以,大家只需要用css设置父容器的大小就可以了,剩下的交给代码解决。我们先用window.getComputedStyle来获取父容器的大小,这里获取的数值是有px的,因此还需要切除,前面的“+”是将其转化为数值。

      //获取容器设定的宽度,用于设定img的宽度,使得图片自适应容器的大小。
        cWidth=window.getComputedStyle(container , null)['width'];
        cHeight=window.getComputedStyle(container , null)['height'];
        cWidth=+cWidth.slice(0,cWidth.length-2);
        cHeight=+cHeight.slice(0,cHeight.length-2);

    但是大家都知道img有个问题,就是他们之间并不是无缝的,为此,我用style.cssText将img设置为float:left;这样,图片之间就是无缝的了,也就是默认状态下图片是水平排列的。那如果我要向上或者向下滚动呢,只需要设置li的宽度为父容器的宽度就可以变成竖直排列了,是不是很简单?前面我还提到图片的大小

    //设置图片的样式,float:left;所以不管在什么情况下,图片与图片之间都是无缝连接的,后面只需要改动slide宽度,就可以改变图片的排列方式了,水平竖直无缝切换
        for(var i=0 ,l=img.length; i<l;i++){
          img[i].style.cssText = "float:left;"+cWidth+"px;height:"+cHeight+"px";
        }
        
    //将宽度变为两倍这样可以容下两倍的图片,即默认是水平排列,同时复制一份自身加到原来图像上
        slide.style.width=imgNum*2*cWidth+"px";
        slide.innerHTML += slide.innerHTML;

    那该滚动到什么时候,我们是不是应该设置一个临界点?是的,我们必须设置一个临界点,当所有的图片都过了一遍的时候,我们就把它拉回来重新开始滚,因为方向的不同,临界点自然也不一样,跟父容器的大小有关。

      //水平和竖直方向上的临界点
        var horizontal = slide.offsetWidth/2,
            vertical=imgNum*cHeight;

     准备工作做好之后,就可以开始写滚动函数了。不管是哪个方向的滚动,其实原理是差不多的。下面就以向上滚动为例来讲讲。

    因为图片默认是水平排列的,因此第一步就是让图片数值排列。只要改变li的大小就可以了。我们在设一个变量,用来滚动,当滚动到临界点的时候,就重新开始滚动。方向向上,临界点就是当滚动的距离是所有的图片高度之和的时候,这时候,就可以返回了。代码具体如下:

         //slide.style.width是要有px的,而img[0].width是没有px的,只是数值
            slide.style.width=img[0].width+"px";//这样图片只能竖着排列
            //console.log(img[0].width); //500
            var delta=0;
            var rolling = function(){
              delta == -vertical ? delta = 0 : delta--;
              slide.style.top = delta + "px";
            }

    其他方向类推就是了。有四个放下,我们采用swich语句来实现方向的选择。

    当然,有时候,有些人对图片上的东西感兴趣,这时候,我们可以设置鼠标hover的时候,就暂停,移出去就继续滚动。

    container.onmouseover=function() {clearInterval(timer)}//鼠标移到marquee上时,清除定时器,停止滚动
        container.onmouseout=function() {timer=setInterval(rolling,speed)}//鼠标移开时重设定时器

    最后附上源码供大家学习参考:

    <!doctype html>
    <html>
      <head>
        <title>图片的无缝滚动  by sjq</title>
        <meta charset="utf-8"/>
        <style type="text/css">
        h1 {
          font:400 16px/1 "Microsoft YaHei",KaiTi_GB2312,SimSun
        }
        #marquee {
          width: 500px;
          height: 400px;
          padding:0;
          margin:0;
          overflow: hidden;
        }
        #marquee {
          position:relative;
          list-style:none;
          border:10px solid #369;
        }
        #marquee li {
          position:absolute;
          margin: 0px;
          padding: 0px;
        }
        #marquee img{
          margin: 0px;
          padding: 0px;
        }
    
      </style>
    </head>
    <body>
      <h1>图片的无缝滚动 by sjq</h1>
      <ul id="marquee">
        <li>
          <img id="index1" src="img/1.png" />
          <img id="index2" src="img/2.png" />
          <img id="index2" src="img/3.png" />
          <img id="index2" src="img/4.png" />
          <img id="index2" src="img/5.png" />
          <img id="index2" src="img/6.png" />
        </li>
      </ul>
    </body>
    <script type="text/javascript">
    
      var Marquee = function(id,direction,speed){
    
        //为了防止在ie6及以下的浏览器出现图片一闪的现象
        try{document.execCommand("BackgroundImageCache", false, true);}catch(e){};
    
        var container = document.getElementById(id),
        slide = container.getElementsByTagName("li")[0],
        img= container.getElementsByTagName("img"),
        speed = parseInt(speed)|| 10,//默认速度为10
        imgNum=img.length; //获取图片的数量
    
        //获取容器设定的宽度,用于设定img的宽度,使得图片自适应容器的大小。
        cWidth=window.getComputedStyle(container , null)['width'];
        cHeight=window.getComputedStyle(container , null)['height'];
        cWidth=+cWidth.slice(0,cWidth.length-2);
        cHeight=+cHeight.slice(0,cHeight.length-2);
    
        //设置图片的样式,float:left;所以不管在什么情况下,图片与图片之间都是无缝连接的,后面只需要改动slide宽度,就可以改变图片的排列方式了,水平竖直无缝切换
        for(var i=0 ,l=img.length; i<l;i++){
          img[i].style.cssText = "float:left;"+cWidth+"px;height:"+cHeight+"px";
        }
        
        //console.log(container.getElementsByTagName("li")[0].offsetHeight);//400
        //console.log(container.getElementsByTagName("img")[0].offsetHeight);//400
        //console.log("container.scrollTop"+container.scrollTop);//0
    
        //将宽度变为两倍这样可以容下两倍的图片,即默认是水平排列,同时复制一份自身加到原来图像上
        slide.style.width=imgNum*2*cWidth+"px";
        slide.innerHTML += slide.innerHTML;
    
        //水平和竖直方向上的临界点
        var horizontal = slide.offsetWidth/2,
            vertical=imgNum*cHeight;
        console.log("slide.offsetWidth:"+slide.offsetWidth);
    
        //console.log(container.getElementsByTagName("li")[0].offsetHeight);//400
        //console.log("img[0].height"+img[0].height);//400
    
        //根据方向选取不同运动方式
        switch(direction){
          //刚开始距离左边为0
          case "left":
            var delta = 0;
            var rolling = function(){
              delta == -horizontal ? delta = 0 : delta--;
              slide.style.left = delta + "px";
            }
            break;
    
          //刚开始定位到复制的那一份的位置,然后在滚动,滚动到头的时候,再切换回去
          case "right":
            var delta=-horizontal; 
            var rolling = function(){
              delta == 0 ? delta = -horizontal : delta++;
              slide.style.left = delta + "px";
            }
            break;
    
          //刚开始距离上边为0
          case "up":
            //slide.style.width是要有px的,而img[0].width是没有px的,只是数值
            slide.style.width=img[0].width+"px";//这样图片只能竖着排列
            //console.log(img[0].width); //500
            var delta=0;
            var rolling = function(){
              delta == -vertical ? delta = 0 : delta--;
              slide.style.top = delta + "px";
            }
            break;
    
          case "down":
            slide.style.width=img[0].width+"px";;
            var delta=-vertical;
            var rolling = function(){
              delta == 0 ? delta = -vertical : delta++;
              slide.style.top = delta + "px";
            }
            break;
        }
    
        var timer = setInterval(rolling,speed)//设置定时器
    
        container.onmouseover=function() {clearInterval(timer)}//鼠标移到marquee上时,清除定时器,停止滚动
        container.onmouseout=function() {timer=setInterval(rolling,speed)}//鼠标移开时重设定时器
      }
    
      window.onload = function(){
        Marquee("marquee","up","ttt");
      }
    </script>
    </html>
    View Code

    ps:最后大家实现临界点哪里也可以采用scrollTop,scrollLeft,offsetWidth来实现

    本文参考:

    1、javascript无缝滚动

    2、javascript无缝滚动2

  • 相关阅读:
    B题 hdu 1407 测试你是否和LTC水平一样高
    A题 hdu 1235 统计同成绩学生人数
    hdu 1869 六度分离(最短路floyd)
    hdu 2795 Billboard(线段树+单点更新)
    hdu 1754 I Hate It(线段树)
    hdu 1166敌兵布阵(线段树)
    hdu 1556(线段树之扫描线)
    Contest2073
    中南oj String and Arrays
    51nod 1459 迷宫游戏 (最短路径—Dijkstra算法)
  • 原文地址:https://www.cnblogs.com/huansky/p/5446766.html
Copyright © 2020-2023  润新知