Koodini palauttaa unixtimestampin tietokannasta. Aika kuvaa ajankohtaa, jolloin käyttäjän istunto vanhenee. Javascriptillä voin tarkistaa, onko aika oikea kun vertaan time-muuttujaa jossa on unixtime PHP:llä palautettuna ja getTime() / 1000. Jos muuttujassa jäljellä
on aikaero noitten kahden välillä, niin miten voi paluttaa käyttäjälle kyseisen sekuntiajan tunneissa, minuuteissa ja sekunneissa kaikista järkivimmillä (Huh, nyt suomenkielentaitoa kaivattaisiin) tavalla?
Nykyinen toteutukseni, joka ei palauta laskuri-elementtiin yhtään mitään:
function paivita() { var rtime = <?php echo $time; ?>; var unixtime = getTime() / 1000; var ero = rtime - unixtime; var laskuri = document.getElementById("laskuri"); laskuri.innerHTML = "<a href=\"?logout\">Kirjaudu ulos (" + ero + ")</a>"; if(ero === 0) { document.location = "?logout"; } else { setTimeout(paivita, 1000); } }
Käytä jakojäännöstä apuna.
<script type="text/javascript"> var aika = 3600; var tunnit, minuutit, sekunnit; tunnit = Math.floor(aika / 3600); minuutit = Math.floor((aika % 3600) / 60); sekunnit = Math.floor((aika % 3600) % 60); alert(tunnit+"h "+minuutit+"min "+sekunnit+"s"); </script>
Kiitos! En kuitenkaan saa tulostettua aikaa näytölle. Missä vika? En ymmärrä mikä meni väärin:
laskuri = document.getElementById("laskuri"); function paivita() { aika = <?php echo $time; ?>; // sekunnin päästä aika--; var tunnit, minuutit, sekunnit; tunnit = Math.floor(aika / 3600); minuutit = Math.floor((aika % 3600) / 60); sekunnit = Math.floor((aika % 3600) % 60); laskuri.innerHTML = "<a href=\"?logout\">Kirjaudu ulos (" + tunnit + ":" + minuutit + ":" + sekunnit + ")</a>"; if(aika === 0) { document.location = "?logout"; } else { setTimeout(paivita, 1000); } }
Varmaankin vikana muuttujan näkyvyysalue; muuttuja laskuri
ei näy tuolla funktion sisällä. Tietääkseni sen pitäisi toimia kuin globaali, mutta jostakin ihmeen syystä mulla ei ainakaan ole toiminut.
Kannattaa varmaan muuten tehdä tuohon systeemiisi myös PHP:n puolella pakollinen kirjauttaminen ulos. Jos käyttäjällä ei ole javascriptiä päällä niin tuohan ei silloin toimisi :P
PHP:ssä on tämä toiminto myös, mutta sen takia haluan Javascriptin mukaan koska pelkällä PHP:llä se kirjautuu ulos vasta sivunlatauksen yhteydessä.
Muokkaus. var laskurin eteen ja funktioon niin alkoi toimimaan. Miten saisin miinustettua joka kierroksella tuota aika-muuttujaa (aika--)? Ei onnistunut noin, joten aika seisoo.
Muokkaus. PHP kyllä osaa antaa oikean ajan aina sivun latauduttuessa: $time = (strtotime("2010-02-16 09:35:32pm") - time())
En ole testannut mutta toimiskos tämmönen. Eli kutsut funktiota ekalla kerralla ilman arvoja.
function paivita(aika = <?php echo $time; ?>) { laskuri = document.getElementById("laskuri"); var tunnit, minuutit, sekunnit; tunnit = Math.floor(aika / 3600); minuutit = Math.floor((aika % 3600) / 60); sekunnit = Math.floor((aika % 3600) % 60); laskuri.innerHTML = "<a href=\"?logout\">Kirjaudu ulos (" + tunnit + ":" + minuutit + ":" + sekunnit + ")</a>"; if(aika === 0) { document.location = "?logout"; } else { setTimeout("paivita("+(aika-1)+")", 1000); } }
Ei auttanut yhtään.
Hmm, näköjään javascriptissä ei ollut noita funktioille annettujen muuttujien oletusarvoja.
Sovellappa tätä pätkää:
<p id="test">0</p> <script type="text/javascript"> function asd(aika){ if(!aika) aika = 3600; document.getElementById('test').innerHTML = aika; setTimeout("asd("+(aika-1)+")", 1000); } asd(); </script>
Kai muistit tarkistaa Firefoxin virhekonsolista, menikö jotain pieleen?
var loppuaika = 1000 * <?php echo $time; ?>; var paivita_timeout; function paivita() { var jaljella = Math.max(0, loppuaika - (new Date()).getTime()); var sekunnit = Math.floor(jaljella / 1000); var minuutit = Math.floor(sekunnit / 60); var tunnit = Math.floor(minuutit / 60); minuutit %= 60; sekunnit %= 60; // DEBUG: alert(tunnit + ":" + minuutit + ":" + sekunnit); // document.XYZ.innerHTML = ...; if (!jaljella) { document.location.href = "?logout"; } else { paivita_timeout = setTimeout(paivita, 1000); } }
var laskuri = 55; function showLaskuri() { alert(laskuri); } // toimii laskuri = 55; function showLaskuri() { alert(laskuri); } // ei toimi
Ainakin greasemonkeyssä menee noin. Eli var alussa = global muuttuja
Short Php kirjoitti:
Ainakin greasemonkeyssä menee noin. Eli var alussa = global muuttuja
Globaalissa nimitilassa on ihan sama onko var
vai ei, muuttujia ei tarvitse esitellä vaan ne ovat automaattisesti globaaleja (mitä muutakaan?). Funktioiden sisällä taas var
esittelee paikallisen muuttujan ja kaikki mitä ei esitellä ovat globaaleja, eli siellä var
-sanalla on tärkeä merkitys.
Näin ainakin tavallisessa JavaScriptissä, ja pikaisen testin perusteella greasemonkeyssa toimii ihan samalla tavalla. Olet luultavasti sählännyt jotain epämääräistä ja päätit syyttää kieltä/greasemonkeya kun ei toimi.
Kiitos Metabolix. En kuitenkaan saanut sitä toimimaan...
var loppuaika = <?php echo $time; ?>; var paivita_timeout; function paivita() { var jaljella = Math.max(0, loppuaika - (new Date()).getTime()); document.write(jaljella + " " + loppuaika); var sekunnit = Math.floor(jaljella / 1000); var minuutit = Math.floor(sekunnit / 60); var tunnit = Math.floor(minuutit / 60); minuutit %= 60; sekunnit %= 60; document.getElementById("laskuri_tunnit").firstChild.nodeValue = ("0" + tunnit).replace(/.*(..)$/, "$1"); document.getElementById("laskuri_minuutit").firstChild.nodeValue = ("0" + minuutit).replace(/.*(..)$/, "$1"); document.getElementById("laskuri_sekunnit").firstChild.nodeValue = ("0" + sekunnit).replace(/.*(..)$/, "$1"); if (!jaljella) { document.location.href = "?logout"; } else { paivita_timeout = setTimeout(paivita, 1000); } } window.onload = paivita; window.onunload = function() { clearTimeout(paivita_timeout); paivita_timeout = null; }
Tuloksena jaljella-muuttuja on aina 0 ja kirjautuu ulos heti.
Miksi poistit tuhannella kertomisen? Tietenkin millisekunteja on kulunut paljon enemmän kuin sekunteja.
Ooops, hupsista. Kiitos, kun korjasit. Kuitenkin tämä ohjaa selaimen heti toiseen osoitteeseen.
Kuten esimerkkisivultani näet, laskuri toimii aivan oikein, kunhan alkuajaksi sijoitetaan jotain järkevää. Oletko nyt varma, että $time sisältää istunnon loppumisajankohdan eikä esimerkiksi kirjautumishetkeä tai nykyistä aikaa?
No niin. Miksi ihmeessä siinä on ajan muutos eikä oikeaa UNIX-aikaleimaa? Joko otat tuosta time()-vähennyksen pois tai lisäät JS:n puolella uudestaan siihen arvon (new Data()).getTime(). Jälkimmäinen vaihtoehto on sikäli parempi, että käyttäjän koneen kellon virheellinen aika ei haittaa. Toisaalta jos kello on oikeassa, ensimmäinen tapa antaa tarkemman laskurin, koska siinä sivun lataamiseen kulunut aika ei vaikuta.
Empähän tullut ajatelleeksi, mutta kiitos. "Ajan muutos" siinä on siksi, kun tietokannassa ei ole vielä tietoa tästä ajasta.
Aihe on jo aika vanha, joten et voi enää vastata siihen.