Timer stoppen

Für Fragen von Einsteigern und Programmieranfängern...
Antworten
Chaentel
Beiträge: 4
Registriert: Sa 24. Apr 2021, 17:56

Timer stoppen

Beitrag von Chaentel »

Hallöchen,
wir müssen für die Schule ein Spiel entwickeln und meine Partnerin und ich haben uns für das simple 'Stein Schere Papier' entschieden. Um was neues hineinzupacken haben wir uns überlegt, dass bevor das Ergebnis gezeigt wird ein Timer im Intervall von 200 random Bilder anzeigt bevor er das Ergebnisbild anzeigt. Nun haben wir aber das Problem, dass der Timer nicht mehr gestoppt wird. Ich habe es mit if-Strukturen und Schleifen sowohl im Button, als auch im timer probiert. kann mir da einer behilflich sein? Im Anhang habe ich auch nochmal meinen bisherigen Quelltext angehängt.
Quelltext.txt
(4.26 KiB) 64-mal heruntergeladen

Benutzeravatar
h-elsner
Lazarusforum e. V.
Beiträge: 259
Registriert: Di 24. Jul 2012, 15:42
OS, Lazarus, FPC: LINUX Mint21.1, Win10, Lazarus 2.2.4, FPC3.2.2
CPU-Target: X86-64; arm 32bit
Wohnort: Illertissen
Kontaktdaten:

Re: Timer stoppen

Beitrag von h-elsner »

Ich verstehe zwar nicht, warum es drei Timer sind, aber innterhalb der Procedure, wenn der 200ms Timer ausgelöst wird, wartet das Programm zweimal 200ms. Erst dann wird n hochgezählt. Er soll bis 10 zählen. Aber in dieser Zeit wird der Timer erneut ausgelöst und läuft wieder in die Routine. Damit wird nie Timer1.Enabled:=false erreicht.
Du musst dich entscheiden, ob du Timer verwenden willst oder sleep(200). Timer ist sicherlich besser.
Da die Timer gleichzeitig starten überschreiben sie Image1 und 2 immer gegenseitig. Wird da überhaupt etwas dargestellt bei dem Geflimmer?

Ich würde einen Timer nehmen, der nacheinander die Bilder aufruft. Dann eine TImageList und die Bilder per Index der Liste auswählen. Der Index kann random sein.

Ein zweiter Timer (z.B. 3s) macht die zeitdauer der Flimmeranzeige und stoppt dann sich selbst und den Timer 1.

Gruß HE

Benutzeravatar
Winni
Beiträge: 1577
Registriert: Mo 2. Mär 2009, 16:45
OS, Lazarus, FPC: Laz2.2.2, fpc 3.2.2
CPU-Target: 64Bit
Wohnort: Fast Dänemark

Re: Timer stoppen

Beitrag von Winni »

Hi!

Wir lösen zwar hier keine Hausaufgaben, aber ein Hinweis zum weitermachen:

Du kannst den Timer stoppen mit:

Code: Alles auswählen

Timer.enabled := false;
Und Du kannst ihn wieder starten mit

Code: Alles auswählen

Timer.enabled := true;
Hoffe Ihr kommt damit weiter.

Winni

Benutzeravatar
h-elsner
Lazarusforum e. V.
Beiträge: 259
Registriert: Di 24. Jul 2012, 15:42
OS, Lazarus, FPC: LINUX Mint21.1, Win10, Lazarus 2.2.4, FPC3.2.2
CPU-Target: X86-64; arm 32bit
Wohnort: Illertissen
Kontaktdaten:

Re: Timer stoppen

Beitrag von h-elsner »

@Winni: Er weiß ja, wie er den Timer stoppen kann, aber seine Timer überschreiben sich immer selbst, so dass er nie dahin kommt.
@ Chaentel: Das Konzept ist zu verzwickt. Merke: Einfacher ist besser. Ein Timer für das Wechseln der Bilder und ein zweiter, der bestimmt, wie lange das Wechseln dauern soll. Kein sleep, nix hochzählen.

Gruß HE

Chaentel
Beiträge: 4
Registriert: Sa 24. Apr 2021, 17:56

