![]() |
Timerabruf (Timer2) bei Timerablauf (Timer1)
Ich möchte Timer2 aufrufen, sobald Timer1 abgelaufen ist. Wenn ich dies über
Delphi-Quellcode:
mache, wird dieser aber trotzdem nie abgerufen.
if TimerReload.Interval<=1 then TimerNextTab.OnTimer(TimerNextTab);
|
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Hallo,
ich verstehe nicht ganz, was Du willst (vor allem wenn ich Deine Konstruktion und Bezeichner lese). Nach Deiner Fragestellung würde ich einfach Folgendes machen:
Delphi-Quellcode:
Oder was verstehe ich falsch? Jürgen
procedure MyForm.Timer1OnTimer(Sender: TObject);
begin Timer1.Enabled := false; Timer2.Enabled := true; end; |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Also ich habe ein Programm, womit ich den aktuellen Vertretungsplan aus einer dbf abrufen und auf dem Monitor anzeigen lasse.
Nun kann man einstellen, wie lange eine Seite eingeblendet sein soll. Wenn diese Zeit abgelaufen ist, soll TimerNextTab abgerufen werden, damit der jeweilige Wechsel vorgenommen werden kann. Das Problem ist nur, dass er wenn er auf die letzte Seite wechselt und gleichzeitig der Timer aktiviert wird, er direkt auf den nächsten Tag wechselt. |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Aaaahhh! Du willst keinen zweiten Timer aktivieren, sondern einen Timer ein weiteres Mal (ggf. mit anderen Werten) aufrufen. Dann hast Du zwei Sachen nicht verstanden, wie ein Timer arbeitet:
Du musst also nach folgendem Schema vorgehen:
Delphi-Quellcode:
Viel Erfolg! Jürgen
private NextTabTimer: TTimer;
// Startwert auf 5 Sekunden einstellen NextTabTimer.Interval := 5000; // Timer aktivieren, nachdem z.B. Daten eingelesen wurden NextTabTimer.Enabled := true; Anzeige.TabIndex := 0; // umschalten nach 5 Sekunden // weitere Seiten werden 10 Sekunden angezeigt procedure MyForm.NextTabTimerOnTimer(Sender: TObject); begin NextTabTimer.Interval := 10000; // nach der letzten Tab-Seite deaktivieren, sonst weiterschalten if Anzeige.TabIndex = 4 then NextTabTimer.Enabled := false else Anzeige.TabIndex := Anzeige.TabIndex + 1; end; |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Also, am besten, ich erklär alles nochmal ganz genau. :D
Also: AktuSeiten (TabIndex1) bzw. AktuSeitena (TabIndex2) = aktuelle Seiten TimerReload = holt regelmäßig die Vertretungsdaten TimerNextTab = Umschalten des TabIndexes Wenn nun AktuSeite bzw. AktuSeitea = 0 und TimerReload abgelaufen ist (nicht vor dem Umschalten auf AktuSeite = 0, sondern erst, nachdem diese letzte Seite x Sekunden [sprich die Zeit aus dem Timer] angezeigt worden ist!), soll TimerNextTab abgerufen werden. In diesem soll dann halt das Umschalten geregelt werden (TabIndex0 ---> 1; 1 ---> 2; 2 ---> 0). |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Also doch, wie ich es schon in meiner ersten Antwort gesagt habe: die beiden Timer aktivieren und deaktivieren sich gegenseitig.
Delphi-Quellcode:
Das Zusammenspiel könnte in der Praxis vereinfacht werden. Eigentlich brauchst Du den TimerReload überhaupt nicht, sondern liest die Daten einfach dann ein, wenn er wieder auf TabIndex 0 umgeschaltet hat. Aber das ist ein anderes Thema.
// vereinfacht: die Intervalle bleiben konstant
TimerReload.Interval = 30000; TimerNextTab.Interval = 10000; // Anzeige weiterschalten: procedure MyForm.TimerNextTabOnTimer(Sender: TObject); begin if Anzeige.TabIndex = 2 then begin Anzeige.TabIndex := 0; // das Weiterschalten deaktivieren, damit erst einmal eingelesen werden kann TimerNextTab.Enabled := false; end else begin Anzeige.TabIndex := Anzeige.TabIndex + 1; end; end; // Daten neu einlesen procedure MyForm.TimerReloadOnTimer(Sender: TObject); begin if Anzeige.TabIndex = 0 then begin DatenNeuEinlesen(); // das Weiterschalten aktivieren TimerNextTab.Enabled := true; end; end; Gruß Jürgen |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Ja schon, allerdings funktioniert es so nur richtig beim TabIndex2, wo nur die Meldung angezeigt werden.
Denn wenn ein Tag nur eine Seite hat, dann wird dieser direkt übersprungen. Denn der Timer geht momentan direkt weiter, sobald er auf AktuSeite bzw AktuSeitea = 0 trifft und nicht erst, nachdem diese Seite 0 x Sek angezeigt wurde. |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Tut mir leid, dann bin ich nicht mehr fähig zu raten. Wie wäre es, wenn Du uns Deinen bisherigen Code angäbest?!
|
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Reload-Prozedur
Delphi-Quellcode:
NextTab-Timer:
procedure TForm2.TimerReloadTimer(Sender: TObject);
var Ini: TIniFile; y,ya,i,ia,count,count2,counta,countb,ReloadTime,dnr:integer; morgen_m: String; tomorrow,today: TDateTime; begin dnr:=DayOfWeek(Date); if dnr=7 then begin today:=Date+2; tomorrow:=Date+3; end else if dnr=6 then begin today:=Date+3; tomorrow:=Date+4; end else begin today:=Date; tomorrow:=Date+1; end; try Ini:=TIniFile.Create(ExtractFilePath(ParamStr(0))+'conf.ini'); ReloadTime:=(Ini.ReadInteger('Zeiteinstellungen','Tagwechsel',10)*1000); morgen_m:=Ini.ReadString('Zeiteinstellungen','Datum morgen',DatetoStr(tomorrow)); if StrToDate(morgen_m)<tomorrow then morgen_m:=DateToStr(tomorrow) else tomorrow:=StrToDate(morgen_m); finally Ini.Free; end; if PageControl1.TabIndex=0 then begin Label5.Caption:='Vertretungsplan für den'; Label6.Caption:=DateToStr(today)+' (heute)'; end else if PageControl1.TabIndex=1 then begin Label5.Caption:='Vertretungsplan für den'; Label6.Caption:=DatetoStr(tomorrow); end else begin Label5.Caption:='Meldungen'; Label6.Caption:=''; end; TimerReload.Interval:=ReloadTime; if PageControl1.TabIndex=0 then begin if aktuseite = Gesseiten then count := length(Daten) mod 19 else count := 19; y:= 19*AktuSeite; stringgrid1.RowCount:=count+1; for i:=0 to count-1 do begin stringgrid1.Cells[0,i+1]:= Daten[i+y].klasse; stringgrid1.Cells[1,i+1]:= Daten[i+y].stunde; stringgrid1.Cells[2,i+1]:= Daten[i+y].fuer; stringgrid1.Cells[3,i+1]:= Daten[i+y].wer; stringgrid1.Cells[4,i+1]:= Daten[i+y].fach; stringgrid1.Cells[5,i+1]:= Daten[i+y].raum; stringgrid1.Cells[6,i+1]:= Daten[i+y].bemerkung; end; if AktuSeite = GesSeiten then AktuSeite := 0 else AktuSeite:=AktuSeite+1; end else if PageControl1.TabIndex=1 then begin if aktuseitea = Gesseitena then counta := length(Daten2) mod 19 else counta := 19; ya:= 19*AktuSeitea; stringgrid2.RowCount:=counta+1; for ia:=0 to counta-1 do begin stringgrid2.Cells[0,ia+1]:= Daten2[ia+ya].klasse; stringgrid2.Cells[1,ia+1]:= Daten2[ia+ya].stunde; stringgrid2.Cells[3,ia+1]:= Daten2[ia+ya].fuer; stringgrid2.Cells[2,ia+1]:= Daten2[ia+ya].wer; stringgrid2.Cells[4,ia+1]:= Daten2[ia+ya].fach; stringgrid2.Cells[5,ia+1]:= Daten2[ia+ya].raum; stringgrid2.Cells[6,ia+1]:= Daten2[ia+ya].bemerkung; end; if AktuSeitea = GesSeitena then AktuSeitea := 0 else AktuSeitea:=AktuSeitea+1; end; TimerNextTab.Enabled:=True; end;
Delphi-Quellcode:
Der Interval wird jeweils aus einer Ini-Datei ausgelesen.
procedure TForm2.TimerNextTabTimer(Sender: TObject);
var Ini: TIniFile; dnr,interval: Integer; morgen_m: String; tomorrow,today: TDateTime; begin dnr:=DayOfWeek(Date); if dnr=7 then begin today:=Date+2; tomorrow:=Date+3; end else if dnr=6 then begin today:=Date+3; tomorrow:=Date+4; end else begin today:=Date; tomorrow:=Date+1; end; try Ini:=TIniFile.Create(ExtractFilePath(ParamStr(0))+'conf.ini'); interval:=(Ini.ReadInteger('Zeiteinstellungen','Tagwechsel',10)*1000); morgen_m:=Ini.ReadString('Zeiteinstellungen','Datum morgen',DatetoStr(tomorrow)); if StrToDate(morgen_m)<tomorrow then morgen_m:=DateToStr(tomorrow) else tomorrow:=StrToDate(morgen_m); finally Ini.Free; end; if PageControl1.TabIndex=0 then begin PageControl1.TabIndex:=1; TimerNextTab.Enabled:=False; TimerNextTab.Interval:=interval; Label5.Caption:='Vertretungsplan für den'; Label6.Caption:=DateToStr(today)+' (heute)'; end else if PageControl1.TabIndex=1 then begin PageControl1.TabIndex:=2; TimerNextTab.Enabled:=False; TimerNextTab.Interval:=interval; Label5.Caption:='Vertretungsplan für den'; Label6.Caption:=DateToStr(Tomorrow); end else if PageControl1.TabIndex=2 then begin PageControl1.TabIndex:=0; TimerNextTab.Enabled:=False; TimerNextTab.Interval:=interval; Label5.Caption:='Meldungen'; Label6.Caption:=''; end end; |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Hallo Svenkan,
dringende Empfehlung: Strukturiere Deinen Code übersichtlicher:
Im Moment erschwerst Du mir/uns das Verständnis viel zu sehr. Du willst schließlich Hilfe; also solltest Du uns dies erleichtern. Gruß Jürgen |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Hallo Svenkan,
mir sind jetzt noch ein paar Gedanken gekommen; die möchte ich mit meinen früheren Vorschlägen zusammenfassen. 1. Einmalige Maßnahmen gehören in den Aufbau des Formulars. Also interval bestimmen, today, tomorrow 2. Anzeige aktualisieren gehört in eigene Prozeduren:
Delphi-Quellcode:
3. Daten einlesen gehört in eine eigene Prozedur.
procedure MyForm.StringGrid1Zeigen(dieseSeite: integer);
begin ... end; procedure MyForm.StringGrid2Zeigen(dieseSeite: integer); begin ... end; Hier werden auch die Einstellungen vorgenommen, die nur dafür geändert werden müssen:
Delphi-Quellcode:
4. Die Timer-Aktion reduziert sich auf einen Verteiler.
procedure MyForm.NeueDatenEinlesen;
begin // Einstellungen auf "Einlesen" umschalten PageControl1.TabIndex := 2; Label5.Caption:='Meldungen'; Label6.Caption:=''; TimerNextTab.Enabled := false; // Daten einlesen ... // erste Seite zur Anzeige vorbereiten AktuSeite := 0; StringGrid1Zeigen((0); // Einstellungen auf "Anzeigen" umschalten Label5.Caption:='Vertretungsplan für den'; Label6.Caption:=DatetoStr(tomorrow); PageControl1.TabIndex := 0; // und natürlich das Umschalten aktivieren TimerNextTab.Enabled := true; end; Das ist unbedingt die wichtigste Änderung, die Du vornehmen musst!
Delphi-Quellcode:
Ich habe die Unterscheidungen bei AktuSeite(a) und GesSeiten(a) nach wie vor nicht verstanden. Weil das interval der beiden Timer gleich ist, verstehe ich auch nicht, warum Du zwei Timer haben willst.
procedure TForm2.TimerNextTabTimer(Sender: TObject);
begin case PageControl1.TabIndex of 0: begin PageControl1.TabIndex := 1; StringGrid2Zeigen(AktuSeite); 1: if (AktuSeite < GesSeiten) then begin Inc(AktuSeite); StringGrid1Zeigen(AktuSeite); PageControl1.TabIndex := 0; end else begin NeueDatenEinlesen; end; 2: // kommt eigentlich wegen NeueDatenEinlesen gar nicht mehr vor, // aber vielleicht ergibt sich noch etwas, deshalb dummy-Code: begin end; end; Versuch doch einmal eine solche Struktur und berücksichtige meine Bemerkungen im letzten Post. Jürgen |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Hallo Svenkan,
noch ein Gedanke, wenn Du wirklich zwei Timer nutzen willst. Das kann sinnvoll sein, wenn ihr Intervall ziemlich unterschiedlich festgelegt wird (z.B. 15 Minuten für Reload und 10 Sekunden für NextTab). TimerReload wird aktiviert (Enabled := true), nachdem die Daten eingelesen wurden, d.h. am Ende der Prozedur NeueDatenEinlesen. TimerReloadOnTimer macht nichts anderes als sich zu deaktivieren: TimerReload.Enabled := false; Die Prüfung innerhalb NextTab wird einfach erweitert, ob TimerReload abgelaufen ist oder nicht, d.h. ob er noch aktiviert ist:
Delphi-Quellcode:
Jürgen
procedure TForm2.TimerNextTabTimer(Sender: TObject);
begin case PageControl1.TabIndex of 0: begin PageControl1.TabIndex := 1; StringGrid2Zeigen(AktuSeite); 1: if ((AktuSeite < GesSeiten) or TimerReload.Enabled) // die vorstehende Abfrage wird erweitert then begin // wenn TimerReload noch läuft, dann zurück zu Seite 0 if (AktuSeite < GesSeiten) then Inc(AktuSeite) else AktuSeite := 0; StringGrid1Zeigen(AktuSeite); // alles andere bleibt wie gehabt PS. Ich weiß nicht, ob Du meine vorigen Beiträge bereits gelesen hast; deshalb trage ich es als neuen Beitrag ein. |
Re: Timerabruf (Timer2) bei Timerablauf (Timer1)
Also grundsätzlich gibt es kaum Gründe mehr als einen Timer pro Anwendung zu verbauen.
Es sei denn man braucht ab und zu einen hochauflösenden Timer und ansonsten einen nicht so hoch auflösenden Timer. Warum lehrt man in der Schulde schon GUI Programmierung bevor die Programmierprache beherrscht wird? |
Alle Zeitangaben in WEZ +1. Es ist jetzt 21:29 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz