![]() |
In virt. Meth. wird stat. Meth. aufgerufen, diese Verdecken?
Hallo,
Ich möchte verhindern, dass ein Modales Fenster unter bestimmten Umständen geschlossen wird. [EDIT] Das Programm soll aber weiterlaufen, auch wenn das Fenster geöffnet bleibt. [/EDIT] (Siehe auch ![]() Dort Überschrieb ich die Methode ShowModal, diese Lösung ist aber nicht sehr elegant. Daher untersuchte ich die Methode ShowModal etwas genauer: in der
Delphi-Quellcode:
befindet sich u.a. der Aufruf von Hide, den ich Überschreiben wollte.
function TCustomForm.ShowModal: Integer;
var ... begin ... try Show; try ... finally Hide; // <--------------------------------- end; finally ... end; end; Hide ist aber eine statische Methode:
Delphi-Quellcode:
Wenn ich nun folgendes schreibe
procedure TCustomForm.Hide;
begin Visible := False; end;
Delphi-Quellcode:
wird nach
TYPE
TForm3 = CLASS(TForm) PRIVATE FDebugMode: Boolean; PUBLIC PROCEDURE Hide; // Static, d.h. nicht Override-bar PROPERTY DebugMode: Boolean READ FDebugMode WRITE FDebugMode; END; PROCEDURE TForm3.Hide; BEGIN IF DebugMode AND (fsModal IN self.FormState) THEN ELSE Visible := False; // Original-Code END;
Delphi-Quellcode:
trotzdem TCustomForm.Hide und nicht "mein" Hide aufgerufen,
PROCEDURE TForm1.Button2Click(Sender: TObject);
VAR aDebugForm : TForm3; BEGIN aDebugForm := TForm3.Create(self); aDebugForm.DebugMode := TRUE; aDebugForm.Showmodal; // Hier gibt es ein "Hide" END; kann ich das irgendwie verhindern (ausser das ich die VCL patche) ? p.s. Mir ist klar das dieses Verhalten die Regeln der OOP befolgt (zumindest jene die mir geläufig sind), aber trotzdem: Es muß doch noch einen anderen Weg geben, oder? |
Hallo App,
wie du ja selbst schon gesagt hast: Hide ist eine statische Methode und wird deshalb "früh gebunden", soll heißen, die Adresse der Funktion wird schon im Comiliervorgang festgelegt und sie hat keinen Eintrag in der VMT (virtuellen Methoden Tabelle). Es kann dir deshalb (außer dem Patchen von VCL) nicht gelingen, dass dein Hide aufgerufen wird. Natürlich könntest du versuchen eine neue Komponente von einem Vorgänger abzuleiten, bei der Hide noch nicht definiert ist, dabei dürfte aber der Aufwand deutlich größer sein. Eventuell könntest du eine eigene "ShowModalCustomHide" schreiben, die parallel zu ShowModal existiert. |
Hallo,
erst mal ist es wichtig zu wissen was für ein Fenster du benutzt. Ich würde ein "normales" Fenster benutzen und es mit ShowModal aufrufen. Dann ist es recht einfach alle Bedingungen in der OnClose Methode zu verarbeiten um ein Schließen zu verhindern. Gruß oki |
Hallo oki,
da hast Du schon recht, aber mein Programm soll danach ja weiterlaufen, das tut es aber nicht wenn das modale Fenster nicht geschlossen wird. TSCHULDIGUNG :oops: , ich dachte neues Thema - neuer Tread, leider ist der Zusammenhang nun futsch, daher eine Kurzzusammenfassung des "Parent-Threads" ![]() Zitat:
|
Hi,
ich hab mir deine eingefügten Komentare sowie deinen Link angeschaut. Folgende Lösung: Schreibe einen Thread in dem Du die Aktionen deines nicht modalen Überwachungsfensters steuerst (Fenster auch in diesem Thread kreieren und aufrufen). An den entsprechenden Stellen deines Hauptprogrammes setzt du eine Abfrage über eine eigene Function für Warten (in dieser ein Sleep und Application.ProcessMessages). Mit dem Thred kannst du ein Ereignis senden, mit dem eine globale Variable deines Hauptprogrammes gesetzt wird. Das alles so etwa nach dem Schema
Delphi-Quellcode:
Die Variable isWait wird durch das Ereignis des Thread für das Anzeigefenster gesetzt. So liegt das Fenster aus dem Thread heraus immer oben und der Programmablauf wird durch die Schalter gesteuert.
Function MyWeiter: Boolean;
begin Result := False; sleep(50); Application.ProcessMessages; if not isWait then Result := True; end; // laufend im Hauptprogramm // ab hier warten repeat until MyWeiter isWait := False; // und weiter zum nächsten Wartepunkt Gruß oki |
Hallo oki,
vielen Dank für Deine Bemühungen, ich habe mir Deine Lösung leider nur Kurz ansehen können, aber ich finde den Ansatz sehr interessant. p.s. Außerdem habe ich etwas über Endlosschleifen gelernt: :shock:
Delphi-Quellcode:
belastet den Prozessor (genauer die CPU-Auslastun im Taskmanager) fast gar nicht, aber
REPEAT
sleep(50); Application.ProcessMessages; UNTIL MyWeiter;
Delphi-Quellcode:
führt zu einer 100% CPU-Auslastung
REPEAT
Application.ProcessMessages; UNTIL MyWeiter; ...und ein Druck auf
Delphi-Quellcode:
führt dazu, dass das Programm 3 Sekunden nicht ansprechbar ist (d.h. nicht einmal die Form läßt sich bewegen), da habe ich die OH
PROCEDURE TForm1.Button4Click(Sender: TObject);
BEGIN sleep(3000); END; Zitat:
Tja, man lernt nie aus! :warn: |
Zitat:
|
Jo,
ich denke das wars. Gruß oki |
Alle Zeitangaben in WEZ +1. Es ist jetzt 21:34 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