Showing MDI form as modal

Ertugrul Kara picture Ertugrul Kara · Sep 22, 2009 · Viewed 8.1k times · Source

This will sound against the nature of MDI.. I need to show a MDI form (FormStyle=fsMdiChild) as modal sometimes. And I also need to access the part between Application.CreateForm and OnShow event of another MDI form, i.e.

Application.CreateForm(Form2,TForm2); // but don't set form2's visible property true.
Form2.caption:='not working example'; 
Form2.SomeMagicToSetVisibleTrue;

Any ideas?

Answer

Ralph M. Rickenbach picture Ralph M. Rickenbach · Sep 22, 2009

For your first problem: Add another constructor, for example CreateAsMDI, like this:

constructor TModalAndMDIForm.CreateAsMDI(AOwner: TComponent); 
begin 
  f_blChild := true; 
  GlobalNameSpace.BeginWrite; 
  try 
    inherited CreateNew(AOwner); 
    if(not(csDesigning in ComponentState)) then begin 
      Include(FFormState, fsCreating); 
      try 
        FormStyle := fsMDIChild; 
        if(not(InitInheritedComponent(self, TForm))) then 
          raise Exception.CreateFmt('Can't create %s as MDI child', [ClassName]); 
      finally 
        Exclude(FFormState, fsCreating); 
      end; 
    end; 
  finally 
    GlobalNameSpace.EndWrite; 
  end; 
end; 

In the normal constructor just set the variable f_blChild to false and call the inherited create.

You need two more things, rather self explaining:

procedure TModalAndMDIForm.Loaded; 
begin 
  inherited; 
  if(f_blChild) then 
    Position := poDefault 
  else begin 
    Position := poOwnerFormCenter; 
    BorderStyle := bsDialog; 
  end; 
end; 
//----------------------------------------------------------------------------- 
procedure TModalAndMDIForm.DoClose(var Action: TCloseAction); 
begin 
  if(f_blChild) then 
    Action := caFree; 
  inherited DoClose(Action); 
end; 

Now you can call the form modal, if created with the standard constructor, and as MDI child, if created with CreateAsMDI.

If you include this in your form's declaration

property IsChild: boolean read f_blChild; 

you can even do things depending on whether the form is an MDI child or not, just interrogating the isChild property.

As for your second problem: do not use Application.CreateForm, but create your form yourself:

Here the two creations for modal and MDI:

//Modal 
frmDialog := TMyForm.Create(self); 
// Your Code
frmDialog.ShowModal; 
frmDialog.Release; 

//MDI-Child 
frmDialog := TMyForm.CreateChild(self); 
// Your code
frmDialog.Show;

I have translated this answer form an article on the site DelphiPraxis.