2013-01-24 10 views
5

पर कॉल करते समय मेरा विवरण फ़ॉर्म मुख्य रूप के पीछे छिपा हुआ है मेरा आवेदन मेनफॉर्म, विवरणफॉर्म और डायलॉगफॉर्म पर आधारित है। टास्कबार पर मैं मेनफॉर्म बटन और विवरणफॉर्म भी देख सकता हूं। इसलिए मैं का उपयोग करें:TsaveDialog

procedure <DetailForm>.CreateParams(var Params: TCreateParams); 
begin 
    inherited CreateParams(Params); 
    Params.ExStyle := Params.ExStyle or WS_EX_APPWINDOW; 
    Params.WndParent:= GetDesktopWindow; 
end; 

मैं डेल्फी 2010 का उपयोग और मैं Application.MainFormOnTaskbar निर्धारित किया है: = सच; जब मैं विवरणफॉर्म में PromptForFileName या TSaveDialog का उपयोग करता हूं तो DetailForm मेनफॉर्म के पीछे जाता है। डायलॉगफॉर्म संवाद बंद करने के बाद वापस आ गया।

जब मैं डायलॉगफॉर्म (संपत्ति पॉपअपमोड: पीएमएटो के साथ टीएफओएम का शोमोडल) का उपयोग करता हूं तो मेरा विवरणफॉर्म मुख्य और संवाद के बीच रहता है। मैं कैसे संपत्ति PopupMode के साथ एक showmodal तरह TSaveDialog मजबूर कर सकते हैं: pmAuto या मैं कैसे है कि मेरे detailform MainForm

डेमो पीछे चला जाता है रोका जा सकता है:

program Project1; 

uses 
    Forms, 
    Unit1 in 'Unit1.pas' {Form1}, 
    Unit2 in 'Unit2.pas' {Form2}; 

    {$R *.res} 

begin 
    Application.Initialize; 
    Application.MainFormOnTaskbar := True; 
    Application.CreateForm(TForm1, Form1); 
    Application.Run; 
end. 

unit Unit1; 

interface 

uses 
    Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, 
    Dialogs, StdCtrls, ImgList, ActnList; 

type 
    TForm1 = class(TForm) 
    Button1: TButton; 
    procedure Button1Click(Sender: TObject); 
    private 
    { Private declarations } 
    public 
    { Public declarations } 
    end; 

var 
    Form1: TForm1; 

implementation 

uses Unit2; 

{$R *.dfm} 

procedure TForm1.Button1Click(Sender: TObject); 
var 
    oForm: TForm; 
begin 
    oForm:= Unit2.TForm2.Create(Self); 
    oForm.Show; 
end; 
end. 

unit Unit2; 

interface 

uses 
    Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, 
    Dialogs, StdCtrls; 

type 
    TForm2 = class(TForm) 

    SaveDialog1: TSaveDialog; 
    procedure cxButton1Click(Sender: TObject); 
    private 
    protected 
    procedure CreateParams(var Params: TCreateParams); override; 
     { Private declarations } 

    public 
    { Public declarations } 
    end; 

var 
    Form2: TForm2; 

implementation 

{$R *.dfm} 

{ TForm2 } 

procedure TForm2.CreateParams(var Params: TCreateParams); 
begin 
    inherited CreateParams(Params); 
    Params.ExStyle := Params.ExStyle or WS_EX_APPWINDOW; 
    Params.WndParent:= 0; // --> Testing 
end; 

procedure TForm2.cxButton1Click(Sender: TObject); 
begin 
    self.SaveDialog1.execute(); 
end; 

end. 

उत्तर

10

चरण 1 यह है कि आपको डेस्कटॉप विंडो को अपने फॉर्म के स्वामी नहीं बनाना चाहिए। रेमंड चेन explains क्यों नहीं।

