JS 非图片动态loading效果实现代码

  代码如下:

  首先实现该功能的js对象LoadingMsg:

  

复制代码 代码如下:

  var Class = {

  create: function() {

  return function() { this.init.apply(this,arguments); }

  }

  }

  var LoadingMsg = Class.create();

  LoadingMsg.prototype = {

  init: function(spanId, spanMsg) {

  this.intervalID = -10000;

  this.spanId = spanId;

  this.spanMsg = spanMsg;

  this.timespan = 1000;

  this.pointNum = 3;

  this.initPointMsg = "...";

  },

  Loading: function() {

  var maxLength = this.spanMsg.length + this.pointNum;

  var currentSpanMsg = document.getElementById(this.spanId).innerHTML;

  if (currentSpanMsg.length < maxLength) {

  document.getElementById(this.spanId).innerHTML += ".";

  }

  else {

  document.getElementById(this.spanId).innerHTML = this.spanMsg;

  }

  },

  Start: function() {

  document.getElementById(this.spanId).innerHTML = this.spanMsg + this.initPointMsg;

  var callObj = this;

  this.intervalID = setInterval(function() { callObj.Loading(); }, this.timespan);

  },

  End: function() {

  document.getElementById(this.spanId).innerHTML = "";

  clearInterval(this.intervalID);

  }

  }

  关键点:

  如果把

  

复制代码 代码如下:

  var callObj = this;

  this.intervalID = setInterval(function() { callObj.Loading(); }, this.timespan);

  写成:

  

复制代码 代码如下:

  this.intervalID = setInterval(this.Loading, this.timespan);

  在执行Loading方法时则会报找不到this.spanMsg的错误。

  因为在setInterval里的第一个参数里的this是windows对象,而不是LoadingMsg对象。windows.setInterval嘛。

  应用该方法:

  

复制代码 代码如下:

  <body>

  <input type="button" value="Start" onclick="javascript:StartLoading();" />

  <span id="spanId" style="color:Red"></span>

  <br />

  <input type="button" value="End" onclick="javascript:EndLoading();" />

  <br /><br />

  <script type="text/javascript">

  var loadingMsgObj = new LoadingMsg("spanId","loading");

  function StartLoading() {

  loadingMsgObj.Start();

  }

  function EndLoading() {

  loadingMsgObj.End();

  }

  </script>

  </body>

  来源于prototype.js里经典创建Js对象的

  

复制代码 代码如下:

  var Class = {

  create: function() {

  return function() { this.init.apply(this,arguments); }

  }

  }

  var LoadingMsg = Class.create();

  在Class.create()的时候做了2件事,1个是创建了LoadingMsg的对象,即var LoadingMsg = function() {};

  另外一件事就是调用LoadingMsg的init方法,初始化LoadingMsg里的静态私有变量,相当于c#里的构造函数作用。

  如果你觉得这很装逼的话,如果你更喜欢简单朴实的女孩子的话,也可以改写LoadingMsg对象:

  

复制代码 代码如下:

  var LoadingMsg = function() { };

  LoadingMsg.prototype = {

  init: function(spanId, spanMsg) {

  this.intervalID = -10000;

  this.spanId = spanId;

  this.spanMsg = spanMsg;

  this.timespan = 1000;

  this.pointNum = 3;

  this.initPointMsg = "...";

  },

  Loading: function() {

  var maxLength = this.spanMsg.length + this.pointNum;

  var currentSpanMsg = document.getElementById(this.spanId).innerHTML;

  if (currentSpanMsg.length < maxLength) {

  document.getElementById(this.spanId).innerHTML += ".";

  }

  else {

  document.getElementById(this.spanId).innerHTML = this.spanMsg;

  }

  },

  Start: function(spanId, spanMsg) {

  this.init(spanId, spanMsg);

  document.getElementById(this.spanId).innerHTML = this.spanMsg + this.initPointMsg;

  var callObj = this;

  this.intervalID = setInterval(function() { callObj.Loading(); }, this.timespan);

  },

  End: function() {

  document.getElementById(this.spanId).innerHTML = "";

  clearInterval(this.intervalID);

  }

  }

  所不同的是把init的过程调到Start时执行,因此调用的时候也就变成了

  

复制代码 代码如下:

   var loadingMsgObj = new LoadingMsg();

  function StartLoading() {

  loadingMsgObj.Start("spanId", "loading");

  }

  从面向对象的习惯上来说,我个人还是倾向第一种写法,在实例化对象的时候即传入参数,而不是执行对象方法的时候传入参数。

  另外关于setInterval方法传参数时,如果参数是简单的string,可以

  setInterval("DisplayXYZ('xyz')",1000);

  如果参数是对象,

  则可以setInterval(function(){DisplayXYZ(obj);},1000);

  LoadingMsg还是主要用在Ajax中,应用于执行时间可能较长的场景,在发送请求后loadingMsgObj.Start(),在成功获取响应时loadingMsgObj.End()。