C# 中心屏幕() Winforms 设计器 屏幕位置

6

我有一个项目,其中的表单继承了一个基本表单(称为frmBase)的属性。 我遇到了一个让我非常困惑的问题:

我希望程序在用户屏幕上居中显示,所以我将

this.CenterToScreen();

添加到 frmBase_Load() 中。当我运行应用程序时,这非常有效。但是,当我尝试设计任何从 frmBase 继承的表单时,它们都会被移动到设计器屏幕的右下角,我必须使用滚动条才能看到它们。

如果我将

this.CenterToScreen();

移动到 frmBase() 代码中,则该应用程序默认在屏幕的左上角运行,但设计器可以正确地显示表单。你有什么主意吗?我搜索了一下,但似乎找不到类似的问题,虽然我知道我不可能是第一个遇到这个问题的人. . . . .


5
Load 事件也会在设计时触发。使用 if (!DesignMode) 来防止这样的代码影响程序运行。 - Hans Passant
当您在设计器中加载一个表单时,设计器会创建一个您的表单基类的实例,并使用它来托管您的表单控件。由于您的表单基类在构造函数中运行InitializeComponents中附加的事件处理程序,因此当您在设计器中打开子表单时,基本表单加载事件处理程序中的代码将运行。如@HansPassant所述,防止在设计模式下执行基本表单代码的解决方案是在基本表单的加载事件处理程序中添加if(!DesignMode) - Reza Aghaei
你可能会发现这篇文章或者这篇文章有所帮助。 - Reza Aghaei
你为什么想要将窗体居中于屏幕?你希望在运行时窗体位于屏幕中央吗? - Hitesh
此外,“DesignMode”并不总是有效。请参见这里 - Jens Kloster
@JensKloster 不错的链接,但这里它会起作用。 - Reza Aghaei
1个回答

4

根据HansReza所述,您的基类由Visual Studio表单设计器实例化,因此构造函数中的代码及其Load事件也会运行。请参见此有关设计器解析行为的详细说明。使用属性DesignMode,您可以防止代码执行或进行区分。以下代码示例演示了其用法:

基本表单

当处于DesignMode时,基本表单将背景颜色设置为红色;当不处于DesignMode时,将背景颜色设置为绿色。

// Form1 inherits from this class
public class MyBase : Form
{
    public MyBase()
    {
        // hookup load event
        this.Load += (s, e) =>
        {
            // check in which state we are
            if (this.DesignMode)
            {
                this.BackColor = Color.Red;
            }
            else
            {
                this.BackColor = Color.Green;
            }
        };
    }
}

继承基本表单的Form1

代码中没有什么魔法,但请注意使用MyBase而不是Form

// we inherit from MyBase!
public partial class Form1 : MyBase
{
    public Form1()
    {
        InitializeComponent();
    }
}

导致以下结果:

design time and runtime in one view


OP应该知道的非常重要的事情是,当前窗体的Load事件在设计时不会触发。它是基础窗体的Load事件可以并且会在设计时触发。+1您可能会发现我链接的两篇文章有所帮助。它们对设计师如何工作有一些很好的解释。此外,它们还分享了一些有趣的设计师代码示例。 - Reza Aghaei
1
@RezaAghaei 谢谢,我稍微编辑了一下答案,添加了一个链接以更清晰地表达。 - rene

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接