.NET 中是否有与 Mac OS X 文档模式表等效的内容?

发布于 2024-12-09 14:03:06 字数 527 浏览 0 评论 0原文

我的应用程序收到越来越多的请求,要求某些对话框的行为类似于 Mac OS X 文档模态表功能,其中对话框仅对父控件/对话框是模态的,而不是整个应用程序(请参阅http://en.wikipedia.org/wiki/Window_dialog)。

当前的 Windows ShowDialog() 不足以满足我的应用程序的需求,因为我需要让一个对话框成为应用程序中另一个对话框的模式,但仍然允许用户访问应用程序的其他区域。

C# .NET 中是否有与文档模式表等效的工具?或者甚至是某人已经完成的紧密实现,或者我自己尝试实现此功能?我尝试搜索谷歌和SO但无济于事。

谢谢,

凯尔

My application has been getting more and more requests to have certain dialogs behave similar to Mac OS X Document modal Sheet functionality, where a dialog is modal to just the parent control/dialog, and not the whole application (see http://en.wikipedia.org/wiki/Window_dialog).

Current windows ShowDialog() is insufficient for the needs of my application, as I need to have a dialog be modal to another dialog in the application, but still allow the user to access other areas of the application.

Is there an equivalent to Document modal Sheet in C# .NET? Or even a close implementation someone has done, or am I on my own to try and implement this functionality? I tried searching Google and SO to no avail.

Thanks,

Kyle

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

眼眸里的那抹悲凉 2024-12-16 14:03:06

重新审视这个问题后,我做了一些挖掘,找到了一个可以满足我的需求的混合解决方案。

我采纳了 p-daddy 的建议:https://stackoverflow.com/a/428782/654244

我使用建议修改了代码以适用于 32 位和 64 位编译作者:hans-passanthttps://stackoverflow.com/a/3344276/654244

结果如下:

const int GWL_STYLE   = -16;
const int WS_DISABLED = 0x08000000;

public static int GetWindowLong(IntPtr hWnd, int nIndex)
{
    if (IntPtr.Size == 4)
    {
        return GetWindowLong32(hWnd, nIndex);
    }
    return GetWindowLongPtr64(hWnd, nIndex);
}

public static int SetWindowLong(IntPtr hWnd, int nIndex, int dwNewLong)
{
    if (IntPtr.Size == 4)
    {
        return SetWindowLong32(hWnd, nIndex, dwNewLong);
    }
    return SetWindowLongPtr64(hWnd, nIndex, dwNewLong);
}

[DllImport("user32.dll", EntryPoint = "GetWindowLong", CharSet = CharSet.Auto)]
private static extern int GetWindowLong32(IntPtr hWnd, int nIndex);

[DllImport("user32.dll", EntryPoint = "GetWindowLongPtr", CharSet = CharSet.Auto)]
private static extern int GetWindowLongPtr64(IntPtr hWnd, int nIndex);

[DllImport("user32.dll", EntryPoint = "SetWindowLong", CharSet = CharSet.Auto)]
private static extern int SetWindowLong32(IntPtr hWnd, int nIndex, int dwNewLong);

[DllImport("user32.dll", EntryPoint = "SetWindowLongPtr", CharSet = CharSet.Auto)]
private static extern int SetWindowLongPtr64(IntPtr hWnd, int nIndex, int dwNewLong);


public static void SetNativeEnabled(IWin32Window control, bool enabled)
{
    if (control == null || control.Handle == IntPtr.Zero) return;

        NativeMethods.SetWindowLong(control.Handle, NativeMethods.GWL_STYLE, NativeMethods.GetWindowLong(control.Handle, NativeMethods.GWL_STYLE) &
            ~NativeMethods.WS_DISABLED | (enabled ? 0 : NativeMethods.WS_DISABLED));
}

public static void ShowChildModalToParent(IWin32Window parent, Form child)
{
    if (parent == null || child == null) return;

    //Disable the parent.
    SetNativeEnabled(parent, false);

    child.Closed += (s, e) =>
    {
        //Enable the parent.
        SetNativeEnabled(parent, true);
    };

    child.Show(parent);
}

After revisiting this issue, I did some digging and found a hybrid solution that will work for my needs.

I took the suggestion by p-daddy: https://stackoverflow.com/a/428782/654244

And I modified the code to work for 32-bit and 64-bit compiles using the suggestion by hans-passant: https://stackoverflow.com/a/3344276/654244

The result is the following:

const int GWL_STYLE   = -16;
const int WS_DISABLED = 0x08000000;

public static int GetWindowLong(IntPtr hWnd, int nIndex)
{
    if (IntPtr.Size == 4)
    {
        return GetWindowLong32(hWnd, nIndex);
    }
    return GetWindowLongPtr64(hWnd, nIndex);
}

public static int SetWindowLong(IntPtr hWnd, int nIndex, int dwNewLong)
{
    if (IntPtr.Size == 4)
    {
        return SetWindowLong32(hWnd, nIndex, dwNewLong);
    }
    return SetWindowLongPtr64(hWnd, nIndex, dwNewLong);
}

[DllImport("user32.dll", EntryPoint = "GetWindowLong", CharSet = CharSet.Auto)]
private static extern int GetWindowLong32(IntPtr hWnd, int nIndex);

[DllImport("user32.dll", EntryPoint = "GetWindowLongPtr", CharSet = CharSet.Auto)]
private static extern int GetWindowLongPtr64(IntPtr hWnd, int nIndex);

[DllImport("user32.dll", EntryPoint = "SetWindowLong", CharSet = CharSet.Auto)]
private static extern int SetWindowLong32(IntPtr hWnd, int nIndex, int dwNewLong);

[DllImport("user32.dll", EntryPoint = "SetWindowLongPtr", CharSet = CharSet.Auto)]
private static extern int SetWindowLongPtr64(IntPtr hWnd, int nIndex, int dwNewLong);


public static void SetNativeEnabled(IWin32Window control, bool enabled)
{
    if (control == null || control.Handle == IntPtr.Zero) return;

        NativeMethods.SetWindowLong(control.Handle, NativeMethods.GWL_STYLE, NativeMethods.GetWindowLong(control.Handle, NativeMethods.GWL_STYLE) &
            ~NativeMethods.WS_DISABLED | (enabled ? 0 : NativeMethods.WS_DISABLED));
}

public static void ShowChildModalToParent(IWin32Window parent, Form child)
{
    if (parent == null || child == null) return;

    //Disable the parent.
    SetNativeEnabled(parent, false);

    child.Closed += (s, e) =>
    {
        //Enable the parent.
        SetNativeEnabled(parent, true);
    };

    child.Show(parent);
}
与他有关 2024-12-16 14:03:06

Form.ShowDialog 方法允许您调用时指定所有者。在这种情况下,该表单仅对给定所有者而言是模态的。

编辑:我尝试过,结果好坏参半。我创建了一个简单的 Windows 窗体应用程序,其中包含一个主窗体和另外两个窗体。通过单击主窗体上的按钮,我使用 Show 方法打开了 Form2。 Form2 上也有一个按钮,单击时,我使用 ShowDialog 方法打开 Form3,并传入 Form2 作为其所有者。虽然 Form3 似乎确实是 Form2 的模式,但在关闭 Form3 之前我无法切换回 Form1。

The Form.ShowDialog method allows you to specify an owner when you call it. In this case the form is modal only to the given owner.

EDIT: I tried this with mixed results. I created a simple Windows Forms app with a main form, and two others. From a button click on the main form, I opened Form2 using the Show method. Form2 has a button on it as well, and when clicked, I opened Form3 using the ShowDialog method, passing in Form2 as it's owner. While Form3 did seem to be modal to Form2, I could not switch back to Form1 until I closed Form3.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文