C# と VB.NET の質問掲示板

ASP.NET、C++/CLI、Java 何でもどうぞ

C# と VB.NET の入門サイト

Re[2]: メッセージボックスの閉じるボタンを無効にしたい


(過去ログ 172 を表示中)

[トピック内 7 記事 (1 - 7 表示)]  << 0 >>

■99309 / inTopicNo.1)  メッセージボックスの閉じるボタンを無効にしたい
  
□投稿者/ ラルフ (1回)-(2022/03/08(Tue) 19:01:53)

分類:[C#] 

MessageBox.Showでポップアップしたメッセージボックスの右上の×ボタンを無効にするにはどうすればいいですか?
フォームアプリケーションで作成しています。
引用返信 編集キー/
■99310 / inTopicNo.2)  Re[1]: メッセージボックスの閉じるボタンを無効にしたい
□投稿者/ furu (147回)-(2022/03/08(Tue) 19:32:15)
No99309 (ラルフ さん) に返信
> MessageBox.Showでポップアップしたメッセージボックスの右上の×ボタンを無効にするにはどうすればいいですか?
ボタンは何を表示していますか?

無効にする方法は知りませんが
以下のルールで無効になるようです。

MessageBoxButtons.YesNo
MessageBoxButtons.AbortRetryIgnore
のようなCancelが無い場合、×ボタンは無効

但し
MessageBoxButtons.OK
のようにボタンが1つだけだと×ボタンは有効
引用返信 編集キー/
■99311 / inTopicNo.3)  Re[2]: メッセージボックスの閉じるボタンを無効にしたい
□投稿者/ ラルフ (2回)-(2022/03/08(Tue) 20:03:11)
No99310 (furu さん) に返信
> ボタンは何を表示していますか?
>
> 無効にする方法は知りませんが
> 以下のルールで無効になるようです。
>
> MessageBoxButtons.YesNo
> MessageBoxButtons.AbortRetryIgnore
> のようなCancelが無い場合、×ボタンは無効
>
> 但し
> MessageBoxButtons.OK
> のようにボタンが1つだけだと×ボタンは有効

MessageBoxButtons.OKだけです。
なので困っています。

引用返信 編集キー/
■99312 / inTopicNo.4)  Re[3]: メッセージボックスの閉じるボタンを無効にしたい
□投稿者/ furu (148回)-(2022/03/08(Tue) 20:32:53)
No99311 (ラルフ さん) に返信
> MessageBoxButtons.OKだけです。
> なので困っています。
困るというのは表示されていることが気になるのですか?

OKだけの場合、2つ3つから好きなの選べというのではなく
お知らせを表示しているだけです。

このOKだけの場合ですが
×ボタンはOKボタンとまったく同じ動作で
いずれもDialogResult.OKを返しますので
どちらをクリックされても処理に影響はありません。
引用返信 編集キー/
■99313 / inTopicNo.5)  Re[1]: メッセージボックスの閉じるボタンを無効にしたい
□投稿者/ 魔界の仮面弁士 (3305回)-(2022/03/08(Tue) 20:36:53)
No99309 (ラルフ さん) に返信
> MessageBox.Showでポップアップしたメッセージボックスの右上の×ボタンを無効にするにはどうすればいいですか?
> フォームアプリケーションで作成しています。

Windows の標準仕様なので、他のアプリケーションとの統一性という意味では
あまり手を加えるべきでは無いと思いますが…どうしても必要なのであれば、
サブクラス化して SC_CLOSE を DeleteMenu することで無効化できます。

以下は VB6 のサンプルですが、参考までに。
https://www.vbforums.com/showthread.php?866647-MessageBox-without-Red-X-close-button


あるいは No99265 のような「自作メッセージボックス」に切り替えるという別案とか。
引用返信 編集キー/
■99314 / inTopicNo.6)  Re[2]: メッセージボックスの閉じるボタンを無効にしたい
□投稿者/ KOZ (228回)-(2022/03/09(Wed) 01:12:31)
No99313 (魔界の仮面弁士 さん) に返信
> 以下は VB6 のサンプルですが、参考までに。
> https://www.vbforums.com/showthread.php?866647-MessageBox-without-Red-X-close-button

.NET のサンプルが意外に見つからなかったので URL を参考にサンプルを書いてみました。
こんな感じで使います。

using (var remover = new CloseButtonRemover()) {
    MessageBox.Show("TEST");
}

