如何检查“Z 位置” MDI 应用程序中的形式?

发布于 2024-08-10 21:40:12 字数 574 浏览 5 评论 0原文

我已经在 Delphi 中创建了 MDI 应用程序。假设我的应用程序中有一堆在屏幕上可见的 MDIChild 表单。我想对这些表单执行循环,并检查每个表单在屏幕上显示的顺序。

例如,如果我有 3 个 MDICHild 表单:

FormAFormBFormC

FormB 部分重叠 FormAFormC 部分重叠 FormB

我想将它们的 Z 属性(深度)标记如下:

FormB.Z = 2 // that form is between FormA and FormC
FormA.Z = 3 // that form's distance is longest from user, form is overlapped by FormB and 
FormC.Z = 1 // that form is at the top of all forms in my application 

感谢您的宝贵时间。

I have created MDI application in Delphi. Lets assume that I have a bunch of MDIChild forms in my application which are visible on the screen. I would like to perform a loop on those forms and check in what order each of the forms is displayed on the screen.

For example if I have 3 MDICHild forms:

FormA, FormB, FormC

and

FormB partly overlaps FormA and FormC partly overlaps FormB

I want to mark their Z property (deepth) as follows:

FormB.Z = 2 // that form is between FormA and FormC
FormA.Z = 3 // that form's distance is longest from user, form is overlapped by FormB and 
FormC.Z = 1 // that form is at the top of all forms in my application 

Thanks for your time.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

凯凯我们等你回来 2024-08-17 21:40:12

J 的答案在 Screen.Forms 中循环。这包含应用程序中的所有表单,包括非 MDI 表单,正如我从评论中看到的那样。您可以手动过滤主表单和“关于”框,但这很混乱,并且您还需要对其他表单执行相同的操作。我真的不喜欢这样做,因为它看起来很容易出错。

您的问题表明您只想知道父级中 MDI 子窗体的 z 顺序,在这种情况下,有一个更好的解决方案。

MDI 子窗体在 MDI 父窗体的 MDIChildren 属性中按 z 排序顺序列出。查找 Z 深度的代码看起来像这样(未经测试):

function FindChildDepth(Child : TForm) : Integer;
var
  i : Integer;
begin
  Result := -1; // Form not found
  for i := 0 to MDIChildCount-1 do
  begin
    if (MDIChildren[i] == Child) then
    begin
      Result := i;
      Exit;
    end;
  end;
end;

应该返回 0 到 n-1 之间的子深度,其中 0 是顶部,如果在 MDIChildren 数组中找不到该表单,则返回 -1。如果您希望“1”表示顶部而不是 0,只需将 Result 设置为 i+1 即可。

J's answer loops through Screen.Forms. This contains all forms in the application, including non-MDI ones, as I see you found from your comment. You can filter your main form and About box manually, but that's messy, and you'll also need to do the same thing for other forms. I really don't like having to do that because it seems rather error-prone.

Your question says you only want to know the z-order of MDI child forms within the parent, and in this case there's a much better solution.

MDI children are listed in z-sorted order in the MDI parent form's MDIChildren property. The code to find the Z depth would look something like this (untested):

function FindChildDepth(Child : TForm) : Integer;
var
  i : Integer;
begin
  Result := -1; // Form not found
  for i := 0 to MDIChildCount-1 do
  begin
    if (MDIChildren[i] == Child) then
    begin
      Result := i;
      Exit;
    end;
  end;
end;

That should return the depth of a child between 0 and n-1, where 0 is top, and -1 if the form is not found in the MDIChildren array. If you want "1" to mean top instead of 0, simply set Result to i+1 instead.

别念他 2024-08-17 21:40:12

使用 Screen.Forms 属性循环访问应用程序中的表单。它按 Z 顺序返回它们,完全按照您的要求。

例如,创建一个具有 1 个 MDIForm 和 3 个 MDIChild 表单的应用程序。

在主窗体上的菜单选项中,输入:

procedure TForm1.mnuFormOrder2Click(Sender: TObject);
var
  i: Integer;
  s: String;
begin
  s := '';
  for i := 0 to Pred(Screen.FormCount) do
  begin
    s := s + Screen.Forms[i].Caption+#13;
  end;

  MessageBox(Self.Handle, PChar(s),
    PChar(Self.Caption), MB_OK or MB_ICONINFORMATION or MB_TASKMODAL);
end;

这将显示一条消息,列出 Z 序列中窗体的名称。它还会列出您的主表单,但您可以将其编码出来。如果您将另一个子窗体设置为活动窗体,然后再次单击菜单选项,您将看到窗体的顺序已更改。

Use the Screen.Forms property to iterate though the forms in your application. It returns them in Z order, exactly as you want.

e.g. Create an application with 1 MDIForm and 3 MDIChild forms.

In a menu option on the main form, enter:

procedure TForm1.mnuFormOrder2Click(Sender: TObject);
var
  i: Integer;
  s: String;
begin
  s := '';
  for i := 0 to Pred(Screen.FormCount) do
  begin
    s := s + Screen.Forms[i].Caption+#13;
  end;

  MessageBox(Self.Handle, PChar(s),
    PChar(Self.Caption), MB_OK or MB_ICONINFORMATION or MB_TASKMODAL);
end;

This will show a message listing the names of the forms in their Z-sequence. It will also list your main form but you can code this out. If you make a different child form the active one, then click the menu option again, you will see the order of the forms has changed.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文