Entwickler-Ecke

Sonstiges (Delphi) - Timer-Prozedur wird nicht aufgerufen


Gagga - Mo 27.05.24 21:36
Titel: Timer-Prozedur wird nicht aufgerufen
Hallo!

Zur Laufzeit schalte ich einen Timer auf enabled, dessen Routine (mit Haltepunkt) jede Sekunde die Position einer Progressbar erhöhen soll. Funktioniert nicht.

Dass Veränderungen der Position einer Progressbar Probleme bereiten, ist mir bekannt. Das war früher anders, da war ja auch mehr Lametta, aber dass jetzt nicht einmal die Timer-Prozedur aufgerufen wird, das ist mir neu. Am Ende der Routine wird das Hochzählen der Progressbar-Positionen im Zeitraffer nachgeholt aber der Haltepunkt in der Timerprozedur ignoriert.

► Ich weiß, wie ich einen Haltepunkt setze.
► application.processmessages, sleep, update, refresh, repaint alles durch
► Mit Multithreading habe ich noch nicht gearbeitet

Weiß jemand Rat?

Gruß
Rüd


mandras - Mo 27.05.24 23:33

Könntest Du weitere Infos geben, zB
Ausschnitte des relevanten Codes und ggf. Form-Definition?


jasocul - Di 28.05.24 11:30

Ich zähle mal ein paar Klassiker auf:

user profile iconGagga hat folgendes geschrieben Zum zitierten Posting springen:
Am Ende der Routine wird das Hochzählen der Progressbar-Positionen im Zeitraffer nachgeholt

Wenn die Progressbar nur durch den Timer verändert wird, deutet das obige Verhalten darauf hin, dass der Timer wieder aktiv wird, bevor er überhaupt komplett abgearbeitet wurde. Das würde bedeuten, dass das Timer-Intervall zu kurz ist. Deswegen auch der eine Tipp das Enabled innerhalb des Timers aus- und anzuschalten.


Gagga - Di 28.05.24 15:25

Mal das vorweg: ohne Änderung am Code funktioniert es jetzt. Heißt, die Timerprozedur wird aufgerufen und in die Progressbar kommt Bewegung. Also Problem - wie auch immer - gelöst.

An Deine sieben Punkte kann ich einen Haken machen.
Ist es nicht unschön, das Enabled innerhalb des Timers - unnötigerweise - intervallmäßig aufrufen zu lassen?

Moderiert von user profile iconTh69: Vollzitat entfernt.


jasocul - Di 28.05.24 16:10

user profile iconGagga hat folgendes geschrieben Zum zitierten Posting springen:
Ist es nicht unschön, das Enabled innerhalb des Timers - unnötigerweise - intervallmäßig aufrufen zu lassen?

Das kommt drauf an.
Wenn klar ist, dass das Intervall IMMER groß genug ist, ist es überflüssig. Andrenfalls ist das ein guter Sicherungsmechanismus. Besonders dann, wenn im Timer zeitkritische Dinge passieren. Auf die Weise hat man auch garantierte Mindestlaufzeit nach Abarbeitung.


Blup - Do 06.06.24 11:16

user profile iconjasocul hat folgendes geschrieben Zum zitierten Posting springen:
user profile iconGagga hat folgendes geschrieben Zum zitierten Posting springen:
Am Ende der Routine wird das Hochzählen der Progressbar-Positionen im Zeitraffer nachgeholt

Wenn die Progressbar nur durch den Timer verändert wird, deutet das obige Verhalten darauf hin, dass der Timer wieder aktiv wird, bevor er überhaupt komplett abgearbeitet wurde. Das würde bedeuten, dass das Timer-Intervall zu kurz ist. Deswegen auch der eine Tipp das Enabled innerhalb des Timers aus- und anzuschalten.

Der Timer sendet jede Sekunde eine Nachricht an die Nachrichtenwarteschlange.
Damit diese Nachricht abgeholt und verarbeitet wird, muss deine Anwendung regelmäßig Application.Processmessages() aufrufen.
Scheinbar läuft aber ein Programmteil, wo das nicht passiert. Entsprechend stauen sich die Nachrichten.
Wenn das Programmteil beendet ist, werden durch das nächste Application.Processmessages() alle aufgestauten Nachrichten verarbeitet.
Folge ist dieser "Zeitraffereffekt".

Den Timer innerhalb des OnTimer-Ereignis abzuschalten macht Sinn, wenn Application.Processmessages() im OnTimer-Ereignis selbst (auch indirekt) aufgerufen wird.


jaenicke - Do 06.06.24 12:52

user profile iconBlup hat folgendes geschrieben Zum zitierten Posting springen:
Den Timer innerhalb des OnTimer-Ereignis abzuschalten macht Sinn, wenn Application.Processmessages() im OnTimer-Ereignis selbst (auch indirekt) aufgerufen wird.
Es gibt nur sehr wenige Fälle, in denen man Application.ProcessMessages aufrufen muss (nicht threadfähiges COM Control, ...). In aller Regel ist es aber ein Designfehler der Anwendung, wenn man es braucht.

Alle länger dauernden Vorgänge gehören in Threads.