Re: Timer stoppen

Beitrag von Chaentel »

So wie der Quelltext gerade ist, hat es mir auch mein Lehrer gesagt. Ich schaue morgen mal, aber Timer so haben wir noch nie behandelt und da weiß ich auch leider nicht wie das an sich funktioniert.

Benutzeravatar
af0815
Lazarusforum e. V.
Beiträge: 6208
Registriert: So 7. Jan 2007, 10:20
OS, Lazarus, FPC: FPC fixes Lazarus fixes per fpcupdeluxe (win,linux,raspi)
CPU-Target: 32Bit (64Bit)
Wohnort: Burgenland
Kontaktdaten:

Re: Timer stoppen

Beitrag von af0815 »

Bei Google mal "Lazarus TTimer" eingeben. Damit kann man mal Grundlegend was zum Timer in Erfahrungen bringen.
Blöd kann man ruhig sein, nur zu Helfen muss man sich wissen (oder nachsehen in LazInfos/LazSnippets).

Benutzeravatar
h-elsner
Lazarusforum e. V.
Beiträge: 259
Registriert: Di 24. Jul 2012, 15:42
OS, Lazarus, FPC: LINUX Mint21.1, Win10, Lazarus 2.2.4, FPC3.2.2
CPU-Target: X86-64; arm 32bit
Wohnort: Illertissen
Kontaktdaten:

Re: Timer stoppen

Beitrag von h-elsner »

Das hat dir dein Lehrer so gezeigt? Ziemlich wirr...

Der Timer funktioniert folgendermaßen: Wenn er enabled wird beginnt er zu laufen. Nach dem eingestellten Intervall, löste er einen Interupt aus. Das sagt dem Betriebssystem, da will einer was. Wenn das Betriebssystem deinem Programm CPU-Zeit gibt, wird das OnTimer Ereignis aufgerufen und das ausgeführt, was du da reingeschrieben hast. Inzwischen läuft aber der Timer weiter und löst dann nach dem Intervall wieder einen Interupt aus usw.
Da das betriebssystem deinem Programm nur gelegentlich Rechenzeit zuweist, sind Timerintervalle nicht so sehr genau und abhängig von der Prozessorlast. Sehr schnelle Bildwechsel im Millisekundenbereich sind da nicht zu machen. Beim Laden der Bilder aus einer Datei von Festplatte erst recht nicht. Für eine Demo reicht aber 100 - 200ms denke ich.

Wie baust du das also auf? Die einfache Lösung:
Ein Timer für die Zeit, wie lange die Bilder wechseln sollen. Sagen wir 3 Sekunden.
Ein Timer, wie schnell die Bilder wechseln sollen. Du hast 200ms vorgeschlagen. Das ist OK.

Beim Programmstart sind beide Timer disabled. Dies hast du ja richtig gemacht. Prima. Wenn du auf den Button drückst, der das ganze starten soll, brauchst du in OnClick Routine eigentlich nur beide Timer enabeln.
Was passiert? Der 3 Sekunden Timer startet und läuft nach ~3s ab (~ deshalb, weil ja das Betriebssystem hier seine Pfötchen drin hat). Wenn die drei Sekunden um sind, stoppst du beide Timer. Und die Bilder Stein, Schere, Papier werden in deinen Images dauerhaft angezeigt. Du gewinnst oder auch nicht...

Jetzt willst du aber die Bilder vorher wechseln lassen. Diese Prozedur, je ein zufälliges Bild in Image 1 bzw. 2 zuschreiben packst du in den OnTimer Event von dem 200ms Timer. Dieser Event wird ja alle 200ms ausgelöst, plus/minus Zeitverzug durch das Betrienssystem. das heißt die Bilder werden für rund 200ms angezeigt bevor sie wieder zufällig wechseln. Das ist ja das, was du haben willst.

