zoukankan      html  css  js  c++  java
  • jQuery插件开发之windowScroll

          回首望,曾经洋洋得意的代码现在不忍直视。曾经看起来碉堡的效果现在也能稍微弄点出来。社会在往前发展,人也得向前迈进。

          参考于搜狗浏览器4.2版本首页的上下滚动效果。主要实现整个窗口的上下和左右滚动逻辑,还有很多可以拓展的空间。希望大家能多提意见与建议。

      欢迎fork项目:https://github.com/codetker/myWindowScroll, 实现的效果见http://www.梦萦无双.xyz/myWindowScroll/demo/Default.html, 应用见http://wechat.wutnews.net/Web/PhotoWall/(尚在改善中)。

    插件效果:


        实现window的上下滚动,默认绑定键盘上下按钮和鼠标滑轮
        实现window的左右滚动,默认绑定键盘左右按钮
        可附加ul li协助控制滚动
        可修改后附加缓动函数,实现多种效果,详情见缓动函数表 http://easings.net/zh-cn#easeInOutQuad

    html 结构(ZenCoding形式)

      -div.divClass
          -div.toLeftOrTop
          -div.toRightOrBottom
          -div.stageClass*n
    
        -ul.controlUl
          -li.liClass*n

        其中div.toLeftOrTop,div.toRightOrBottom,ul.controlUl可选

    调用方法(详情见demo)(按需设置参数)


    A.vertical

        $(".divClass").windowScroll({
            'choose': 0,             //垂直滚动,默认
            'verticalSpeed': 1,      //控制垂直滚动速度
            'objControlUl': 'ul.controlUl', //控制垂直滚动按钮,默认为null
            'list': '.stageClass',          //垂直滚动的对象
            'crash': true,                  //撞击底部特效
            'toTop': '.toLeftOrTop',        //向上按钮,默认为null
            'toBottom': 'toRightOrBottom',  //向下按钮,默认为null
            'liHover': 'stageSelect'        //设置当前stage的类名
        });

    B.horizontal

        $(".divClass").windowScroll({
            'choose': 1,               //水平滚动
            'horizontalSpeed': 1,      //控制水平滚动速度
            'objControlUl': 'ul.controlUl', //控制水平滚动按钮,默认为null
            'list': '.stageClass',          //水平滚动的对象
            'crash': true,                  //撞击左右特效
            'toTop': '.toLeftOrTop',        //向左按钮,默认为null
            'toBottom': 'toRightOrBottom',  //向右按钮,默认为null
            'liHover': 'stageSelect'        //设置当前page的类名
        });


    运行demo
        最简单的方法为改Default.html中jquery对应script元素的src为本地的jquery(离线)或CDN中的jquery(在线),然后双击Default.html即可
        或者配置myBoxScroll.jquery.json or package.json

    PS:代码之间耦合过强,可重复利用的很多,准备参考学长的建议按模块写个人函数库,通过模块加载注入需要使用的工具函数

          Demo代码如下:

    HTML

    <!doctype html>
    <html>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
    <meta content="" name="keywords" />
    <meta content="" name="description" />
    <meta name="author" content="codetker" />
    <head>
    <title>window对象滚动插件</title>
    <link href="style/reset.css" rel="stylesheet" type="text/css">
    <link href="style/style.css" rel="stylesheet" type="text/css">
    <script type="text/javascript" src="../src/jquery-1.9.1.min.js"></script>
    <script type="text/javascript" src="../dest/jquery.codetker.windowScroll.min.js"></script>
    </head>
    
    <body scroll="no">
        <div class="wrap" style="dispaly:block;">
            <div class="stageControl">
                <ul>
                    <li class="stageSelect">stage1</li>
                    <li>stage2</li>
                    <li>stage3</li>
                    <li>stage4</li>
                    <li>stage5</li>
                </ul>
            </div>
            <div class="toTop">Top</div>
            <div class="toBottom">Bottom</div>
            <div class="stage stage1">
                <div class="pageControl">
                    <ul>
                        <li class="pageSelect">page1</li>
                        <li>page2</li>
                        <li>page3</li>
                    </ul>
                </div>
                <div class="toLeft">Left</div>
                <div class="toRight">Right</div>
                <div class="page page1"></div>
                <div class="page page2"></div>
                <div class="page page3"></div>   
            </div>
            <div class="stage stage2"></div>
            <div class="stage stage3"></div>
            <div class="stage stage4"></div>
            <div class="stage stage5"></div>
        </div>
    <script type="text/javascript">
        $(document).ready(function() {
            $(".wrap").windowScroll({
                'choose': 0,
                'verticalSpeed': 1, 
                'objControlUl': '.wrap .stageControl',
                'list': '.wrap .stage',
                'crash': true,
                'toTop': '.toTop',
                'toBottom': '.toBottom',
                'liHover': 'stageSelect'
            });
            $(".stage1").windowScroll({
                'choose': 1,
                'horizontalSpeed': 1, 
                'objControlUl': '.stage1 .pageControl',
                'list': '.stage1 .page',
                'crash': true,
                'toLeft': '.toLeft',
                'toRight': '.toRight',
                'liHover': 'pageSelect'
            });
        });
    </script>
    </body>
    </html>
    View Code HTML

    CSS

    @charset "utf-8";
    /* CSS Document */
    /* whole */
     body{
        margin  : 0 0;
        padding : 0 0;
        height  : 100%;
        width   : 100%;
        overflow: hidden;;
     }
     .wrap{
        font-family: "微软雅黑","宋体", Times, "Times New Roman", serif;
        font-size  : 14px;
        margin     : 0 0;
        padding    : 0 0;
        height     : 100%;
        width      : 100%;
        overflow   : hidden;
     }
    /* whole end */
    
    /* stage */
     .stage,.page{
        width : 100%;
        height: 100%;
     }
     .stage1{
        background-color: #b9f579;
     }
     .stage2{
        background-color: #d87efa;
     }
     .stage3{
        background-color: #f97171;
     }
     .stage4{
        background-color: #ffc438;
     }
     .stage5{
        background-color: #9ff4d5;
     }
     .stageControl{
        position: fixed;
     }
     .stageControl ul li{
         -webkit-transition-duration: 0.3s;
         -o-transition-duration     : 0.3s;
         transition-duration        : 0.3s;
        /* 兼容低版本IE,add PIE.htc or IE-css3.htc here */
     }
     .stageSelect{
         background-color: #888 !important;
     }
    /* stage end */
    
    /* page */
     .page{
        float: left;
     }
     .page2{
        background-color: #fca172;
     }
     .page3{
        background-color: #b6befc;
     }
     .pageControl{
        position: absolute;
        left    : 200px;
     }
     .pageControl ul li{
        float   : left;
        -webkit-transition-duration: 0.3s;
         -o-transition-duration     : 0.3s;
         transition-duration        : 0.3s;
        /* 兼容低版本IE,add PIE.htc or IE-css3.htc here */
     }
     .pageSelect{
         background-color: #888 !important;
     }
    /* page end */
    
    /* left,right,top,bottom button */
     .toTop,.toBottom{
        position: fixed;
     }
     .toTop{
        top :180px;
     }
     .toBottom{
        top :220px;
     }
     .toLeft,.toRight{
         position: absolute;
     }
     .toLeft{
        left: 600px;
     }
     .toRight{
        left: 720px;
     }
     .toLeft,.toRight,.toTop,.toBottom,.pageControl ul li,.stageControl ul li{
        width : 100px;
        height: 30px;
        line-height: 30px;
        text-align : center;
        cursor: pointer;
        color : #fff;
        background-color: #aaa;
     }
     .toLeft:hover,.toRight:hover,.toTop:hover,.toBottom:hover,.pageControl ul li:hover,.stageControl ul li:hover{
        background-color: #888;
     }
    /* left,right,top,bottom button end */
    View Code CSS

    JavaScript

    /*
     * windowScroll 0.1
     * window滚动插件,上下左右,可选择是否回弹。参考搜狗欢迎页面
     * 兼容等常见浏览器
     * 借鉴搜狗4.2版http://ie.sogou.com/features4.2.html
     */
    ;(function($, window, document, undefined) {
        //定义构造函数
        var WindowObj = function(ele, opt) {
            this.$element = ele;
            this.defaults = {
                'choose': 0,
                'list': null,
                'verticalSpeed': 1,
                'horizontalSpeed': 1,
                'objControlUl': null,
                'toLeft': null,
                'toRight': null,
                'toTop': null,
                'toBottom': null,
                'crash': true,
                'liHover': null
            };
    
            this.options = $.extend({}, this.defaults, opt);
    
        };
    
        //给构造函数添加方法
        WindowObj.prototype = {
    
            //上下滚动的方法
            verticalMove: function() {
                var
                    obj = this.$element,
                    speed = this.options.verticalSpeed,
                    objControl = this.options.objControlUl,
                    controlList = $(objControl).find('li'),
                    windowHeight = $(window).height(),
                    list = this.options.list,
                    listMax = $(list).length,
                    toTop = this.options.toTop,
                    toBottom = this.options.toBottom,
                    crashButton = this.options.crash,
                    liHover = this.options.liHover,
                    stop = 0,
                    stageIndex,
                    windowobject = is_chrome();
    
    
                function setCss() {
                    $(obj).css({
                        'width': $(window).width() + 'px',
                        'height': $(window).height() * listMax + 'px'
                    });
                    $(list).css({
                        'min-width': $(window).width() + 'px',
                        'height': $(window).height() + 'px'
                    });
                }
                setCss();
    
                function markStage() {
                    getIndex();
                    $(controlList).removeClass(liHover);
                    $(controlList).eq(stageIndex).addClass(liHover);
                }
    
                function is_chrome() {
                    var is_ch = navigator.userAgent.toLowerCase().indexOf('chrome') > -1;
                    if (is_ch) {
                        //判断webkit内核,供scrollTop兼容性使用
                        return 'body';
                    } else {
                        //支持IE和FF
                        return 'html';
                    }
                }
    
    
                //阻止默认行为和冒泡
                function stopDefaultAndBubble(e) {
                    e = e || window.event;
                    if (e.preventDefault) {
                        e.preventDefault();
                    }
                    e.returnValue = false;
    
                    if (e.stopPropagation) {
                        e.stopPropagation();
                    }
                    e.cancelBubble = true;
                }
    
                //得到当前的垂直位置
                function getIndex() {
                    stageIndex = Math.round($(window).scrollTop() / windowHeight);
                }
    
                function goTop() {
                    getIndex();
                    scrollStage(windowobject, stageIndex, 1);
                }
    
                function goBottom() {
                    getIndex();
                    scrollStage(windowobject, stageIndex, -1);
                }
    
                //绑定键盘上下按键事件
                $(document).keydown(function(event) {
                    /* 绑定keycode38,即向上按钮 */
                    if (event.keyCode == 38) {
                        goTop();
    
                    } else if (event.keyCode == 40) { //绑定40,即向下按钮
                        goBottom();
                    }
                });
    
                //绑定滑轮功能的函数
                function handle(delta) {
                    getIndex();
                    if (delta < 0) {
                        scrollStage(windowobject, stageIndex, -1); //stageIndex为当前页码
                    } else {
                        scrollStage(windowobject, stageIndex, 1); //stageIndex为当前页码
                    }
    
                }
    
                //判断滑轮,解决兼容性
                function wheel(event) {
                    var delta = 0;
                    if (!event) event = window.event;
                    if (event.wheelDelta) {
                        delta = event.wheelDelta;
                        if (window.opera) delta = -delta;
                    } else if (event.detail) {
                        delta = -event.detail;
                    }
                    if (delta)
                        handle(delta); //调用执行函数
                }
    
                //注册事件
                if (window.addEventListener) {
                    window.addEventListener('DOMMouseScroll', wheel, false);
                }
                window.onmousewheel = document.onmousewheel = wheel;
    
                //绑定鼠标滚轮事件
                $(document).bind('mousedown', function(e) {
                    if (e.which == 2) { //which=2代表鼠标滚轮,即为中键
                        stopDefaultAndBubble(e);
    
                        //bugfix 搜狗浏览器的ie内核只有在定时器触发这个函数才生效
                        setTimeout(function() {
                            stopDefaultAndBubble(e);
                        }, 10);
                    }
                });
    
                //如果有ul li控制按钮
                if (objControl !== null) {
                    $(objControl).delegate('li', 'click', function() {
                        stageIndex = $(this).index();
                        scrollStage(windowobject, stageIndex, 0);
                    });
                }
    
                //如果有上下控制
                $(toTop).click(function() {
                    goTop();
                });
                $(toBottom).click(function() {
                    goBottom();
                });
    
                function scrollStage(obj, stIndex, dir) {
    
                    var
                        sIndex = stIndex,
                        windowobject = obj,
                        direction = 0 || dir,
                        target = windowHeight * sIndex;
    
                    function move() {
                        $(windowobject).animate({
                            'scrollTop': target + 'px'
                        }, 1000 * speed, function() {
                            crash(1, target, 20, 150, -1);
    
                            markStage();
                        });
                    }
    
                    function after_crash(distant, time, termin) {
                        if (distant <= 15 || time > 150) {
                            stop = 1; //停止碰撞
                            $(windowobject).animate({
                                'scrollTop': termin + 'px'
                            }, time, function() {
                                stop = 0;
                            });
                        }
                    }
    
                    //撞击函数
                    function crash(direction, termin, distant, time, aspect) {
                        if (crashButton) {
                            if (!stop) {
                                if (direction === 1) {
                                    direction = 0;
                                    if (aspect === 1) {
                                        $(windowobject).animate({
                                            'scrollTop': '-=' + distant + 'px'
                                        }, time, function() {
                                            crash(direction, termin, distant * 0.6, time, 1);
                                            after_crash(distant, time, termin);
                                        });
                                    } else {
                                        $(windowobject).animate({
                                            'scrollTop': '+=' + distant + 'px'
                                        }, time, function() {
                                            crash(direction, termin, distant * 0.6, time, -1);
                                            after_crash(distant, time, termin);
                                        });
                                    }
    
                                } else if (direction === 0) {
                                    direction = 1;
                                    if (aspect === 1) {
                                        $(windowobject).animate({
                                            'scrollTop': termin + 'px'
                                        }, time, function() {
                                            crash(direction, termin, distant * 0.6, time, 1);
                                            after_crash(distant, time, termin);
                                        });
                                    } else {
                                        $(windowobject).animate({
                                            'scrollTop': termin + 'px'
                                        }, time, function() {
                                            crash(direction, termin, distant * 0.6, time, -1);
                                            after_crash(distant, time, termin);
                                        });
                                    }
    
                                }
                            }
                        }
    
                    }
    
    
                    if (!$(windowobject).is(':animated')) {
    
                        switch (direction) {
                            case 0:
                                if ($(window).scrollTop() > target) {
                                    direction = -1;
                                    move();
                                } else if ($(window).scrollTop() == windowHeight * sIndex) {
                                    direction = 0;
                                    crash(1, target, 20, 150, -1);
                                } else {
                                    direction = 1;
                                    move();
                                }
                                break;
    
                            case 1:
                                if (sIndex === 0) {
                                    crash(1, target, 20, 150, 1);
                                } else {
                                    sIndex -= 1;
                                    target = windowHeight * sIndex;
                                    move();
                                }
                                break;
    
                            case -1:
                                if (sIndex === listMax - 1) {
                                    crash(1, target, 20, 150, -1);
                                } else {
                                    sIndex += 1;
                                    target = windowHeight * sIndex;
                                    move();
                                }
                                break;
    
                            default:
                        }
                    }
                }
    
            },
    
            //左右滚动
            horizontalMove: function() {
                var
                    obj = this.$element,
                    speed = this.options.horizontalSpeed,
                    objControl = this.options.objControlUl,
                    controlList = $(objControl).find('li'),
                    windowWidth = $(window).width(),
                    list = this.options.list,
                    listMax = $(list).length,
                    liHover = this.options.liHover,
                    toLeft = this.options.toLeft,
                    toRight = this.options.toRight,
                    crashButton = this.options.crash,
                    pageIndex;
    
                function setCss() {
                    $(obj).css({
                        'width': windowWidth * listMax + 'px',
                        'height': $(window).height() + 'px'
                    });
                    $(list).css({
                        'width': windowWidth + 'px',
                        'min-height': $(window).height() + 'px'
                    });
                }
                setCss();
    
                function markPage() {
                    getPageIndex();
                    $(controlList).removeClass(liHover);
                    $(controlList).eq(pageIndex).addClass(liHover);
                }
    
                function getPageIndex() {
                    pageIndex = (-1) * Math.round(parseInt($(obj).css('margin-left')) / windowWidth);
                }
    
                function goLeft() {
                    getPageIndex();
                    scrollPage(obj, pageIndex, 1);
                }
    
                function goRight() {
                    getPageIndex();
                    scrollPage(obj, pageIndex, -1);
                }
    
                //绑定键盘左右按键事件
                $(document).keydown(function(event) {
                    //判断event.keyCode为39(即向右按钮)
                    if (event.keyCode === 39) {
                        goRight();
                    }
                    //判断event.keyCode为37(即向左按钮
                    else if (event.keyCode === 37) {
                        goLeft();
                    }
                });
    
                //如果有ul li控制按钮
                if (objControl !== null) {
                    $(objControl).delegate('li', 'click', function() {
                        pageIndex = $(this).index();
                        scrollPage(obj, pageIndex, 0);
                    });
                }
    
                //如有有左右控制按钮
                $(toLeft).click(function() {
                    goLeft();
                });
                $(toRight).click(function() {
                    goRight();
                });
    
                function scrollPage(obj, pageIndex, dir) {
                    var
                        windowobject = obj,
                        direction = 0 || dir,
                        dist = Math.round(parseInt($(obj).css('margin-left'))), 
                        aim;
    
                    function getAim() {
                        aim = pageIndex * windowWidth * (-1);
                    }
    
                    function crash(type) {
                        if (crashButton) {
                            if (type === 'left') {
                                $(windowobject).animate({
                                    'margin-left': '+=' + '50px'
                                }, 500).animate({
                                    'margin-left': '-=' + '100px'
                                }, 500).animate({
                                    'margin-left': '+=' + '50px'
                                }, 500);
                            } else {
                                $(windowobject).animate({
                                    'margin-left': '-=' + '50px'
                                }, 500).animate({
                                    'margin-left': '+=' + '100px'
                                }, 500).animate({
                                    'margin-left': '-=' + '50px'
                                }, 500);
                            }
                        }
    
                    }
    
                    function move() {
                        $(windowobject).animate({
                                'margin-left': aim + 'px' 
                            },
                            1000 * speed,
                            function() {
                                markPage();
                            });
                    }
    
                    if (!$(windowobject).is(':animated')) {
                        switch (direction) {
    
                            case 0:
                                getAim();
                                if (dist !== aim) {
                                    move();
                                } else {
                                    direction = 0;
                                    crash('left');
                                }
                                break;
    
                            case 1:
                                if (pageIndex === 0) {
                                    crash('left');
                                } else {
                                    pageIndex -= 1;
                                    getAim();
                                    move();
                                }
                                break;
    
                            case -1:
                                if (pageIndex === (listMax - 1)) {
                                    crash('right');
                                } else {
                                    pageIndex += 1;
                                    getAim();
                                    move();
                                }
                                break;
    
                            default:
                                break;
                        }
    
                    }
                }
    
            }
        };
    
        //绑定方法到jquery对象原型上
        $.fn.windowScroll = function(options) {
    
            var windowObj = new WindowObj(this, options);
    
            if (windowObj.options.choose === 0) {
                return windowObj.verticalMove();
            } else if (windowObj.options.choose === 1) {
                return windowObj.horizontalMove();
            } else {
                //add some functions
            }
        };
    })(jQuery, window, document);
    View Code JS
  • 相关阅读:
    Oracle 安装报错 [INS-06101] IP address of localhost could not be determined 解决方法输入日志标题
    Linux下安装oracle数据库提示DISPLAY not set. Please set the DISPLAY and try again。
    redhat 关机注销命令详解
    VirtualBox的四种网络连接方式
    修改RedHat的系统显示时间
    insufficient memory to configure kdump(没有足够的内存)解决方法(待验证、待解决)
    xen坑随笔 heartbeat dpkg垃圾数据库清除
    tomcat 监控脚本
    负载均衡随笔
    GIT命令介绍
  • 原文地址:https://www.cnblogs.com/codetker/p/4643815.html
Copyright © 2011-2022 走看看