वास्तव में समझने के लिए कि क्या हो रहा है आपको विंडो स्वामित्व की स्पष्ट समझ प्राप्त करने के लिए एमएसडीएन पर Window Features पढ़ने की आवश्यकता है। और बहुत सावधान रहें कि विंडो स्वामित्व एक अवधारणा है जो डेल्फी घटक स्वामित्व से पूरी तरह से असंबंधित है। डेल्फी शर्तों में, विंडो स्वामित्व PopupParent संपत्ति द्वारा नियंत्रित किया जाता है।

टिप्पणियों में स्पष्ट किया गया है, आप चाहते हैं कि दोनों रूपों को अद्वितीय, शीर्ष-स्तरीय विंडो बनें। मुख्य रूप स्वचालित रूप से है। के लिए विवरण फार्म आप 0 को WndParent निर्धारित करने की आवश्यकता है और यह है कि यह क्या है:

procedure <DetailForm>.CreateParams(var Params: TCreateParams); 
begin 
    inherited; 
    Params.WndParent := 0; 
end; 

अंतिम चरण यह सुनिश्चित करें कि बचाने के संवाद ठीक से स्वामित्व में है बनाने के लिए है। जब आप Execute फोन है कि मालिक को निर्दिष्ट करने के लिए:

Self.SaveDialog1.Execute(Self.Handle); 

तो, सारांश में तीन बदलाव करने की जरूरत:

  1. सेट विस्तार प्रपत्र के WndParent0 करने के लिए।
  2. WS_EX_APPWINDOW विस्तारित शैली को हटाएं, इसकी एक अद्वितीय शीर्ष-स्तरीय विंडो के लिए आवश्यक नहीं है।
  3. सहेजें संवाद पर Execute पर कॉल करते समय विस्तार फ़ॉर्म के हैंडल को पास करें।

अद्यतन

यह है कि आप XP का उपयोग कर रहे हैं पता चला है, और डेल्फी कोड है कि फ़ाइल संवाद से पता चलता बकवास है। यद्यपि आप Execute विधि को हैंडल पास करते हैं, जिसे अनदेखा किया जाता है और मुख्य विंडो हैंडल का उपयोग संवाद के स्वामी के रूप में किया जाता है। और यही कारण है कि मुख्य खिड़की सामने आती है।

आप Application.ModalPopupMode से pmAuto पर सेट करके इसे प्राप्त कर सकते हैं। आपको शायद इसे अपनी .dpr फ़ाइल में सेट करना चाहिए।

इस बारे में और पढ़ें: http://blogs.embarcadero.com/abauer/2005/09/30/21517

+0

नहीं, काम नहीं करता है। मैंने wndparent = 0 को बदल दिया है, WS_EX_APPWINDOW को भी छोड़ दिया है और विस्तार के मुख्य मालिक को बनाया है। विस्तृत – Ravaut123

+1

के पीछे विस्तार करें यदि आप 'WNDParent' को' 0' पर सेट करते हैं तो आपके पास एक अनूठी विंडो है। 'WNDParent' सेट करना यह है कि आप विंडो स्वामित्व को कैसे नियंत्रित करते हैं। याद रखें कि विंडो स्वामित्व डेल्फी के घटक स्वामित्व से बिल्कुल अलग है। डेल्फी में विंडो स्वामित्व को 'पॉपअपपेरेंट' संपत्ति द्वारा नियंत्रित किया जाता है। मुझे संदेह है कि आपने ऐसा किया था। उत्तर से कोड का प्रयोग करें। आप एक खिड़की चाहते हैं जो मुख्य रूप से स्वामित्व में है। ऐसा करने के लिए 'पॉपअप पेरेंट' का उपयोग करें। और फिर टास्कबार पर अपनी विंडो प्राप्त करने के लिए, 'WS_EX_APPWINDOW' जोड़ें। –

+0

मुझे मुख्य पर भी मुख्य और मुख्य रूप पर क्लिक करना होगा। जब मैं टास्कबार पर विस्तार से क्लिक करता हूं तो विवरण शीर्ष पर आता है। – Ravaut123