Link to home
Start Free TrialLog in
Avatar of Rob Rietow
Rob Rietow

asked on

Controlling the Width of Delphi's MessageDlgPos

Is there a way to control Delphi's MessageDlgPos width?  I have an app on a handheld device and the MessageDlgPos width exceeds the width of the screen, making some of the dialog box not appear on the screen.
Avatar of Ferruccio Accalai
Ferruccio Accalai
Flag of Italy image

I guess that using MessageDlgPos the matter is not the screen width but the dialog position that may be greater than the screen width.  What about a screen.width check before the call and in case of certain width call MessagedlgPos with 0 for x and y, that means centered on screen?
Avatar of Rob Rietow
Rob Rietow

ASKER

The "default" size of the MessageDlgPos box is greater than the screen width I am using.  I am looking for a way to make the width of the MessageDlgPos box smaller.
However if you want to control a Message Dialog Form you can create your own function to adjust anything using CreateMessageDialog procedure from Dialogs.
Here's an example on how you may control your Message Dialog.
The function can be called as you call MessageDlgPos, but if you declare also a dialog width then the Dialog is redesigned according to it, otherwise the Default MessageDlgPos is called.

function MyMessageDlgPos(const Msg: string; DlgType: TMsgDlgType; Buttons: TMsgDlgButtons; HelpCtx: Longint; X, Y: Integer;
  DlgWidth: Integer = 0): Integer;
var
  Form: TForm;
  Lbl: TLabel;
  i, deltaW, lblH: Integer;
  btn: TButton;
  TextRect: Trect;
begin
  if DlgWidth > 0 then
  begin
    Form := CreateMessageDialog(Msg, mtConfirmation, Buttons);
    try
      Lbl := TLabel(Form.FindComponent('Message'));
      SetRect(TextRect, Lbl.left, Lbl.top, DlgWidth-32, 0);
      DrawText(Form.Canvas.Handle, Msg, Length(Msg)+1, TextRect,
        DT_EXPANDTABS or DT_CALCRECT or DT_WORDBREAK or Lbl.DrawTextBiDiModeFlagsReadingOnly);
      deltaW := Form.ClientWidth - DlgWidth;
      Form.ClientWidth := DlgWidth;
      Lbl.width := Lbl.width-deltaW;
      lblH := Lbl.Height;
      Lbl.BoundsRect := TextRect;
      for i := 0 to Form.ControlCount-1 do
        if Form.Controls[i] is TButton then
        begin
          TButton(Form.Controls[i]).left := TButton(Form.Controls[i]).left - (deltaW div 2);
          TButton(Form.Controls[i]).top := TButton(Form.Controls[i]).top+Lbl.Height-lblH;
        end;
      Form.ClientHeight := Form.ClientHeight+Lbl.Height-lblH;
      if X >= 0 then
        Form.left := X;
      if Y >= 0 then
        Form.top := Y;
      if (Y < 0) and (X < 0) then
        Form.Position := poScreenCenter;
      Form.HelpContext := HelpCtx;
      Result := Form.ShowModal;
    finally
      Form.Free;
    end;
  end
  else
    Result := MessageDlgPos(Msg, DlgType, Buttons, HelpCtx, X, Y);
end;

Open in new window

You can use it as follows
procedure TForm1.Button1Click(Sender: TObject);
begin
  // Show a confirmation dialog at 20,100 with a dialog width of 500
  If MyMessageDlgPos(
    'Is there a way to control Delphi''s MessageDlgPos width? I have an app on a handheld device and the MessageDlgPos width exceeds the width of the screen, making some of the dialog box not appear on the screen.'+#13+'However this is a try, not necessarily a solution!', mtConfirmation, mbYesNo, 0, 20, 100, 500) = mrYes then
    ShowMessage('Yes pressed')
  else
    ShowMessage('NO pressed');
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
  // Show a confirmation dialog at 20,100 without passing a dialog width
  If MyMessageDlgPos(
    'Is there a way to control Delphi''s MessageDlgPos width? I have an app on a handheld device and the MessageDlgPos width exceeds the width of the screen, making some of the dialog box not appear on the screen.'+#13+'However this is a try, not necessarily a solution!', mtConfirmation, mbYesNo, 0, 20, 100) = mrYes then
    ShowMessage('Yes pressed')
  else
    ShowMessage('NO pressed');
end;

Open in new window

ASKER CERTIFIED SOLUTION
Avatar of Ferruccio Accalai
Ferruccio Accalai
Flag of Italy image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Thanks for the above solution. Works great. Now I want to do something similar with the ShowMessageDlgPos.  I tried using the code above and got syntaxed on the CreateMessageDlg.. Seems I need to use something else? I don't normally code at this level.

Procedure FIFShowMessageDlgPos(const msg: string; X,Y: integer; FWidth: integer);
var
  Form: TForm;
  lbl: TLabel;
  i, deltaW, lblH: Integer;
  btn: TButton;
  TextRect: Trect;
begin
    Form := CreateMessageDialog(Msg, mtConfirmation, buttons);   <<<<<< Syntaxed here
    try
      Lbl := TLabel(Form.FindComponent('Message'));
      SetRect(TextRect, Lbl.left, Lbl.top, FWidth-32, 0);
      DrawText(Form.Canvas.Handle, Msg, Length(Msg)+1, TextRect,
        DT_EXPANDTABS or DT_CALCRECT or DT_WORDBREAK or Lbl.DrawTextBiDiModeFlagsReadingOnly);
      deltaW := Form.ClientWidth - FWidth;
      Form.ClientWidth := FWidth;
      Lbl.width := Lbl.width-deltaW;
      lblH := Lbl.Height;
      Lbl.BoundsRect := TextRect;
      for i := 0 to Form.ControlCount-1 do
        if Form.Controls[i] is TButton then
        begin
          TButton(Form.Controls[i]).left := TButton(Form.Controls[i]).left - (deltaW div 2);
          TButton(Form.Controls[i]).top := TButton(Form.Controls[i]).top+Lbl.Height-lblH;
        end;
      Form.ClientHeight := Form.ClientHeight+Lbl.Height-lblH;
      if X >= 0 then
        Form.left := X;
      if Y >= 0 then
        Form.top := Y;
      if (Y < 0) and (X < 0) then
        Form.Position := poScreenCenter;
    finally
      Form.Free;
    end;
end;

SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Thanks again!  You are the best.