在窗口可见后将其设置为模态窗口

4
有没有可能在窗口可见后在模态和非模态之间切换?
这就是我所需要的...调用一个方法并传递窗口句柄,设置是否要使其成为模态。
如果可能的话,任何示例都将对此有很大帮助!
.net、c++等技术都可以。
谢谢!
编辑: 为什么需要这么做呢? 在这种情况下,我正在使用TWAIN扫描图像,并且“某些”数据源不会将其对话框显示为模态,即使我将其设置为这样做,如果它不是模态的,用户也可以在后台窗口中进行操作...
4个回答

2

窗口模态主要由窗口句柄所有权驱动。禁用父窗口并设置本地消息循环是次要的副作用。

将模态窗口句柄的所有者设置为应用程序主窗口会创建这样的行为:单击主窗口会将焦点发送到模态子窗口。如果没有正确设置所有者,则在“模态”窗口显示时可以聚焦主窗口,这不是模态行为。

我似乎隐约记得,您还需要禁用所有者窗口,以防止在模态窗口处于活动状态时鼠标单击按钮或选择菜单。

模态窗口通常也与本地消息循环相关联,但这与窗口的模态UI行为几乎没有关系,而与执行代码的模态状态有关。在Form.ShowDialog()内运行本地消息循环使函数调用与模态窗口生命周期同步 - 它防止函数在模态窗口关闭之前返回给调用者。

只有在创建子窗口句柄时才能设置窗口句柄的所有者。在子窗口句柄存在后无法更改所有者。请参阅MSDN上的Owned Windows

因此,您不能简单地切换并使非模态窗口变为模态窗口。

最好的方法是销毁窗口句柄并使用所需的所有者重新创建它。这可以在很少或没有屏幕闪烁的情况下完成,但更大的问题是保留子控件上的任何本地状态(编辑框中的文本,复选框状态等)。销毁窗口将丢失子窗口中的任何状态信息,因此您需要确保先提取所有状态,然后重新创建窗口句柄,然后在其后恢复子窗口数据。


0
我想知道为什么楼主会问这个问题,但这让我开始思考。我有一些东西可能是找到答案的开端。
我创建了两个表单:Form1和Form2。Form1有一个按钮;Form2有一个文本框。
我尝试了以下代码用于Form1:
    private void button_Click(object sender, EventArgs e)
    {
        form2.Show(this);            
        System.Threading.Thread thread = new System.Threading.Thread(showModal);
        thread.Start();
    }        

    private void showModal()
    {
        System.Threading.Thread.Sleep(2000);
        form2.Visible = false;
        form2.ShowDialog(this);
    }

当单击Form1上的按钮时,它会将Form2显示为非模态框;等待两秒钟;然后隐藏Form2,再将其显示为模态框。如果在切换之前在Form2的文本框中键入文本,则文本将被保留。但是,当我单击Form2右上角的x时,无法关闭它。由于它是模态的,我必须通过任务管理器来终止程序。

0

你不能通过标准WinAPI来实现这个功能,我相信使用.NET框架也无法实现。不过,你可以通过创建自己的消息泵例程来模拟实现从非模态切换到模态。 然而,这似乎是对错误问题的回答。你能否澄清一下为什么需要在模态和非模态之间切换?


0

使用.NET Framework,我不知道有什么方法可以实现这样的行为。在.NET中,使窗体成为非模态或模态的方式是通过分别使用Form.Show()Form.ShowDialog()方法来显示它。

我不明白为什么需要将其显示为非模态,然后再将其设置为模态。你试图完成什么?也许提供更多细节可以帮助我们帮助你或找到其他更好的解决方案,我希望。


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