利用MWheel插件基于jQuery animate写的一个滚屏效果

前两天我写了一个MWheel插件,一些朋友用了表示很方便,非常感谢大家的捧场。

今天闲着没事,花一个小时写了这个滚屏Demo,利用前两天我写的MWheel插件,结合jQuery的便利选择器以及我最喜欢的ainmate做一个滚屏效果。当然,滚屏效果很简单,无非就是for循环递增递减就能实现,算法简单。

在线Demo

源码

index.html

<!DOCTYPE html>
<html>
  <head>
    <meta charset="UTF-8" />  
    <title>滚屏效果 - 琼台博客</title>
    <style type="text/css">
      * { margin:0; padding:0; }
      .box { color:#FFF; text-align:center; font-size:10em; }
    </style>

    <script type="text/javascript" src="jquery-2.0.3.min.js"></script>
    <script type="text/javascript" src="MWheel.js"></script>
    <script type="text/javascript" src="page.js"></script>
    <script type="text/javascript">
      window.onload = function(){
        var element = document.getElementById('scroll');
        $(element).width($(document).width());
        $(element).height($(document).height());

        box(element);
      };  
    </script>
  </head>
  <body>
    <div id="scroll">
      <div class="box" style="background:red;" point="第一个">第一页</div>  
      <div class="box" style="background:black;" point="第二个">第二页</div>    
      <div class="box" style="background:blue;" point="第三个">第三页</div> 
      <div class="box" style="background:green;" point="最后一个">第四页</div>   
    </div>    
  </body>
</html>

page.js

(function (window, undefined) {
  var num = 1,
      width,
      height,
      element,
      parent,
      speed,
      lock = false,
      pointElement = [],
      color = '#FFF',
      scrollElement;

  var margin = function (n) {

    if (n > element.length) {
      num = element.length;   
    }

    if (n < 1) {
      num = 1;    
    }

    return (-1 * (height * (num - 1))) + 'px';
  };

  var scroll = function (marginTop) {
    $(parent).animate({
      'margin-top': marginTop    
    }, speed, function () {
      lock = false;
    });

    changePoint();
  };

  var changePoint = function () {
    var i;  

    for (i = 0; i < pointElement.length; i++) {
      if (i === num - 1) {
        pointElement[i].style.background = color;   
      }else{
        pointElement[i].style.background = 'none';
      }
    }
  };

  var createPoint = function (pe) {

    var mr = 5,
        ico_width = 10,
        ico_height = 10,
        ee,
        i,
        cssText,
        e = document.createElement('div'),
        width = ico_width + mr * 2 + 2,
        height = element.length * (ico_height + 2 + mr * 2);

    e.style.cssText = [
      'width:' + width + 'px',
      'height:' + height + 'px',
      'position: absolute', 
      'right: 10px',
      'top: 50%', 
      'margin-top:' + (-1 * parseInt(height / 2, 10)) + 'px'
    ].join(';');


    for (i = 0; i < element.length; i++) {
      ee = document.createElement('div');
      cssText = [
        'width:' + ico_width + 'px',
        'height:' + ico_height + 'px',
        'margin:' + mr + 'px',
        'cursor: pointer',
        'border-radius: ' + (ico_width / 2) + 'px',
        'border: 1px solid ' + color
      ];

      if (i === 0) {
        cssText.push('background:' + color);s
      }

      ee.style.cssText = cssText.join(';');
      ee.title = element.get(i).getAttribute('point');

      ee.addEventListener('click', (function (i) {
        return function () {  
          num = i + 1;
          lock = true;
          scroll(margin(num));
        };
      })(i));

      e.appendChild(ee);
      pointElement.push(ee);
    }

    pe.appendChild(e);

  };

  var box = function (e) {
    $('body').css({ overflow: 'hidden' });
    element = $(e).css({
      overflow: 'hidden',
      position: 'relative'
    }).find(' > .box');

    width = $(e).width();
    speed = height = $(e).height();

    element.each(function(){
      $(this).width(width);
      $(this).height(height); 
    }); 

    parent = document.createElement('div');
    parent.style.cssText = [
      'width:' + width + 'px',
      'height:' + (height * element.length) + 'px',
      'overflow: hidden',
    ].join(';');
    e.appendChild(parent);  
    $(parent).append(element);

    MWheel(parent)
      .addEventListener('down', function (event) {
        if (!lock) {
          lock = true;
          scroll(margin(--num));
        }
      })
      .addEventListener('up', function (event) {
        if (!lock) {
          lock = true;
          scroll(margin(++num));
        }
      });

    createPoint(e);
  };

  window.box = box;

})(window);

实现思路

首先是布局

既然是滚屏,那么我们首先能想到的模式大概就是一个div一个屏,div里面可以写每一屏的内容。这种div我这里简称为box,但box不能随便乱放,它得被一个div包着,容易分辨,结果就有了这个页面布局:

<div id="scroll">
  <div class="box" style="background:red;" point="第一个">第一页</div>  
  <div class="box" style="background:black;" point="第二个">第二页</div>    
  <div class="box" style="background:blue;" point="第三个">第三页</div> 
  <div class="box" style="background:green;" point="最后一个">第四页</div>   
</div>  

样式

为了灵活,滚屏效果的大小以box被包着的父层大小为主,也就是id=scroll的div要是全屏大小,那滚屏效果就是全屏,要是大小为500200,那么滚屏效果就是500200。所以在index.html页面中,有这两句话(第三第四行)就是让scroll当作全屏滚动效果而设置的

window.onload = function(){
  var element = document.getElementById('scroll');
  $(element).width($(document).width());
  $(element).height($(document).height());

  box(element);
};

实现滚动

JavaScript只不过是一个动态算法,要实现动画效果必须结合样式,能实现滚动效果的样式有很多种,我这次采用的是margin-top偏移的方式。首先在scroll里创建一个div,把class=box的div全部移入div内,div高度设置为scroll高度 * box个数,scroll设置overflow:hidden让它超出隐藏并隐藏滚动条。此时,样式的基础条件我已经设置好,要实现滚动只需修改scroll创建的div的margin-top的值即可实现,如:

<div id="scroll" style="width: 1600px; height: 809px; overflow: hidden; position: relative;">
  <div style="width: 1600px; height: 3236px; overflow: hidden; margin-top: -1618px;">
    <div class="box" style="background-color: red; width: 1600px; height: 809px; background-position: initial initial; background-repeat: initial initial;" point="第一个">第一页</div>
    <div class="box" style="background-color: black; width: 1600px; height: 809px; background-position: initial initial; background-repeat: initial initial;" point="第二个">第二页</div>
    <div class="box" style="background-color: blue; width: 1600px; height: 809px; background-position: initial initial; background-repeat: initial initial;" point="第三个">第三页</div>
    <div class="box" style="background-color: green; width: 1600px; height: 809px; background-position: initial initial; background-repeat: initial initial;" point="最后一个">第四页</div>
  </div>
</div>

滑轮滚动

此时,我们就差一个滚动机制了,可以定时滚动,鼠标滑轮事件滚动,点击小焦点切换滚动,这里我说说鼠标滑轮滚屏效果。借助我前两天写的鼠标滑轮插件MWheel轻松的实现滚动效果:

MWheel(parent)
  .addEventListener('down', function (event) {
    if (!lock) {
      lock = true;
      scroll(margin(--num));
    }
  })
  .addEventListener('up', function (event) {  
    if (!lock) {
      lock = true;    
      scroll(margin(++num));
    }
  });

jQuery的animate效果:

var scroll = function (marginTop) {
  $(parent).animate({
    'margin-top' : marginTop    
  }, speed, function(){
    lock = false;
  });
};

至此,一个滚屏效果做好了!

分享

TITLE: 利用MWheel插件基于jQuery animate写的一个滚屏效果

LINK: https://www.qttc.net/377-demo-with-mwheel.html

NOTE: 原创内容,转载请注明出自琼台博客