zoukankan      html  css  js  c++  java
  • 代理orientationchange事件回调函数

    我们在开发Web App时,通常会遇到一些兼容性问题,orientationchange事件就是其中之一。严格来说,并不是orientationchange有兼容问题,而是触发orientationchange事件回调函数时有兼容问题(很绕口啊)。具体表现在回调函数中获取window.innerWidth与window.innerHeight属性上的差异。

    在safari下,对orientationchange支持很好,当orientationchange触发回调时,使用window.innerWidth能或立刻获取到最新的屏幕高宽。

    而在Android浏览器下,需要延迟一定的时间,才能获取到正确的屏幕高宽。如果触发回调函数时,立刻使用window.innerWidth,那么,只能取到方向未改变之前的高宽,在Android下使用下面的一个简单试验可以得出结果:

    <script type="text/javascript">
    alert(window.innerWidth); // 默认竖屏状态,得到屏宽480px;
    window.addEventListener('orientationchange', function() {
        alert(window.innerWidth); // 触发orientationchange回调时,得到屏宽还是480px;
        setTimeout(function() {
            alert(window.innerWidth); // 延迟300ms,才能得到正确屏宽960px
        }, 300);
    }, false);
    </script>

    对于orientationchange的兼容问题,使用proxy函数是很好的一种方法,下面是我给出的一种解决方案:

    <script type="text/javascript">
    //我的代码库默认依赖了Zepto框架,所以会有Zepto的接口
    function createOrientationChangeProxy(fn, scope) {
        return function() {
            /*
             * 如果是Android浏览器,我们设想一种场景,手机从 竖屏-横屏-竖屏-横屏 时,
             * 这个过程经历了四次切换,但实际我们只需要处理最后一次切横屏的结果,
             * 那么,延迟300ms执行回调函数,可以在最开始时清除冗余的orientationChangedTimeout。
             */
            clearTimeout(scope.orientationChangedTimeout);
            var args = Array.prototype.slice.call(arguments, 0);
            scope.orientationChangedTimeout = setTimeout($.proxy(function() {
                /*
                 * 再设想一种场景,手机从 竖屏-横屏-竖屏 时,在这个过程,系统并未改变任何东西,
                 * 将lastOrientation保存下来,能有效的避免垃圾操作产生的回调处理
                 */
                var ori = window.orientation;
                if (ori != scope.lastOrientation) {
                    fn.apply(scope, args); // 这里才是真正执行回调函数
                }
                scope.lastOrientation = ori;
            }, scope), $.os.android ? 500 : 0);
        };
    }
    
    window.addEventListener('orientationchange', createOrientationChangeProxy(function() {
        alert(window.innerWidth); // 无论是Safari还是Android浏览器都能正确的输出屏宽
    }, window), false);
    </script>
    原创文章,转载请注明出处http://www.cnblogs.com/zhangdaiping
  • 相关阅读:
    关于数据库索引,必须掌握的知识点
    Java基础知识面试题(最详细版)
    基于WinForm制作的用户名密码存储器
    DataGridView点击列名自动排序
    WebRequest.Create(url)无效的URI:无效端口指定的URL时
    knockout 数据绑定,同一个页面table位置加载两个不同的表格数据
    pipeline管道初体验
    Socket,长连接,消息推送,消息提醒,未读消息提醒,消息通知,未读消息通知
    搭建SVN服务器
    C#解决jsonp跨域问题jsonp跨域配置
  • 原文地址:https://www.cnblogs.com/zhangdaiping/p/3055137.html
Copyright © 2011-2022 走看看