(長文ですみません)
MessageBox は,ボタンを押すまで存在し続け,プログラムは停止状態に
なりますが,一定時間の後自動で消えるようにすることは出来ないでしょうか。
いろいろ調べましたが,苦しまぎれに別プログラムとして,マウスが自動で動いて
ボタンをクリックするものを作り,これを ShellExecute コマンドで働かせるように
しましたが,不満があります。
・マウスが自動で移動中,砂時計が伴って表示される( → これは消したい)
・手動でOKボタンをクリックしたときも,マウスの自動動作を中断できない。
何かもっとよい方法があるような気がするのですが,力不足です。
良い方法があれば教えて下さい。
------------------------------------------------
(以下,苦しまぎれの方法, 1.2.をファイルにすればコンパイル可)
次の 1.AutoOKMsg.abp,2.mvMOUSE.abp の2つのファイルをそれぞれ
コンパイルし,AutoOKMsg.exe,mvMOUSE.exe を作ります。
AutoOKMsg.exe を走らせます。
動作:
AutoOKMsg.exe を走らせると,(この中からmvMOUSE.exe を呼ぶ)
メッセージボックスが表示され,数秒後に自動でマウスがOKボタンをクリック
してメッセージボックスが閉じます。
1. "AutoOKMsg.abp"
' マウス移動,クリックプログラムをスタート
ShellExecute(NULL,NULL,"mvMOUSE.exe","",NULL,SW_HIDE)
' (MessageBoxより先に走らせておく)
' メッセージボックス表示
Dim Msg As String
Msg = Ex" MessageBox\n\n\n_
数秒後に,別プログラム mvMOUSE.exe が \n\n_
〔OK〕 をクリックする"
MessageBox(0, Msg, " AutoOKMsg.exe", MB_OK)
' --- ここまで
2. "mvMOUSE.abp"
' 自動で,マウス移動,クリック
' MESSAGEBOX の OKボタンを数秒後に自動で押す。
' マウス(X,Y)へ自動移動
' 絶対座標 全画面 X = 0 ~ 65535 Y = 0 ~ 65535
Sub mvXY(ByVal X As DWord, ByVal Y As DWord)
mouse_event(MOUSEEVENTF_ABSOLUTE + MOUSEEVENTF_MOVE,X,Y,0,0)
End Sub
Sub Lclick()' マウス自動左クリック
mouse_event(MOUSEEVENTF_LEFTDOWN,0,0,0,0)' 押下
mouse_event(MOUSEEVENTF_LEFTUP,0,0,0,0)' 放す
End Sub
Dim I As Word, J As Word, K As Word, DMY As Double
Dim X As Word, Y As Word
Dim X1 As Word, X2 As Word, Y1 As Word, Y2 As Word
Dim X3 As Word, Y3 As Word
' 位置(X1,Y1) → (X2,Y2) マウス自動移動
'(絶対座標 全画面 X = 0 ~ 65535 Y = 0 ~ 65535)
X1=23000: Y1=26000
X2=33000: Y2=37600
FOR X=X1 TO X2
Y=(X-X1)/(X2-X1)*(Y2-Y1)+Y1
mvXY(X,Y)
FOR J=1 TO 30:DMY=Sin(J):NEXT' 移動速度(時間)調整
NEXT
'数秒待って自動クリック
FOR K=1 TO 1500
FOR J=1 TO 3000:DMY=Sin(J):NEXT J' 待ち時間作成
NEXT K
BEEP
Lclick()' マウス左自動クリック
' マウスを他所へ移動して終了
X3=33000: Y3=26000
mvXY(X3,Y3)
'Lclick()
' --- ここまで
MessageBoxを自動で閉じるには...
hiraさんがそれと同じものをDLLにて公開されています。
http://hira.hopto.org/
「AB作品の部屋」の中にあります。
DLLですが、ソースも添付されているので参考にしてみてはどうでしょう?
http://hira.hopto.org/
「AB作品の部屋」の中にあります。
DLLですが、ソースも添付されているので参考にしてみてはどうでしょう?
こんにちは。hiraです。
自動消滅なのですが、現在、PostQuitMessage関数を使用してウィンドウを閉じています。
OKボタンオンリー以外のボタンの組み合わせの場合、OK(キャンセル)ボタンがあるときは×ボタンがあるのでうまくいきます。しかし、「はい」「いいえ」の選択の場合などは、×ボタンが使えないので(環境によると思いますが)、現状のPostQuitMessage関数でのウィンドウ消滅ができなくなってしまっています。
試行錯誤しているのですが、なかなかうまくいきません…。
私もいろいろ試してみますが、良い方法があればお願いします。
※MessageBoxを呼び出すとそのスレッドが停止状態になるので、現状では、自動消滅のタイミングを別スレッドで監視しています。そのため、DestroyWindow関数が使えません…。
自動消滅なのですが、現在、PostQuitMessage関数を使用してウィンドウを閉じています。
OKボタンオンリー以外のボタンの組み合わせの場合、OK(キャンセル)ボタンがあるときは×ボタンがあるのでうまくいきます。しかし、「はい」「いいえ」の選択の場合などは、×ボタンが使えないので(環境によると思いますが)、現状のPostQuitMessage関数でのウィンドウ消滅ができなくなってしまっています。
試行錯誤しているのですが、なかなかうまくいきません…。
私もいろいろ試してみますが、良い方法があればお願いします。
※MessageBoxを呼び出すとそのスレッドが停止状態になるので、現状では、自動消滅のタイミングを別スレッドで監視しています。そのため、DestroyWindow関数が使えません…。
[hira]
http://hira.hopto.org/
http://hira.hopto.org/
自己レスです。対応に成功しましたので報告させていただきます。
ExMsgBox.dll Ver 1.01として「AB作品の部屋」にアップしました。
メッセージボックス内にあるコマンドボタンのどれか1つをクリックしたことにすることで、強制的にメッセージボックスを消すようにしています。もちろんタイムアウトの場合の戻り値はちゃんと別にしていますが。
参考までにDLLなしで使う場合のMsgBox_Extraのソースです。(ほとんどそのままですが…)
ExMsgBox.dll Ver 1.01として「AB作品の部屋」にアップしました。
メッセージボックス内にあるコマンドボタンのどれか1つをクリックしたことにすることで、強制的にメッセージボックスを消すようにしています。もちろんタイムアウトの場合の戻り値はちゃんと別にしていますが。
参考までにDLLなしで使う場合のMsgBox_Extraのソースです。(ほとんどそのままですが…)
コード: 全て選択
Const MEX_MOVE=1
Const MEX_TIMER=2
Const IDTIMEOUT=-1
Dim fTimeOut As DWord
Declare Function FindWindowEx Lib "user32" Alias "FindWindowExA" (hwndParent As HWND,hwndChildAfter As HWND,lpszClass As *Byte,lpszWindow As *Byte) As HWND
Function MsgBox_Extra(hWnd As HWND,lpText As BytePtr,lpCaption As BytePtr,uType As DWord,x As Long,y As Long,dwTimer As DWord,dwFlags As DWord)As Long
Dim Mem As *ULONG_PTR,Mem2 As BytePtr,hThread As HANDLE
Mem=malloc(SizeOf(ULONG_PTR)*6)
Mem2=calloc(Len(lpCaption))
Mem[0]=x
Mem[1]=y
lstrcpy(Mem2,lpCaption)
Mem[2]=Mem2 As ULONG_PTR
Mem[3]=dwTimer
Mem[4]=dwFlags
CreateThread(ByVal 0,0,AddressOf(MsgBoxThread),Mem,0,VarPtr(hThread))
Mem[5]=hThread As ULONG_PTR
fTimeOut=0
MsgBox_Extra=MessageBox(hWnd,lpText,lpCaption,uType)
If fTimeOut Then MsgBox_Extra=IDTIMEOUT
CloseHandle(hThread)
End Function
Function MsgBoxThread(Param As *ULONG_PTR) As DWord
Dim dwTimer As DWord,dwFlags As DWord,hMsgBoxWnd As HWND,dwTick As DWord,hThread As HANDLE
dwTimer=Param[3]
dwFlags=Param[4]
hThread=Param[5] As HANDLE
While FindWindow("#32770",Param[2] As *Byte)=0
Sleep(1)
Wend
hMsgBoxWnd=FindWindow("#32770",Param[2] As *Byte)
If (dwFlags And MEX_MOVE) Then
SetWindowPos(hMsgBoxWnd,0,Param[0],Param[1],0,0,SWP_NOSIZE)
End If
free(Param[2] As *Byte)
free(Param)
If (dwFlags And MEX_TIMER) Then
dwTick=GetTickCount()
While GetTickCount()<=(dwTick+dwTimer)
If IsWindow(hMsgBoxWnd)=0 Then
ExitThread(0)
Exit Function
End If
Sleep(1)
Wend
fTimeOut=1
FindWindowEx(hMsgBoxWnd,NULL,"Button",NULL)
SendMessage(hMsgBoxWnd,WM_COMMAND,MAKELONG(GetDlgCtrlID(FindWindowEx(hMsgBoxWnd,NULL,"Button",NULL)),BN_CLICKED),0)
End If
ExitThread(0)
End Function
[hira]
http://hira.hopto.org/
http://hira.hopto.org/