C# “如何改变”;这是“ShowInTaskBar”;对于一个;form.ShowDialog();在保持开放的同时?

C# “如何改变”;这是“ShowInTaskBar”;对于一个;form.ShowDialog();在保持开放的同时?,c#,.net,winforms,C#,.net,Winforms,如果您在一个新的winform应用程序中运行这段代码(将其放在form1中),该应用程序包含2个表单 private void Form1_Load(object sender, EventArgs e) { Form2 newForm = new Form2(); Button b = new Button(); newForm.Controls.Add(b); b.Click += new EventHandle

如果您在一个新的winform应用程序中运行这段代码(将其放在form1中),该应用程序包含2个表单

    private void Form1_Load(object sender, EventArgs e)
    {
        Form2 newForm = new Form2();
        Button b = new Button();
        newForm.Controls.Add(b);
        b.Click += new EventHandler(click);
        this.Show();
        newForm.ShowDialog();

    }

    private void click(object sender, EventArgs e)
    {
        ((Form)((Control)sender).Parent).ShowInTaskbar = false;
    }
点击新表单(应该是form2)上的按钮,form2将关闭


如何保持开放?

我不太清楚你的问题。无论如何,
newForm
表单显示为一个模式对话框,这意味着它会阻止用户使用父表单,直到它关闭为止。模式对话框通常有一些按钮,可以自动关闭它们,并将
OK
Cancel
返回到调用窗体(作为
ShowDialog
的返回值)。这是使用完成的,因此,如果为按钮设置了此属性,这可能是当您单击模态窗体时它关闭的原因


如果您希望以允许用户同时使用这两个窗体的方式显示更多窗体,则需要使用无模式对话框。这是一个。

在ShowDialog()之前,通过将ShowInTaskbar设置为false来保持其打开状态

或者就是不要把第二种形式变成模态。这也行得通

private void Form1_Load(object sender, EventArgs e)
{
    Form2 newForm = new Form2();
    Button b = new Button();
    newForm.Controls.Add(b);
    b.Click += new EventHandler(click);
    this.Show();

    newForm.Show();
}
我不知道这里的具体机制,但很明显,更改标志(实际上更改了一个或多个WS_EX_xxx窗口样式)会导致ShowDialog()的模式泵退出。这反过来导致您(最终!)退出Form1\u加载,然后您的新表单超出范围并被销毁

因此,您的问题是ShowDialog()的组合以及您没有准备好让ShowDialog()永远退出的事实

现在,的模式首先不应该显示任务栏图标,应用程序及其所有模式窗体实际上应该只有一个任务栏图标,因为当模式窗体运行时,主窗体仍然被禁用。当主窗体最小化时,它拥有的所有模态窗体都将隐藏,等等


因此,如果你真的希望第二个表单是模态的,你不应该给用户一个任务栏图标。如果使用ShowDialog()只是测试代码,那么不用担心。当窗体在主应用泵上运行时,问题将消失。

这是不可能的。事实上,我在微软的反馈网站上提交了一份关于这件事的报告,但他们向我透露了这件事

诚然,这是一个需要解决的棘手问题,更改属性需要Windows窗体从头开始重新创建窗口,因为它由样式标志控制。只能在带有dwExStyle参数的调用中指定的类型。按照ShowDialog()方法调用的要求,重新创建窗口很难使其保持模态


Windows窗体克服了许多User32限制。但不是那个。

怎么。。。我的。。。这是一个丑陋的黑客

这项工作

    private void Form1_Load(object sender, EventArgs e)
    {
        Form2 newForm = new Form2();
        Button b = new Button();
        newForm.Controls.Add(b);
        b.Click += new EventHandler(click);
        newForm.FormClosed += new FormClosedEventHandler(form2_closed);
        newForm.FormClosing += new FormClosingEventHandler(form2_closing);
        this.Show();
        do
        {
          newForm.ShowDialog();
        } while (newForm.IsDisposed == false );               
    }

    private void click(object sender, EventArgs e)
    {
        ((Form)((Control)sender).Parent).ShowInTaskbar = !((Form)((Control)sender).Parent).ShowInTaskbar;
    }

    private void form2_closed(object sender, FormClosedEventArgs e)
    {
        ((Form)sender).Dispose();
    }

    private void form2_closing(object sender, FormClosingEventArgs e)
    {
        if (e.CloseReason == CloseReason.None)
            e.Cancel = true;
    }

我的问题是,如何保留一个设置为显示为对话框的窗体,并将其从任务栏中删除,而不使窗体自动关闭这是一个示例,用户可以从form2中的菜单更改该变量的状态,它不是自动关闭的setting@Fredu你的问题来了。在窗口已经创建之后更改此活动是没有意义的。在任何情况下,如果第二个表单不是模态的,它不会在你改变旗子时消失。看看我自己的答案,一个丑陋的解决方法,我不制定规范,我实现它们:-(@Fredou:如果你告诉我什么应用程序。我很乐意提交一份关于滥用任务栏图标的错误报告;)事情是,这种模态形式可以在任务栏、任务栏或两者之间,这是错误的。模式窗体和任务栏图标不能混合使用。我同意你的观点,但我不制定规范,我希望有一天我能做到。问题不仅在于你违反了惯例,还在于你依赖于未定义的或有缺陷的行为。例如,你可能会发现这在所有版本的Windows上都不起作用。@Fredou:你说得很对,这是fugly妈妈说的。但这是我的荣幸。尽管如此,请尝试遵循常见的UI准则,对话框不应设置其ShowInTaskbar属性。
    private void Form1_Load(object sender, EventArgs e)
    {
        Form2 newForm = new Form2();
        Button b = new Button();
        newForm.Controls.Add(b);
        b.Click += new EventHandler(click);
        newForm.FormClosed += new FormClosedEventHandler(form2_closed);
        newForm.FormClosing += new FormClosingEventHandler(form2_closing);
        this.Show();
        do
        {
          newForm.ShowDialog();
        } while (newForm.IsDisposed == false );               
    }

    private void click(object sender, EventArgs e)
    {
        ((Form)((Control)sender).Parent).ShowInTaskbar = !((Form)((Control)sender).Parent).ShowInTaskbar;
    }

    private void form2_closed(object sender, FormClosedEventArgs e)
    {
        ((Form)sender).Dispose();
    }

    private void form2_closing(object sender, FormClosingEventArgs e)
    {
        if (e.CloseReason == CloseReason.None)
            e.Cancel = true;
    }