Mehr brauchst du nicht. OnClick für den Button sind zwei Zeilen Code, OnTimer des 3s Timers sind zwei Zeilen Code und die restliche Funktionalität, das Darstellen von zwei zufällig ausgewählten Bildern, liegt im OnTimer Event des 200ms Timers. Die überlasse ich dir. Du hast da ja schon etwas gemacht.
Ich habe es mit TImageList ausprobiert und da sind es dann auch nur 2 Zeile Code im OnTimer Event. Dafür musste ich allerdings auch erst die Suchmaschine meiner Wahl bemühen :lol:

Du kannst mit den Timer Intervallen ein bisschen herumspielen, um ein gefühl dafür zu bekommen, was das Betriebssystem so zulässt. Die 3s sollten kein Problem sein. Bei dem Bild-Wechsel-Timer dürfte das aber interessant werden, was Laufzeit deines Programms, Darstellung der Bilder vom Betriebssystem und Zuteilung der Ressourcen vom Betriebssystem betrifft.

Gruß HE

Chaentel
Beiträge: 4
Registriert: Sa 24. Apr 2021, 17:56

Re: Timer stoppen

Beitrag von Chaentel »

So wir haben das jetzt versucht.
Im Timer1 für die 3s haben wir folgendes gemacht:
counter:= counter+1;
if(counter=zeit) then
begin
Timer1.Enabled:=False;
Timer2.Enabled:=False;
end;

die Variable zeit haben wir im Button auf 3 gesetzt und der Counter soll bis 3 zählen und dass beide deaktivieren um das ergebnis anzuzeigen. von der theorie klappt das auch. im 2. Timer haben wir dass folgendes gemacht:
Image1.Picture.LoadFromFile('steinl.jpg');
Image2.Picture.LoadFromFile('papierr.jpeg');
Image1.Picture.LoadFromFile('scherel.jpg');
Image2.Picture.LoadFromFile('steinr.jpeg');
Image1.Picture.LoadFromFile('papierl.jpg');
Image2.Picture.LoadFromFile('scherer.jpeg');
das Intervall haben wir von vorhin auf 200ms gelassen. Das Problem ist hierbei aber, dass er die reihenfolge so anzeigt und dann aber nach nichtmal einem Durchgang die letzten beiden immer wieder anzeigt. Muss ich ja die Bilder mehrfach random laden bis der aufhört oder kann man das auch irgendwie machen, dass er die immer wieder anzeigt?

Benutzeravatar
fliegermichl
Lazarusforum e. V.
Beiträge: 1435
Registriert: Do 9. Jun 2011, 09:42
OS, Lazarus, FPC: Lazarus Fixes FPC Stable
CPU-Target: 32/64Bit
Wohnort: Echzell

Re: Timer stoppen

Beitrag von fliegermichl »

Das ist ja klar,
Wenn die Reihenfolge immer die gleiche ist und auch die Zeiten immer gleich bleiben und auch das laden der Bilder immer die gleiche Zeit beansprucht, dann wird auch immer wieder exakt das gleiche angezeigt.

Wie helsner schon geschrieben hat, ist es besser, die Dateien ganz am Anfang in eine Imagelist zu laden (TImageList)
und in dem 200ms Timerevent per Random ein zufälliges Bild anzeigen. Zum einen geht das schneller (weil die Bilddaten ja schon geladen sind) und zum anderen hast du dann eben nicht immer die gleichen Bilder in der gleichen Reihenfolge.

Benutzeravatar
h-elsner
Lazarusforum e. V.
Beiträge: 259
Registriert: Di 24. Jul 2012, 15:42
OS, Lazarus, FPC: LINUX Mint21.1, Win10, Lazarus 2.2.4, FPC3.2.2
CPU-Target: X86-64; arm 32bit
Wohnort: Illertissen
Kontaktdaten:

Re: Timer stoppen

Beitrag von h-elsner »

Wofür genau brauchst du denn den Counter im Timer1? Kannst du mal erklären, was du damit genau machst? Mir leuchtet absolut nicht ein, wozu das ist.

Sind die Bilder links und rechts für Stein, Schere, Papier wirklich unterschiedlich oder warum lädst du die aus verschiedenen Dateien?

Schreibe auch immer Kommentare in deinen Quelltext. Das bringt dich dazu, über viele Dinge nachzudenken und macht es leichter, später noch zu wissen, was du da gemacht hast.

