2009-01-21 16 views
10

Ich habe eine Anwendung, wo es einen Haupthintergrund Formular gibt, von dort Benutzer kann nur nicht-modale Formen, die verschiedene Teil des Systems verwaltet. Die nicht-modalen Formen überschreibt die CreateParams Verfahren so jeweils eine Taste in der Bar Startaufgabe zeigt:Delphi, ist es möglich, eine Form nur für bestimmte Elternform zu machen?

procedure TfmMaterialsPlanning.CreateParams(var Params: TCreateParams); 
begin 
    inherited; 
    //create a new window on the task bar when this form is created 
    Params.ExStyle := Params.ExStyle or WS_EX_APPWINDOW; 
end; 

tatsächlich ein Benutzer eine nicht modale Form öffnen können, die ‚Äpfel‘, ein weiteres nicht-modal beibehält Form, die "Orangen" unterhält, und verwenden Sie die Startmenüleiste, um einfach zwischen den beiden zu wechseln.

Wenn sie jedoch ein modales Formular aus dem Formular "Äpfel" öffnen, z. um Optionen, Voreinstellungen usw. festzulegen, können sie die Formulare "Orangen" erst verwenden, wenn sie das modale Formular geschlossen haben.

Ist es möglich, ein modales Formular modal nur zum übergeordneten Formular zu machen? Wenn sie also das Optionsformular von Apple öffnen, können sie das Wartungsformular für Äpfel nicht verwenden, können aber weiterhin das Wartungsformular für Orangen verwenden.

Dank

Antwort

0

Könnten Sie nicht den gleichen Effekt erzielen, indem aus der „Äpfel“ Form zu verhindern Fokus zu akzeptieren, während sein Kind Formular geöffnet ist?

-2

Dies ist möglich, wenn Sie jedes nicht modale Formular in einem eigenen Thread erstellen. Jedes modale Formular blockiert dann den Thread, zu dem es gehört.

Edit: Dies sollte möglich sein, obwohl der vcl nicht Thread-sicher ist. Bitte werfen Sie einen Blick auf Alexeys explanation, wie dies geschehen kann:

Also, wenn Sie eine Reihe von Formen haben, die dann in einem separaten Thread leben sollen sich in eine DLL platzieren, kompiliert es ohne Pakete und nutzen! Es wird funktionieren und es wird threadsicher sein.

+0

Bei der Verwendung der VCL ist dies nicht möglich. Sie kann nur von einem Thread verwendet werden, wenn GUI-Dateien erstellt werden. – mghie

+0

True, aber dann hat jede DLL ihre eigene Kopie der gesamten VCL und ihr eigenes Application-Objekt. IMO, das ist kaum besser, als mit anderen ausführbaren Dateien zu arbeiten. – mghie

+0

Ich weiß jetzt nicht, warum Robo die Dinge so haben will, wie er sie beschreibt. Er fragt, ob es möglich ist, und ich sage es. Sie sagen, es ist nicht, ich sage, du liegst falsch ... – Vegar

6

Wenn Sie einen Blick auf den Quellcode TCustomForm.ShowModal() Sie werden sehen, dass die VCL nicht die API von Windows Aufruf modale Dialoge zur Darstellung verwendet, sondern dass sie stattdessen alle anderen Formen in der nicht deaktiviert Anwendung, während das modale Formular angezeigt wird. Sie können natürlich genau das gleiche ausprobieren, nur Show() den formularmodalen Dialog, dann deaktivieren Sie das übergeordnete Element und aktivieren es dann erneut, nachdem der formularmodale Dialog geschlossen wurde. Es muss einen zentralen Ort geben, an dem Sie formale Dialoge, Formulare, die wieder aktiviert werden müssen, verfolgen können. Sie sollten jedoch gründlich prüfen, ob der Code wirklich das tut, was Sie tun möchten, selbst wenn Sie zwischen Anwendungen hin- und herwechseln, wenn Sie die Anwendung minimieren und so weiter.

Nachdem ich das gesagt habe - ich denke nicht, dass das eine gute Idee ist. Es bricht alle Annahmen, die ein Windows-Benutzer über das Verhalten von Anwendungen macht. Anders als in Mac OS X unterscheidet man in Windows nicht zwischen anwendungs-modalen und form-modalen Dialogen, und Sie sollten sich an das Verhalten halten, das mit der Plattform übereinstimmt, auf der Sie programmieren.

Es gibt höchstwahrscheinlich eine bessere Möglichkeit, Ihre Benutzeroberfläche zu strukturieren. Sehen Sie sich die entsprechende Seite für dialog boxes in den "Windows User Experience Interaction Guidelines" an. Modale Dialoge werden so gut wie möglich vermieden, die verlinkten Richtlinien zeigen für viele Anwendungsfälle bessere Alternativen. Wenn Sie die Verwendung modaler Dialoge einschränken, benötigen Sie die formularmäßigen Dialoge möglicherweise nicht mehr.

+1

Wenn der Benutzer zwei Taskleiste-Schaltflächen hat, ist es innerhalb der UI-Richtlinien, dass ein modales Dialogfeld, das von einem dieser beiden Fenster angezeigt wird, das andere Fenster nicht blockiert. Die Tatsache, dass die beiden Taskleistenschaltflächen von demselben Prozess gehostet werden, ist für den Benutzer nicht relevant. Ich würde tatsächlich argumentieren, dass ein modaler Dialog beide Fenster unpassend blockiert. Wie auch immer, Daniel verweist auf eine funktionierende Lösung. –

0

Nur als Nebenerscheinung (obwohl es eine Menge Arbeit wäre), ein anderer Ansatz für dieses Problem ist die Art und Weise Googles Chrom ging, wo jeder "Registerkarte" ist ein separater Prozess, sondern der Benutzer als eine einzige integriert Anwendung.

Auch wenn dieser Ansatz das erreichen würde, was Sie wollten, würde ich dem obigen Kommentar zustimmen müssen, dass dies die Annahmen und Erwartungen des Benutzers über modales Verhalten brechen würde.

3

Dieser Beitrag hat einen schönen Trick, um Ihre Bedürfnisse zu erledige: http://blogs.teamb.com/deepakshenoy/2006/08/21/26864

Die Zusammenfassung ist das nichtmodal Fenster Sie wollen wieder zu aktivieren, wenn ein modales Fenster es deaktiviert.

+0

Funktioniert gut! Wahrscheinlich ist es eine gute Idee, zusätzliche Logik hinzuzufügen, damit das Formular 'WM_REENABLED' nicht an sich selbst sendet, wenn es einen eigenen modalen Dialog zeigt. –