js异步状态监控
说明:写这篇文章,是希望被吐槽的。
一、背景
在做报表页面的时候,页面上有很多的异步加载,而设计的loading是个全局的,一个页面就有一个。
控制loading什么时候出现,什么时候消失,要实时的知道页面上异步加载的东西是否执行完毕,只有所有的异步都加载完,loading才能停止。
并且,如果用户操作了页面,某个局部又要开始加载,loading要被通知到,执行loading效果。
问题的难点有两个:
1.怎么知道所有的异步都加载完闭了呢?
2.如何通知loading?
二、思路
1.思路一
设计一个外部状态map,异步执行完毕,就修改外部变量的值。开一个计时器,不断的这个map,如果全部加载完毕,就停止loading。
// 状态集合 var statusMap = { "异步1": false, "异步2": false // ... }; // 计时器不断检查状态 setInterval(function () { // 检查statusMap if (isReady(statusMap)) { // show loading } else { // hide loading } }, 1000); //异步 $.ajax({ //... success: function () { statusMap["异步1"] = true; } });
这个方案虽然能解决问题,但是太不够优雅,呵呵呵呵......
2.思路二
使用promise或者jQuery的deferred(@上位者的怜悯 提供的建议)。
$.when(异步1,异步2).done(function(){ // show loading }).fail(function(){ // hide loading });
这个方案有个弊端,一旦异步加载完毕,不能修改promise的状态了,因此不适合这个场景。
3.思路三
自己造轮子基于事件监听的,一个状态改变,就扫一遍所有监听的对象,最后再根据用状态,回调对应的函数
三、思路三实现
(function (win) { var watch = function () { var that = this; // arr if (arguments.length == 1 && Object.prototype.toString.call(arguments[0]) === "[object Array]") { that.watchArr = arguments[0]; } else { that.watchArr = Array.prototype.slice.call(arguments); } that.watchArr.forEach(function (fairy) { fairy.watch = that; }); that.isReady = true; return that; }; watch.prototype = { ready: function (callback) { this.readyHandler = callback; this.check(); return this; }, unready: function (callback) { this.unReadyHandler = callback; this.check(); return this; }, add: function (fairy, check) { this.watchArr.push(fairy); if (check === undefined || check === true) { this.check(); } return this; }, check: function () { var nowIsReady = this.watchArr.every(function (fairy) { return fairy.isReady; }); if (nowIsReady != this.isReady) { if (nowIsReady) { if (this.readyHandler) { this.readyHandler.call(); this.isReady = true; } } else { if (this.unReadyHandler) { this.unReadyHandler.call(); this.isReady = false; } } } }, setIsReadyById: function (id, isReady, check) { var index = this.watchArr.indexOf(function (fairy) { fairy.id = id; }); this.watchArr[index].isReady = isReady; if (check === undefined || check === true) { this.check(); } }, setIsReadyAll: function (isReady, check) { this.watchArr.forEach(function (fairy) { fairy.isReady = isReady; }); if (check === undefined || check === true) { this.check(); } } }; var fairy = function (isReady) { this.id = new Date().getTime(); this.isReady = isReady || false; }; fairy.prototype = { toReady: function () { this.isReady = true; this.watch.check(); }, toUnReady: function () { this.isReady = false; this.watch.check(); } }; win.Watch = watch; win.Fairy = fairy; })(window);
// 用例 var loader = new Loader(); var listFairy = new Fairy(); var chartFairy = new Fairy(); var watch = new Watch(listFairy, chartFairy); watch.ready(function () { loader.stop(); }).unready(function () { loader.start(); }); //异步 $.ajax({ //... success: function () { listFairy.toReady(); } });
纳尼,说好的事件呢,哪里去了。
好吧,吐槽点来了,实现的过程中,发现其实没必要用事件。
实现到最后,发现它其实就是一个变相的思路一。
the end 未完不续 ...
js异步状态监控的更多相关文章
- JS魔法堂:深究JS异步编程模型
前言 上周5在公司作了关于JS异步编程模型的技术分享,可能是内容太干的缘故吧,最后从大家的表情看出"这条粉肠到底在说啥?"的结果:(下面是PPT的讲义,具体的PPT和示例代码在h ...
- js异步编程
前言 以一个煮饭的例子开始,例如有三件事,A是买菜.B是买肉.C是洗米,最终的结果是为了煮一餐饭.为了最后一餐饭,可以三件事一起做,也可以轮流做,也可能C需要最后做(等A.B做完),这三件事是相关的, ...
- 深究JS异步编程模型
前言 上周5在公司作了关于JS异步编程模型的技术分享,可能是内容太干的缘故吧,最后从大家的表情看出"这条粉肠到底在说啥?"的结果:(下面是PPT的讲义,具体的PPT和示例代码在h ...
- JS异步加载的三种方式
js加载的缺点:加载工具方法没必要阻塞文档,过得js加载会影响页面效率,一旦网速不好,那么整个网站将等待js加载而不进行后续渲染等工作. 有些工具方法需要按需加载,用到再加载,不用不加载,. 默认正常 ...
- 转:web前端面试题合集 (Javascript相关)(js异步加载详解)
1. HTTP协议的状态消息都有哪些? 1**:请求收到,继续处理2**:操作成功收到,分析.接受3**:完成此请求必须进一步处理4**:请求包含一个错误语法或不能完成5**:服务器执行一个完全有效请 ...
- JS异步加载的三种方案
js加载的缺点:加载工具方法没必要阻塞文档,个别js加载会影响页面效率,一旦网速不好,那么整个网站将等待js加载而不进行后续渲染等工作. 有些工具方法需要按需加载,用到再加载,不用不加载. 一.def ...
- JS 异步系列 —— Promise 札记
Promise 研究 Promise 的动机大体有以下几点: 对其 api 的不熟悉以及对实现机制的好奇; 很多库(比如 fetch)是基于 Promise 封装的,那么要了解这些库的前置条件得先熟悉 ...
- 深入理解node.js异步编程:基础篇
###[本文是基础内容,大神请绕道,才疏学浅,难免纰漏,请各位轻喷] ##1. 概述 目前开源社区最火热的技术当属Node.js莫属了,作为使用Javascript为主要开发语言的服务器端编程技术和平 ...
- 前端分享----JS异步编程+ES6箭头函数
前端分享----JS异步编程+ES6箭头函数 ##概述Javascript语言的执行环境是"单线程"(single thread).所谓"单线程",就是指一次只 ...
随机推荐
- User Word Automation Services and Open XML SDK to generate word files in SharePoint2010
SharePoint 2010 has established a new service called "Word Automation Services" to operate ...
- crontab执行不生效-【问题篇】
背景:shell脚本每隔两分钟从数据库取数据库放到脚本所在目录,做好计划任务发现不生效. 解决:脚本中文件路径问题 测试:在/data/test目录下写的脚本,直接在本目录touch以分钟结尾的文件. ...
- 烂泥:nginx同时支持asp.net与php
本文由秀依林枫提供友情赞助,首发于烂泥行天下. 经过两天的实验,终于让nginx同时支持asp.net与php了.下面就把具体的配置过程记录如下. 注意:本次实验OS:centos6 64bit. 尽 ...
- head,tail
测试文件headtail 1 L 2 L 3 L 4 L 5 L 6 L 7 L 8 L 9 L 10 L 11 L 12 L 13 L 14 L 15 L 16 L 17 L 18 L 19 L h ...
- Linux 解压缩命令
gzip 文件 压缩文件 gzip -d 文件 解压文件 zcat 查看以结尾为zip 文件 bzip2 压缩文件 bzip2 -d 文件 解压文件 bzcat 查看以结尾为zip2 文件 zip ...
- linux基础-基本命令的讲解(1-7单元)
基本命令的讲解 主要内容介绍 1.LINUX操作系统安装及初始化配置(熟悉):2.LINUX操作系统目录组成结构及文件级增删改查操作(重点):3.LINUX操作系统用户.权限管理(重点):4.开源软件 ...
- Ubuntu13.04安装历险记--Mono,Nginx,Asp.Net一个都不能少
----Ubuntu13.04安装历险记--新人新手新作------------------------------------------------- 注:以下操作均省略权限获取操作,如有需要,请 ...
- Android中ListView错位布局实现(无聊向)
由于某些原因,需要个错位的页面,在网上找不到好的例子,试着动手写了写. 不考虑配色的完成图如下: 首先考虑的是,listview每一行左右都有可能缩进. 先假设一行的布局就是ImageView,Tex ...
- 在ASP.NET MVC中使用Unity进行依赖注入的三种方式
在ASP.NET MVC4中,为了在解开Controller和Model的耦合,我们通常需要在Controller激活系统中引入IoC,用于处理用户请求的 Controller,让Controller ...
- 新版Microsoft Azure Web管理控制台 - Microsoft Azure New Portal - (3)
之前我们多次提到过Resource Manager,也知道Resource Manager是Microsoft Azure提供的一种新型资源管理模式.在Service Management模式(Cla ...