各位web前端、js达人,为了用户感觉好一点,在一个费时的js循环前在ie里打出“请稍候...”的div,循环完成后再隐藏此div
现在的问题是显示此div后,立即循环,会导致此div实际没机会显示。
只有显示此div后,alter('xxx'),才会真正显示那个div。
好像是delphi里没有application.processmessages;浏览器没机会刷新界面
怎么样才能让浏览器有机会刷新界面?这个问题还不好搜,找不到对应恰当的关键词
使用“改变div 却没有”等,均不是想要的。

解决方案 »

  1.   

    把循环放到setTimeout里让出一段时间来显示div行不行?
      

  2.   

    通过定时器这样就是比较间接了本来的代码是很直接的:显示等候div,循环处理,隐藏div这样的功能应该非常常用的
      

  3.   

    在js中设置dom后
    要等该段脚本执行完了才会刷新页面
    所以直接调用高强度的js会堵塞当前页面的正常显示 调用settimeout不会堵塞当前页面
    (你想想看 你先设置了页面的dom 然后在执行一段脚本 脚本完了才会刷新页面 这个时候你 设置的DOM有什么用)道理就是这样 选择在自己
      

  4.   


    dom?指操作div?
    操作div后,直接调用高强度的js前,能不能用代码告诉浏览器:你现在可以更新界面一下?
    就像 delphi里的Application.ProcessMessages();、VB里的DoEvent();一样
      

  5.   

    据说ajax新版本不再使用定时器了,不知道它采用什么机制感觉这种 耗cpu的工作中,有一个 释放浏览器的cpu用于短暂刷新浏览器界面 的机制,是以前的客户端程序里经常遇到的,也是改善用户体验(长时间等待前有个提示,长时间循环中时不时更新一下进度条)的必要机制
      

  6.   

    首先,你需要用setTimeout延迟执行你的for循环,保证ie下div顺利显示出来,如果你的for循环需要很长时间执行,可能报脚本失控对话框的话你可以用setInterval分批执行,以避免一次执行的代码时间太长
      

  7.   

    如果必须、只能这样实现,代码逻辑就会复杂很多本来的代码是很直接的:显示等候div,循环处理,隐藏div
    以前写delphi程序,都是这样:
    显示等候信息,freecpu,循环处理(一小段循环,更新进度条等提示信息,freecpu),隐藏div
    这样,逻辑很直观
      

  8.   

    dephi是底层语言,javascript只是面向browser的脚本语言,只有有限的api可用,所以没有可比性。javascript没有提供这样的机制。
      

  9.   

    看来是设计js的人没考虑到这种需要
    而这种需要显然是非常普通而且必要的
    没有提供CpuFree()接口,就应该算是设计者的错误了就像t-sql的select只有top n,不支持skip m,导致以前为了分页这么折腾
    也应该算是设计者的错误:没有预计到使用者很需要的功能
      

  10.   

    您试试我这个方法,虽然土了点,应该好用,下面是二个HTML
    1.tmp.html<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=windows-31j">
    <title>Loading</title></head>
    <body>
    Please wait for a moment...
    </body>
    </html>
    2test.html<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=windows-31j">
    <title>Insert title here</title>
    </head>
    <body><script type="text/javascript"><!--newwin=window.open("tmp.html", 'mywindow1', 'width=400, height=300, menubar=no, toolbar=no, scrollbars=yes');//The following code is a simulated for the long loop;
    i=0;
    timerID=null;
    window.onload = function() {
    timerID = setInterval("message()", 1000);
    }
    function message() {
    document.getElementById("result").innerHTML = new Date() + "<br>"+i;
    i++;
    if(i==10){
     clearInterval(timerID);
     newwin.close();
    }
    }
    // --></script>
    <div id="result"></div>
    </body>
    </html>
    你改一下,窗口的样式,应该可以对应您的问题
      

  11.   

    哦,是利用一个弹出的浏览器新窗口来避开原窗口会无响应的问题?!
    倒是一个新的思路。。只是,提示窗口可以改为js自动生成,应该可以不用定时器吧
    另外,如果是多栏(tab)浏览器,新窗口可能效果不好(到另一个tab了)
      

  12.   

    ie6试了一下,代码很简单,效果也还行:弹出有些滞后(应该1-3秒钟左右后才弹出)但是在多栏(tab)浏览器TheWorld2.4,就很糟了:因为在新的tab,而此时浏览器已经假死了,根本看不到提示信息。最后的关闭好像也关闭不了
    var wmsg;
    function showmsg(s)
    {
    wmsg=window.open("", 'mymsgwindow', 'width=400, height=200, menubar=no, toolbar=no, scrollbars=yes');
    wmsg.document.body.innerHTML=s;
    wmsg.title="提示信息";
    }function closemsg()
    {
    wmsg.close();
    }
      

  13.   

    不才还有一个拙见,就是用FRAME同时间加载两个页面,一个用于提示,一个用于计算LOOP。
    最开始载入的时候,把用于计算的页面高度设为0,
    当计算完成后,把表于显示提示的页面的高度设为0,不才虽感觉可以办到,但并没有亲自证实,
    您不防试一试。
      

  14.   

    我刚才自己试了一下,在IE6上没有问题,主要是我只用IE6,不用别的,所以在多TAB上什么效果,我也不清楚,我把它码贴出来,下面是三个HTML1 frameSet.html<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <title>FRAME</title>
    </head>
    <frameset id="main" rows="80%,*">
      <frame src="frameTitle.html" name="frameTitle">
      <frame src="frameLoop.html" name="frameLoop">
      <noframes>
    SORRY.....
      </noframes>
    </frameset>
    </html>
    2 frameTitle.html<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=windows-31j">
    <title>Loading</title></head>
    <body>
    Please wait for a moment...
    </body>
    </html>
     3 frameLoop.html<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=windows-31j">
    <title>Insert title here</title>
    </head>
    <body><script type="text/javascript"><!--//newwin=window.open("tmp.html", 'mywindow1', 'width=400, height=300, menubar=no, toolbar=no, scrollbars=yes');//The following code is the simulated for a long loop;
    i=0;
    timerID=null;
    window.onload = function() {
    timerID = setInterval("message()", 1000);
    }
    function message() {
    document.getElementById("result").innerHTML = new Date() + "<br>"+i;
    i++;
    if(i==10){
     clearInterval(timerID);
     //newwin.close();
     parent.document.getElementById("main").rows="0%,100%"
     
     
    }
    }
    // --></script>
    <div id="result"></div>
    </body>
    </html>
    嗯,应该可以
      

  15.   

    iframe、新窗口,都是离开一个ie的思路,应该都是可以的只是,我的js是在用户点击 不同的按钮 时执行不同的筛选(对已有的table的行按不同的条件进行隐藏)函数
    能把这个js函数分解到iframe里?即使能分解,也是把本来顺序简单直观的代码逻辑打乱了
      

  16.   

    setTimeout 就可以了div.innerHTML = "请稍候";
    setTimeout(function(){
    // 循环;div.innerHTML ="";
    },1);
      

  17.   

    这样是可以,不过,div里的正在加载的动画也是不会变化显示当然,这个不算大问题
      

  18.   

    delphi/vb就很好地解决了这个问题
    js如果要成为应用的编程语言,也应该要吸收它们的解决办法
      

  19.   

    这个取决于宿主环境。
    js可以用于浏览器编程、ASP(JScript服务器端脚本)编程、.NET框架编程(JScript)、windows系统脚本(WSH脚本编程)等等,
    js语言只有ECMA规定的那些语法,但是它的实际操作能力取决于宿主环境。
    浏览器中,js需要通过浏览器提供的API进行操作,浏览器不提供,js本身无能为力。
    正如来势汹汹的html5也是一样,浏览器支持了,js才可以操作,与js本身无关。
    Delphi不也是用的pascal语言么?只是Delphi提供的控件可以提供这些接口让pascal操作而已。
      

  20.   

    当然,目前是仅仅前端的程序才需要这个功能可以js提供一个语法或标准函数名,由浏览器实现
    或者js提供一种通用的对浏览器函数的引用方式,以便js程序可以直接调用浏览器的一些开放给脚本的函数
      

  21.   

    目前浏览器还没开放到那种程度上。
    html5计划开放socket、worker(类似多线程),可是还没推广开,更何况其他的一些呢。
      

  22.   


    那你玩vb去好啦,记住JS 不是为MS而生的!目前各大浏览器JS都是单线程
      

  23.   

    1、delphi/vb解决了这个问题,不是靠多线程
    2、希望js能提供,与ms无关,与 js真正成为方便高效的编程语言 有关
      

  24.   


    与MS无关?那你用FF运行vb试试! 不靠多线程,根本解决不了这个问题。 
    如果浏览器在执行JS 的时候,不同时BLOCK RENDER DOM 的线程, 就不会出现你上述问题。
    但恐怕,带来的问题会远比BLOCK这个线程要大的多。所以这个问题根本不关JS的事,是浏览器JS引擎的问题。
    当然JS本身也是按单线程设计的。VB跟JS根本就是两回事,VB引擎是嵌在IE里的,别家浏览器没有的.
    虽然也叫脚本,但实际上不在一个层面上的。另外,多线程JS引擎也是有的,不过都是是server端JS引擎。
      

  25.   

    你说的vb的vbscript?
    我说的解决这个问题的win32应用的编程语言vb和delphi,它们解决这个问题,靠的是windows的事件处理机制,真的不是多线程。多线程也能解决这个问题,但是编程会复杂。说js不足,当然是指js的解释器的不足了
      

  26.   

    浏览器内部的界面渲染、JavaScript解释分别由两个引擎完成。
    javascript执行过后,才会执行界面渲染的更新,而浏览器又是单线程的,一次只能做一个工作,所以必须在js全部执行完后才能执行渲染。
    Worker的好处在于,把费时的for送到worker(相当于另开一个线程)工作,脱离主线程,这样主线程的js执行完div操作后,可以立即更新界面,而for在另个线程里工作,在完成后通知主线程,再次更新界面,就可以实现你说的效果。
    另外win32程序的编程环境是windows,所有API由windows提供,所有控件只是封装一些操作。
    跟语言的无关,只跟开发环境提供的控件有关。
    浏览器也是同理,这些跟语言本身无关,只跟浏览器提供的API有关。
    建议了解浏览器内部编程原理再讨论吧。
    我承认win32编程的程序员基础知识多数都比WEB开发的程序员扎实,尤其是算法、数据处理方面。
    但是浏览器编程也不同于win32编程,很多地方也是不一样的,一个win32程序员不一定能写好浏览器编程。
    解释性语言也不同于编译型语言,也就无需讨论优劣对比了,这些都是徒劳。
    能做的只是在充分了解两种语言后,将其中一种语言的编程思想利用到另一种里,而这个不需要改变另一种语言的规则或是其他。
      

  27.   

    口水肯定是口水了,因为这里的讨论不会影响到浏览器的开发者浏览器内部的界面渲染、JavaScript解释分别由两个引擎完成
    这个没问题,但是2个引擎之间最好能增加一些通知机制如果改进(如上面说的通知机制 或 js的暂时“释放cpu”的特性)能方便开发,
    那么浏览器的开发者就应该吸取
    虽然浏览器的开发者普遍比js的开发者“高级”
    就像ms的t-sql,以前只有top n而没有skip m,给sql使用者带来很大的麻烦(比如分页)
      

  28.   


    本来就是这样的:好的程序员就是自己的掘墓人!
    一直挨骂的微软也是类似,让电脑易用了,价格也就下来了
    让系统的开发、维护容易了,所以vc/vb/c#/asp的程序员、mssql的管理员的薪水也低