Innholdsoversikt for programutvikling

Hva er en Timer?

En Timer har evne til periodisk å generere hendelser av type ActionEvent, eller til å generere én slik hendelse etter at en bestemt tid har gått. En Timer kan derfor brukes som hjelpemiddel til å få utført en oppgave gjentatte ganger, eller én gang etter at det først har gått en bestemt tid. Det finnes flere eksempler på at dette kan være aktuelt i forbindelse med GUI-programmering. For eksempel ønsker vi at en markør skal blinke på skjermen med en bestemt frekvens. Eller vi ønsker at en tooltip-tekst skal vises en bestemt tid dersom musepekeren har stått stille over en komponent et visst tidsrom. Et annet eksempel er programmering av animasjoner: En serie av bilder skal vises på skjermen med en bestemt frekvens, slik at det gir illusjon om bevegelse. I alle de nevnte eksempler vil en Timer være et nyttig hjelpemiddel for å få til det vi ønsker.

To typer Timere

I javas klassebibliotek finnes det to Timer-klasser: javax.swing.Timer og java.util.Timer. Den første av disse anbefales brukt for GUI-relaterte oppgaver. Alle eksemplene nevnt ovenfor er av denne typen. Det er bare denne Timer-klassen som vil bli omtalt videre i dette notatet. For å presisere hvilken det gjelder, skal vi kalle den for en swing-Timer. Den andre typen Timer er mer generell og har flere egenskaper. Den som ønsker nærmere omtale av den, samt anbefalinger om når det bør brukes den ene eller den andre typen Timer, vises til notatet på adressen http://java.sun.com/products/jfc/tsc/articles/timer/.

Hvordan bruke swing-Timere

Et Timer-objekt genererer gjentatte ganger hendelser av type ActionEvent, hver gang etter en bestemt forsinkelse. Dette kjører i en egen programtråd - den samme programtråd som tar hånd om brukergenererte hendelser og oppfrisking av skjermbildet. På engelsk kalles denne programtråden the event-dispatching thread. Til Timer-objektet kan vi knytte et eller flere lytteobjekter som fanger opp hendelsene generert av Timer-objektet. Det er selvsagt i dette eller disse lytteobjektene vi må legge inn den kode vi ønsker utført som følge av hendelsene.

Når vi oppretter et Timer-objekt, må vi som konstruktørparametre angi pause i antall millisekunder mellom hver hendelse, samt et lytteobjekt av type ActionListener som skal varsles for hver hendelse:

  int pause = ....;
  ActionListener lytter = ...;
  Timer klokke = new Timer( pause, lytter );
  klokke.start();  // starter Timeren

Dersom vi ønsker å knytte flere lytteobjekter til Timer-objektet, kan vi gjøre det på vanlig måte ved bruk av metoden addActionListener for Timer-objektet.

Når vi har startet en Timer, vil det før den første hendelsen inntreffer gå en tid lik pausen mellom hendelsene. Vi har imidlertid mulighet til å få et annet tidsintervall før den første hendelsen inntreffer ved å bruke metoden setInitialDelay. Pausen mellom hendelsene kan vi, om vi ønsker det, endre fra den som ble bestemt i konstruktøren ved bruk av metoden setDelay, med ønsket pause som parameter. Når vi først har startet en Timer, så vil den gjennomføre sin syklus inntil vi gjør kall på dens stop-metode. Ønsker vi å 'nullstille' og starte igjen, kan vi bruke metoden restart. Eventuelle ufullførte hendelser vil da bli kansellert og Timeren vil starte igjen med den startpausen som er definert for den. Metoden isRunning kan vi bruke for å sjekke om en Timer er i virksomhet.

Dersom vi ønsker at et Timer-objekt ikke skal utføre repetisjoner, men generere hendelse bare én gang, kan vi få til det ved å gjøre metodekallet setRepeats(false) for Timer-objektet.

Som nevnt ovenfor, vil den kode som skal utføres som følge av at en Timer genererer sine hendelser, bli utført av samme programtråd som behandler hendelser som brukeren genererer ved bruk av mus og tastatur. For at brukeren skal oppleve rask respons på slike hendelser, er det viktig at hendelseshånderingen for Timer-hendelsene foregår raskt. Lytteobjektene for Timer-objektene bør derfor ikke inneholde kode som det er tidkrevende å utføre.

Eksempel

Et eksempel på bruk av en swing-Timer finnes i programmet Calendardemo i notatet Dato og tid. En Timer blir der brukt til å oppdatere en label i programvinduet hvert sekund.

Merknad

Virkemåten for en swing-Timer er at det er en bestemt forsinkelse før hver ny ActionEvent blir generert. Denne forsinkelsen kommer i tillegg til den tid det tar å utføre den kode vi har bestemt skal utføres som følge av hendelsen. (I tillegg til den utførelsen vi selv har bestemt, kan det være systembestemte oppgaver som sletting av objekter det ikke lenger blir referert til.) Dette betyr at den pause som vi spesifiserer for Timer-objektet ikke vil være lik tida mellom hver ActionEvent. Dersom vi trenger en Timer som kjører med en bestemt frekvens, må vi bruke den andre Timer-typen som ble nevnt innledningsvis, den som er definert i pakken java.util.

Innholdsoversikt for programutvikling

Copyright © Kjetil Grønning, revidert av Eva Hadler Vihovde 2014