XMLHttpRequest + setTimeout nem működik IE7 alatt
2008-11-14T19:07:19+01:00
2008-11-19T04:03:35+01:00
2022-08-12T13:50:32+02:00
matyilecso
Sziasztok!

Írtam egy rövid scriptet ami előre megadott időközönként frissíti a kijelölt div-ek tartalmát xmlHttpRequest segítségével. A kód a következő:


var AjaxLoader={ xmlHttp: new Array(), sendRequest : function(i){ if(AjaxLoader.xmlHttp[i]!=null){ var url,d=new Date(); if(AjaxLoader.strpos(AjaxLoader.xmlHttp[i].url,'?')) url=AjaxLoader.xmlHttp[i].url+'&rnd='+d.getTime(); else url=AjaxLoader.xmlHttp[i].url+'?rnd='+d.getTime(); AjaxLoader.xmlHttp[i].onreadystatechange=function(){ if(this.readyState==4){ document.getElementById(this.contID).innerHTML=this.responseText; if(this.rate>-1) this.timeout=setTimeout('AjaxLoader.refresh('+this.idx+')',this.rate); } } AjaxLoader.xmlHttp[i].open("GET",url); AjaxLoader.xmlHttp[i].send(null); } }, refresh : function(i){ this.sendRequest(i); }, add : function(url,contID,rate){ if(url instanceof Array){ if(url.length!=contID.length){ alert('error!'); return false; } for(var i in url) this.push(url[i],contID[i],rate[i]); } else this.push(url,contID,rate); }, push : function(url,contID,rate){ var idx=this.xmlHttp.length; this.xmlHttp[idx]=this.getXmlHttpObject(); this.xmlHttp[idx].idx=idx; this.xmlHttp[idx].url=url; this.xmlHttp[idx].contID=contID; this.xmlHttp[idx].rate=rate; if(rate>-1) this.xmlHttp[idx].timeout=setTimeout('AjaxLoader.sendRequest('+idx+')',rate); else this.sendRequest(idx); }, getXmlHttpObject : function(){ var xmlHttp=null; try { xmlHttp=new XMLHttpRequest(); } catch (e) { try { xmlHttp=new ActiveXObject("Msxml2.XMLHTTP"); } catch (e) { xmlHttp=new ActiveXObject("Microsoft.XMLHTTP"); } } return xmlHttp; }, strpos : function( haystack, needle, offset){ var i = haystack.indexOf( needle, offset ); return i >= 0 ? i : false; } }

Ha az oldalon elhelyezem a következő sort:

AjaxLoader.add(['inc/echo.php','inc/echo.php?p=1','inc/echo.php?p=2'],['id1','id2','id3'],[-1,1000,2000]);

akkor a három url az adott id-vel rendelkező elembe betöltődik. Az utolsó tömb a frissítési gyakoriságot jelenti, a -1 esetén csak egyszer töltődik be a tartalom.

Nem tudok rájönni arra, hogy mért nem működik IE7 alatt a script (minden url csak egyszer töltődik be), pedig FF3-mal nincs fennakadás.

Tanácsaitokat előre is köszönöm!
matyilecso
Mutasd a teljes hozzászólást!

  • Biztos jó ennyi idx?

    this.xmlHttp[idx].idx=idx;

    de ha javítom, akkor is az alert(2) után eldobja magát az ie6:
    var idx0=this.xmlHttp.length; alert("*"+idx0); this.xmlHttp[idx0]=this.getXmlHttpObject(); alert(2) this.xmlHttp[idx0].idx=idx0; alert(3) this.xmlHttp[idx0].url=url; alert(4)
    Mutasd a teljes hozzászólást!
  • for(var i in url) this.push(url[i],contID[i],rate[i]);
    ez így nem fog menni, ha tömböt így iterálsz javascriptben, akkor nagyon elqrtad. bármikor, ha írsz az Array.prototype-ba saját függvényt, azt is beleveszi az iterálásba, szóval helyette

    for(var i=0; i<url.length; i++) this.push(url[i],contID[i],rate[i]);

    a másik hiba, hogy a hibakezelés aboszult hiányzik a getxmlhttprequestnél.. ha egyik típusú objectet sem tudja létrehozni, akkor legalább egy alertet dobjál, ha meg megjön a response, akkor a statust is ellenőrizd, hogy 200 e.

    nemtom, hogy ie7 hogyan reagál, ha beleírsz az activexobjectjébe. nem minden ilyen objectnek van meg a getes és setes felülete, bár az ilyen hibák inkább domban jellemzőek, de ie esetén ki tudja....

    szóval ahelyett, hogy a "gyári" objectbe írnál jobb megoldás az ha, hogy burkoló objecteket hozol létre a requestek körül, és azokban tárolod az adatokat (legalábbis én így csinálom)

    erre átírva mondjuk a sendRequest függvényed:
    sendRequest : function(i) { var container=this.xmlHttp[i]; var request=container.request; if(!container) { return; } var url=container.url+(container.url.indexOf('?')!=-1?'&':'?')+'rnd='+((new Date()).getTime()); request.onreadystatechange=function() { if(this.readyState!=4) { return; } if (this.status!=200) { alert("gond"); return; } document.getElementById(container.contID).innerHTML=this.responseText; if(container.rate>-1) { container.timeout=setTimeout('AjaxLoader.refresh('+container.idx+')',container.rate); } } request.open("GET",url,true); request.send(null); },

    viszont ha jól emlékszem, akkor nekem gondom volt a thissel az onreadystate részben, mert asszem valamiért window objectet kaptam helyette (lehet pont ie7 alatt, már nemtom), szóval helyette request-et is lehet írni ilyen formán

    a sokadik dolog meg, hogy nálad nincs kint az async flag a request.open-nél, és szerintem ez a gond, mert ie7 nem rakja automatán true-ra, ha jól emlékszem, firefox viszont igen
    Mutasd a teljes hozzászólást!
abcd