Gruß HE

Benutzeravatar
fliegermichl
Lazarusforum e. V.
Beiträge: 1435
Registriert: Do 9. Jun 2011, 09:42
OS, Lazarus, FPC: Lazarus Fixes FPC Stable
CPU-Target: 32/64Bit
Wohnort: Echzell

Re: Timer stoppen

Beitrag von fliegermichl »

h-elsner hat geschrieben:
Do 29. Apr 2021, 10:00
Wofür genau brauchst du denn den Counter im Timer1? Kannst du mal erklären, was du damit genau machst? Mir leuchtet absolut nicht ein, wozu das ist.
Ich schätze, daß Timer1 alle 1000ms feuert und er damit die Sekunden hochzählt bis "Zeit" erreicht ist.

Benutzeravatar
fliegermichl
Lazarusforum e. V.
Beiträge: 1435
Registriert: Do 9. Jun 2011, 09:42
OS, Lazarus, FPC: Lazarus Fixes FPC Stable
CPU-Target: 32/64Bit
Wohnort: Echzell

Re: Timer stoppen

Beitrag von fliegermichl »

Chaentel hat geschrieben:
Mi 28. Apr 2021, 12:22
So wir haben das jetzt versucht.
Im Timer1 für die 3s haben wir folgendes gemacht:
counter:= counter+1;
if(counter=zeit) then
begin
Timer1.Enabled:=False;
Timer2.Enabled:=False;
end;
Das ist ok, wenn das Interval des Timers auf 1000 steht.
Chaentel hat geschrieben:
Mi 28. Apr 2021, 12:22
die Variable zeit haben wir im Button auf 3 gesetzt und der Counter soll bis 3 zählen und dass beide deaktivieren um das ergebnis anzuzeigen. von der theorie klappt das auch. im 2. Timer haben wir dass folgendes gemacht:
Image1.Picture.LoadFromFile('steinl.jpg');
Image2.Picture.LoadFromFile('papierr.jpeg');
Image1.Picture.LoadFromFile('scherel.jpg');
Image2.Picture.LoadFromFile('steinr.jpeg');
Image1.Picture.LoadFromFile('papierl.jpg');
Image2.Picture.LoadFromFile('scherer.jpeg');
das Intervall haben wir von vorhin auf 200ms gelassen. Das Problem ist hierbei aber, dass er die reihenfolge so anzeigt und dann aber nach nichtmal einem Durchgang die letzten beiden immer wieder anzeigt. Muss ich ja die Bilder mehrfach random laden bis der aufhört oder kann man das auch irgendwie machen, dass er die immer wieder anzeigt?
Das ist Unfug. Du willst doch, daß alle 200ms ein anderes Bild angezeigt werden soll und nicht innerhalb von 200 ms alle Bilder.
Deshalb ist die Imagelist - wie H-Elsner es vorgeschlagen hat, der bessere Weg.

In dem OnTimer Event des 200ms Timers lädst du dann per Random ein Bild aus der Imagelist und weist das dem Image zu.

Chaentel
Beiträge: 4
Registriert: Sa 24. Apr 2021, 17:56

Re: Timer stoppen

Beitrag von Chaentel »

Bruuh...ich bin echt am verzweifeln. Ich habe die Bilder in die Imagelist geladen und wird im timer2 aufgerufen. Jetzt ist nur das Problem, dass die Bilder 16*16 groß sind und ich nicht weiß, wie ich das ändere. Ich habe schon im Internet nachgeschaut, aber entweder ich bin zu doof um richtig zu googlen oder keine ahnung. könntet ihr mir da helfen?

Benutzeravatar
fliegermichl
Lazarusforum e. V.
Beiträge: 1435
Registriert: Do 9. Jun 2011, 09:42
OS, Lazarus, FPC: Lazarus Fixes FPC Stable
CPU-Target: 32/64Bit
Wohnort: Echzell

Re: Timer stoppen

Beitrag von fliegermichl »

Die Imagelist hat die Eigenschaften Width und Height. Da kann man die Größe der Bilder einstellen.

Antworten