Komische Probleme mit (Endlos)Schleife

Für Fragen zur Programmiersprache auf welcher Lazarus aufbaut
ppahl
Beiträge: 56
Registriert: Fr 25. Nov 2016, 00:02

Re: Komische Probleme mit (Endlos)Schleife

Beitrag von ppahl »

Jetzt habe ich erstmal kapiert was du wohl meinst?

Code: Alles auswählen

 
procedure TForm1.Button1Click(Sender: TObject);
begin
  startflag := true;
  timer1.enabled := true;
end;
 
procedure TForm1.Timer1StartTimer(Sender: TObject);
var I:integer;
begin
 i := 0;
 while startflag = true do
  begin
   inc(i);
   label1.caption := inttostr(i);
  end;
end;
 
procedure TForm1.Timer1Timer(Sender: TObject);
begin
 startflag := false;
 label1.caption := 'Done';
end;   


Korrekt?
Funktioniert auch nicht... :mrgreen:
Das Programm hängt weiterhin komplett fest und reagiert auf nichts. In die Timer1StartTimer-Prozedur muss wiederum application.ProcessMessages, dann funktionieren sowohl Ausgabe als auch Abbruch. Dann kann ich es aber auch in der Button1.Click Prozedur lassen, macht keinen Unterschied.

ppahl
Beiträge: 56
Registriert: Fr 25. Nov 2016, 00:02

Re: Komische Probleme mit (Endlos)Schleife

Beitrag von ppahl »

Mal ein kleiner Nachtrag: In die Schleife habe ich jetzt mal noch die Ansteuerung eines GPIO gepackt (die Deklaration von 'led' spare ich mir jetzt mal an der Stelle, basiert auf der pascalio-lib):

Code: Alles auswählen

 
procedure TForm1.Timer1StartTimer(Sender: TObject);
var I:integer;
begin
 i := 0;
 while startflag = true do
  begin
   inc(i);
   label1.caption := inttostr(i);
   if led.value = true then led.value := false else led.value := true;
   delay(500);
  end;
end;


Am Label ändert sich nix, auch Timer- oder Button-Events werden nicht ausgeführt...die LED blinkt aber...
Die 1000$-Frage: Was unterscheidet nun die Zuweisung des Pin-Status von der Zuweisung des Label-Textes? Schon schräg über was für Probleme man stolpern kann.

mschnell
Beiträge: 3444
Registriert: Mo 11. Sep 2006, 10:24
OS, Lazarus, FPC: svn (Window32, Linux x64, Linux ARM (QNAP) (cross+nativ)
CPU-Target: X32 / X64 / ARMv5
Wohnort: Krefeld

Re: Komische Probleme mit (Endlos)Schleife

Beitrag von mschnell »

Thandor hat geschrieben:ein Delay(10); bewirkt hier schon wunder.

sleep(10000) wäre besser :D
Aer immer noch ein übler wügaround
-Michael

wp_xyz
Beiträge: 4886
Registriert: Fr 8. Apr 2011, 09:01

Re: Komische Probleme mit (Endlos)Schleife

Beitrag von wp_xyz »

ppahl hat geschrieben:Am Label ändert sich nix, auch Timer- oder Button-Events werden nicht ausgeführt...die LED blinkt aber...
Die 1000$-Frage: Was unterscheidet nun die Zuweisung des Pin-Status von der Zuweisung des Label-Textes? Schon schräg über was für Probleme man stolpern kann.

Ich denke mir, der Unterschied ist, dass die Zuweisung des Pin-Status direkt ausgeführt wird. Auch der Label-Text wird mäglicherweise sofort geändert, aber auf jeden Fall wird die Anzeige nicht aktualisiert, weil dies über eine Paint-Message in der Nachrichtenschleife erst verzögert geschieht. Und die Nachrichtenschleife wird ohne Application.ProcessMessages nicht abgearbeitet.

Jetzt hätte ich gerne die 1000$.

Spaß beiseite: Schreibe hinter label1.caption := intToStr(i) einfach mal label1.Refresh - dies sollte m.E. ein sofortiges Neuzeichnen des Labels bewirken. Aber hier die Warnung: das Programm bleibt trotzdem nicht mehr bedienbar, weil die sonstigen Nachrichten nicht abgearbeitet werden. Application.ProcessMessages ist in einer solchen Art von Programm unerlässlich.

ppahl
Beiträge: 56
Registriert: Fr 25. Nov 2016, 00:02

Re: Komische Probleme mit (Endlos)Schleife

Beitrag von ppahl »

dies sollte m.E. ein sofortiges Neuzeichnen des Labels bewirken

Jein. Das Label wird zwar refreshed, aber unregelmässig. Gelegentlich nach jedem, meist aber nur nach jedem 2. oder 3. Inkremet von i (das ist tatsächlich ständig unterschiedlich und eine Logik nicht zu erkennen). Hätte ich jetzt auch wieder nicht erwartet...

Application.ProcessMessages ist in einer solchen Art von Programm unerlässlich

Wie schon mehrfach empfohlen werde ich wohl einen eigenen Thread damit beauftragen, aber ich war halt neugierig ob creeds Timer-Variante tatsächlich funzt ;).

mschnell
Beiträge: 3444
Registriert: Mo 11. Sep 2006, 10:24
OS, Lazarus, FPC: svn (Window32, Linux x64, Linux ARM (QNAP) (cross+nativ)
CPU-Target: X32 / X64 / ARMv5
Wohnort: Krefeld

Re: Komische Probleme mit (Endlos)Schleife

Beitrag von mschnell »

ppahl hat geschrieben:Wie schon mehrfach empfohlen werde ich wohl einen eigenen Thread damit beauftragen.

Dann kannst Du einfach mit TTHread.Queue den String des des Labels ändern und ihn dadurch neu zeichnen lassen, ohne dass der Thread aufgehalten wird und dadurch eine Aktion verpassen könnte .

-Michael

Benutzeravatar
kupferstecher
Beiträge: 422
Registriert: Do 17. Nov 2016, 11:52

Re: Komische Probleme mit (Endlos)Schleife

Beitrag von kupferstecher »

ppahl hat geschrieben:Wie schon mehrfach empfohlen werde ich wohl einen eigenen Thread damit beauftragen, aber ich war halt neugierig ob creeds Timer-Variante tatsächlich funzt ;).

Klar funzt die Timer-Variante, aber nicht so wie du denkst :wink:

IMMER wenn dein Code durchlaufen wird, ist die Hauptschleife (Messagequeue) blockiert! Normal macht das nichts aus, da einzelne Prozeduren sehr kurz sind. Hast du aber eine größere Schleife macht sich das schon bemerkbar. In deinem Fall hast du dich sogar selbst blockiert. Mit einem Timer brauchst du kein "Application.ProcessMessages", da es auch keine Schleife mehr gibt, der Timer wird sowieso zyklisch gerufen und zwar bis du ihn wieder deaktivierst.

Code: Alles auswählen

 
procedure TForm1.Timer1Call(Sender: TObject);
begin
 
  Label1.caption := inttostr(Timeout);
  led.value := not led.value;
 
  Timeout:= Timeout -1;
  if Timeout <= 0 then Timer1.enabled := false//Timer nicht weiter benötigt
 
  if not startflag then Timer1.enabled := false//Timer nicht weiter benötigt
end;
 

Antworten