1

在我们的应用程序中,我们有从 VB6 COM 组件打开 .NET 表单的业务需求。就 VB6 应用程序而言,子窗体基本上应该像 ShowDialog() 那样工作,但 .NET 应用程序应该保持解锁状态。

为了处理这个问题,我使用 Show(IWin32Window) 重载 + EnableWindow(hwnd, False) 方法来设置 .NET 表单的父级并禁用所有者 VB6 表单。

但是,我有两个问题:

  1. 由于某种原因,菜单仍部分启用。我无法单击菜单,但 ALT 快捷方式仍在工作。例如,我可以使用 ALT+F 打开“文件”菜单,然后向下箭头到“关闭”菜单项以关闭屏幕。其他一切都被正确禁用(即,我无法单击任何菜单/控件或在任何地方键入任何内容)。我需要做其他事情来禁用菜单快捷方式吗?

  2. 我仍然可以单击 VB6 表单。当您使用 ShowDialog() 时,所有者窗体会闪烁几次并将焦点重置到子窗体,但 EnableWindow 不会发生这种情况。我可以进行另一个 PInvoke 调用来伪造 ShowDialog() 功能吗?每当 VB6 窗口获得焦点时,有没有办法将焦点集中在 .NET 窗口上?

编码:

<DllImport("user32.dll")>
Public Shared Function EnableWindow(hwnd As IntPtr, bEnable As Boolean) As Boolean
End Function

<DllImport("user32.dll", SetLastError:=True)> _
Private Shared Function GetForegroundWindow() As IntPtr
End Function

Public Class WindowWrapper
    Implements IWin32Window

    Private _handle As IntPtr

    Public Sub New(handle As IntPtr)
        _handle = handle
    End Sub

    Public ReadOnly Property Handle As System.IntPtr Implements IWin32Window.Handle
        Get
            Return _handle
        End Get
    End Property
End Class

Dim foregroundWindowId As IntPtr = GetForegroundWindow()
Dim vb6Process As Process = Process.GetProcessById(VB6ProcessId)
Dim ownerWindow As WindowWrapper = New WindowWrapper(foregroundWindowId)

EnableWindow(foregroundWindowId, False)
Show(ownerWindow)
4

0 回答 0