Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/300.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在MDI子对象的中心显示对话框_C#_Winforms_Centering_Mdi - Fatal编程技术网

C# 在MDI子对象的中心显示对话框

C# 在MDI子对象的中心显示对话框,c#,winforms,centering,mdi,C#,Winforms,Centering,Mdi,免责声明:我知道已经为类似的问题提供了答案,但是这些似乎对我不起作用 我有一个应用程序,它使用MDI客户端的主窗体;我想显示一个对话框,允许用户输入一个值;此对话框将显示在调用该对话框的子窗体的中心 我已经研究了以下解决方案: 然而,除非我的解决方案与应用程序相关,否则这似乎有一些基本问题 建议采取以下措施来实现这一目标: private void OpenForm(Form parent) { FormLoading frm = new FormLoading(); frm.

免责声明:我知道已经为类似的问题提供了答案,但是这些似乎对我不起作用

我有一个应用程序,它使用MDI客户端的主窗体;我想显示一个对话框,允许用户输入一个值;此对话框将显示在调用该对话框的子窗体的中心

我已经研究了以下解决方案:

然而,除非我的解决方案与应用程序相关,否则这似乎有一些基本问题

建议采取以下措施来实现这一目标:

private void OpenForm(Form parent)
{
    FormLoading frm = new FormLoading();
    frm.Parent = parent;
    frm.StartPosition = FormStartPosition.CenterParent;
    frm.ShowDialog();
}
然而,这有以下问题:

当我尝试实现这一点时,在单步执行代码时,只要它到达设置表单父级的行,就会发生以下异常:

Top-level control cannot be added to a control.
注意:除非所有表单都使用顶级值
true
初始化,否则该值似乎不会在任何地方设置

好,那么,;我们将TopLevel设置为
false
,以允许将父窗体设置为对话框的父窗体。假设我这样做,当它到达
ShowDialog()
的行时:

这就是我的泥潭;对话框窗体似乎不需要是顶级窗体才能拥有父级,但同时需要是顶级窗体,以便可以显示为对话框


最后请注意,我不认为我应该设置我想要作为对话框的表单的“StartPosition”,因为这已经在表单的
InitializeComponent()
部分中设置;尽管如此,我还是尝试在函数中显式设置它,但没有任何区别。

您可以手动定位对话框窗体:

    private void invokeDialogButton_Click(object sender, EventArgs e)
    {
        var dialogForm = new DialogForm();
        dialogForm.StartPosition = FormStartPosition.Manual;

        //Get the actual position of the MDI Parent form in screen coords
        Point screenLocation = Parent.PointToScreen(Parent.Location);

        //Adjust for position of the MDI Child form in screen coords
        screenLocation.X += Location.X;
        screenLocation.Y += Location.Y;

        dialogForm.Location = new Point(screenLocation.X + (Width - dialogForm.Width) / 2, 
                                        screenLocation.Y + (Height - dialogForm.Height) / 2);

        dialogForm.ShowDialog(this);
    }

请在我的Github页面(Visual Studio 2015社区版项目)上查看这一点。

您好,ShowDialog过载,无法设置表单的所有者/父级。您需要在设计时或在运行时的Form Load事件中使用from自身设置FormLoading的开始位置;我尝试过使用重载,但仍然被告知无法将非顶级表单显示为对话框。我已经尝试在构造函数、Load事件和Showed事件中将StartPosition设置为CentreParent,但这对位置没有影响;如果仍然显示在屏幕中央,即认为主窗体仍然是父窗体。这种方式在对话框几乎居中时起作用;但是,每次生成对话框时,它似乎会稍微向下和向右移动?我已经仔细阅读了代码,子窗体的Location属性没有改变,但PointToScreen每次都返回不同的X和Y值,即使它具有相同的输入值?我在MDI子窗体中添加了一个按钮(而不是通过
form\u show
事件处理程序加载),因此我可以在不同的位置进行检查。我没有看到您描述的
指向屏幕的行为不一致;然而,我确实在我的答案中发现了一个bug(当MDI子对象从起点显著移动时,这一点很明显)。我用正确的代码更新了我的答案。我修复了对话框每次显示时都会轻微移动的问题,并且我还实现了您对答案所做的添加;不幸的是,似乎正在发生的是,表单的一个小的移动会导致对话框的一个更大的移动。例如,当表单位于左上角的右上角时,对话框出现在表单中心附近;但是,当您将表单移动到屏幕的一半时,对话框将显示在屏幕之外!如果有一种上传视频的方法,我可以用更好的方式来演示……只要确保-你看到我改变了获取
screenLocation
的方式,对吗?我在我的回答中发布了一个指向工作代码示例(Github repo)的链接,看看您是否可以将其应用于您的项目。我测试了移动MDI父窗口和父窗口中的MDI子窗口,等等-对话框居中显示。
    private void invokeDialogButton_Click(object sender, EventArgs e)
    {
        var dialogForm = new DialogForm();
        dialogForm.StartPosition = FormStartPosition.Manual;

        //Get the actual position of the MDI Parent form in screen coords
        Point screenLocation = Parent.PointToScreen(Parent.Location);

        //Adjust for position of the MDI Child form in screen coords
        screenLocation.X += Location.X;
        screenLocation.Y += Location.Y;

        dialogForm.Location = new Point(screenLocation.X + (Width - dialogForm.Width) / 2, 
                                        screenLocation.Y + (Height - dialogForm.Height) / 2);

        dialogForm.ShowDialog(this);
    }