【问题标题】:Win api MessageBox alternative that has a set for text-align: centerWin api MessageBox 替代方案,具有一组 text-align: center
【发布时间】:2015-05-02 15:27:35
【问题描述】:

我通过搜索发现,无法使用居中对齐的文本创建 MessageBox()

那么是否有一些简单的替代方法提供 MessageBox() 功能(包括程序等待关闭/接受框),可以选择居中对齐文本?

感谢您的建议/示例。

PS:在 Windows7+ 上,使用 C++ Windows API(在 MS Visual Studio 2012 中编译)

编辑:
一些有用的提示:
1) Visual Studio Express 版本没有资源编辑器/文件创建选项:

2)Visual Studio C++ how to display a dynamic message (i.e., string) in my About box?

【问题讨论】:

    标签: c++ winapi messagebox text-alignment


    【解决方案1】:

    我通过搜索发现,无法使用居中对齐的文本创建 MessageBox()。

    无法创建居中对齐的MessageBox() 对话框,因为 API 没有为此提供选项。但是可以操纵标准 MessageBox()` 对话框通过一些小技巧来强制它居中对齐。

    使用SetWindowsHookEx() 为调用MessageBox() 的线程创建一个WH_CBT 挂钩(不需要DLL)。 hook callback 允许您发现 MessageBox() 创建的对话框的 HWND。有了它,你可以随心所欲地操纵它。在这种情况下,您可以使用FindWindowEx() 获取对话框文本的STATIC 控件的HWND,然后使用SetWindowLong() 对其应用SS_CENTER 样式。例如:

    LRESULT CALLBACK CenterMsgBoxTextProc(int nCode, WPARAM wParam, LPARAM lParam)
    {
        if (nCode == HCBT_ACTIVATE)
        {
            HWND hDlg = (HWND) wParam;
            HWND hTxt = FindWindowEx(hDlg, NULL, TEXT("STATIC"), NULL);
            if (hTxt)
                SetWindowLong(hTxt, GWL_STYLE, GetWindowLong(hTxt, GWL_STYLE) | SS_CENTER);
        }
    
        return CallNextHookEx(NULL, nCode, wParam, lParam);
    }
    

    HHOOK hHook = SetWindowsHookEx(WH_CBT, (HOOKPROC) &CenterMsgBoxTextProc, NULL, GetCurrentThreadId());
    MessageBox(...);
    if (hHook) UnhookWindowsHookEx(hHook);
    

    或者,您可以使用SetWinEventHook() 代替SetWindowsHookEx()

    void CALLBACK CenterMsgBoxTextProc(HWINEVENTHOOK hWinEventHook, DWORD event, HWND hwnd, LONG idObject, LONG idChild, DWORD dwEventThread, DWORD dwmsEventTime)
    {
        HWND hTxt = FindWindowEx(hwnd, NULL, TEXT("STATIC"), NULL);
        if (hTxt)
            SetWindowLong(hTxt, GWL_STYLE, GetWindowLong(hTxt, GWL_STYLE) | SS_CENTER);
    }
    

    HWINEVENTHOOK hHook = SetWinEventHook(EVENT_OBJECT_CREATE, EVENT_OBJECT_CREATE, NULL, &CenterMsgBoxTextProc, GetCurrentProcessId(), GetCurrentThreadId(), 0);
    MessageBox(NULL, TEXT("test"), TEXT("test"), MB_OK);
    if (hHook) UnhookWinEvent(hHook);
    

    以下是两种情况下的结果:

    【讨论】:

    • 棘手,但很有用,是我自己还是有点偏离中心? (不过没关系......)无论如何我是对的,你不能创建这样的 MessageBox 但你可以在创建后强制它:)
    • 文本在STATIC 控件的宽度内居中,但默认情况下控件本身不会延伸到对话框的整个宽度。但是,由于可以同时获取两个 HWND,因此可以查询对话框的客户端宽度,并根据需要调整控件的宽度。
    • 以这种方式操作MessageBox() HWND 是人们习惯于在MessageBoxTimeout() 成为标准功能之前实现它,或者向对话框添加自定义控件(例如“记住这个选项”类型复选框),或自定义按钮文本等。
    【解决方案2】:

    Afaik 没有。但实际上使用 Win32 资源和DialogBox function 创建这样一个对话框非常容易。

    【讨论】:

    • 是的,我提到了类似的东西,你能提供和示例如何在 DialogBox 中居中文本吗?
    • 您只需在对话框中放置一个 STATIC 控件并为其指定 StyleSS_CENTER。搜索“Win32 example rc”应该会给你一个例子。此外,如果您使用 MSVC,您可以一起单击对话框并在静态控件上设置该样式。
    • 对不起,我在这里有点迷路了,如何将 STATIC 控件添加到 dialogBox ?我就是找不到,
    • transmissionzero.co.uk/computing/win32-apps-with-mingw 查找“关于对话框”部分。 This 告诉我还有一个用于居中文本的 CTEXT 元素。我也不能给你一个具体的例子,因为我目前在 Linux 上。
    • 抱歉,不,编写自己的MessageBox 版本一点也不容易。它不仅仅是显示一个对话框。例如,当按下 [Ctrl]+C 时,标准的 MessageBox 会将其内容的文本版本呈现到剪贴板。不止眼前一亮。
    猜你喜欢
    • 2018-07-01
    • 2016-07-15
    • 2012-03-18
    • 2019-12-23
    • 1970-01-01
    • 2015-07-16
    • 1970-01-01
    • 2015-01-17
    • 2014-10-02
    相关资源
    最近更新 更多