以下クラスです。

using Microsoft.Win32.SafeHandles;
using System;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;

class CloseButtonRemover : SafeHandleZeroOrMinusOneIsInvalid
{
    readonly HookProcDelegate hookProcDelegate;
    readonly MessageBoxWindow messageBoxWindow = new MessageBoxWindow();

    public CloseButtonRemover() : base(true) {
        hookProcDelegate = new HookProcDelegate(HookProc);
        handle = SetWindowsHookEx(WH_CALLWNDPROC, hookProcDelegate, IntPtr.Zero, GetCurrentThreadId());
    }

    protected override bool ReleaseHandle() {
        return UnhookWindowsHookEx(handle);
    }

    private IntPtr HookProc(int code, IntPtr wp, IntPtr lp) {
        var cwp = Marshal.PtrToStructure<CWPSTRUCT>(lp);
        if (cwp.message == WM_CREATE) {
            var sb = new StringBuilder(128);
            GetClassName(cwp.hwnd, sb, sb.Capacity);
            if (sb.ToString() == "#32770") {
                messageBoxWindow.AssignHandle(cwp.hwnd);
            }
        }
        return CallNextHookEx(handle, code, wp, lp);
    }

    class MessageBoxWindow : NativeWindow
    {
        protected override void WndProc(ref Message m) {
            switch (m.Msg) {
                case WM_INITDIALOG:
                    IntPtr hMenu = GetSystemMenu(m.HWnd, false);
                    DeleteMenu(hMenu, SC_CLOSE, MF_BYCOMMAND);
                    base.WndProc(ref m);
                    break;
                default:
                    base.WndProc(ref m);
                    break;
            }
        }

        const int WM_INITDIALOG = 0x0110;
        const int MF_BYCOMMAND = 0x0000;
        const int SC_CLOSE = 0xF060;

        [DllImport("user32.dll")]
        static extern IntPtr GetSystemMenu(IntPtr hWnd, bool bRevert);
        [DllImport("user32.dll")]
        static extern bool DeleteMenu(IntPtr hMenu, int position, int flags);
    }

    const int WM_CREATE = 0x0001;
    const int WH_CALLWNDPROC = 4;

    delegate IntPtr HookProcDelegate(int code, IntPtr wParam, IntPtr lParam);
    [DllImport("user32.dll", SetLastError = true)]
    static extern IntPtr SetWindowsHookEx(int hookType, HookProcDelegate lpfn, IntPtr hMod, uint dwThreadId);
    [DllImport("kernel32.dll")]
    static extern uint GetCurrentThreadId();
    [DllImport("user32.dll")]
    static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode, IntPtr wParam, IntPtr lParam);
    [DllImport("user32.dll", SetLastError = true)]
    static extern bool UnhookWindowsHookEx(IntPtr hhk);
    [DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
    static extern int GetClassName(IntPtr hWnd, StringBuilder lpClassName, int nMaxCount);
    [StructLayout(LayoutKind.Sequential)]
    private struct CWPSTRUCT
    {
        public IntPtr lparam;
        public IntPtr wparam;
        public int message;
        public IntPtr hwnd;
    }
}

引用返信 編集キー/
■99315 / inTopicNo.7)  Re[3]: メッセージボックスの閉じるボタンを無効にしたい
□投稿者/ PATIO (26回)-(2022/03/11(Fri) 15:50:33)
No99311 (ラルフ さん) に返信
> ■No99310 (furu さん) に返信
>>ボタンは何を表示していますか?
>>
>>無効にする方法は知りませんが
>>以下のルールで無効になるようです。
>>
>>MessageBoxButtons.YesNo
>>MessageBoxButtons.AbortRetryIgnore
>>のようなCancelが無い場合、×ボタンは無効
>>
>>但し
>>MessageBoxButtons.OK
>>のようにボタンが1つだけだと×ボタンは有効
>
> MessageBoxButtons.OKだけです。
> なので困っています。

なぜ&#10005;ボタンを無効にしたいのかを説明した方が有益な話は聞けるかもしれません。
furuさんが書かれているように普通に考えたら何が困るのかよくわからない状態なので。
労力の割に報われない作業になりそうでクエスチョンマーク出まくりです。
引用返信 編集キー/


トピック内ページ移動 / << 0 >>

このトピックに書きこむ

過去ログには書き込み不可

管理者用

- Child Tree -