請問VB5是用shell來執行外部檔案,那執行後,要怎樣用VB的語法來終止此檔案的執行呢!?老怪答:Dim FHandle As Variant '(儲存視窗代碼的變數Private Sub Command1_Click() FHandle = Shell("C:\WIND98\CALC.EXE", 1) '(開啟外部執行檔) End SubPrivate Sub Command2_Click() AppActivate FHandle '讓先前開啟的視窗取得焦點。 SendKeys "%{f4}", True '送出 [Alt]+[F4] Windows 系統的關閉組合鍵。 End Sub改寫成能處理錯誤的呼叫函數則如下:開啟 Windows 應用程式 'varAppName 是程式路徑及名稱之傳遞參數 'varWinState 是應用程式視窗開啟狀態,設定方式請參考 Shell '的 WindowsStyle 說明 Private Function OpenApp(ByVal varAppName As String, _ Optional ByVal varWinState As Integer) '傳回應用程式之視窗代碼 Dim varWinTitle As Variant'錯誤處理 On Error GoTo OpenAppErrvarWinTitle = Shell(varAppName, varWinState) OpenApp = varWinTitle Exit FunctionOpenAppErr: Select Case Err.Number Case 53 MsgBox "程式路徑或名稱錯誤", vbOKOnly, "開啟應用程式" End Select End Function'關閉 Windows 應用程式 'varWinTitle 是開啟程式時 Windows 系統給的代碼 Private Sub CloseApp(ByVal varWinTitle As Variant)'錯誤處理 On Error GoTo CloseAppErrAppActivate varWinTitle '用 SendKeys 陳述模擬鍵盤 [ALT]+[F4] SendKeys "%{F4}" Exit SubCloseAppErr: Select Case Err.Number Case 5 MsgBox "程式視窗已被關閉", vbOKOnly, "關閉應用程式" End Select End Sub'上面是改寫 Shell 和 AppActivate 的兩個函數,呼叫方式如下:'宣告一個儲存視窗代碼的變數 Private WinTitle As Variant'開程式 Private Sub Command1_Click() Dim AppName As StringAppName = "你的程式路徑及名稱" WinTitle = OpenApp(AppName) End Sub'關程式 Private Sub Command2_Click() CloseApp WinTitle End Sub
请确认是否的确得到了captureUp.exe的句柄,可以加上debug.print看看在CmdQuit_Click()里才查找该句柄: private sub CmdQuit_Click()retval=findwindow(vbnullstring,"captureup") setparent retval,me.hwndend sub
'============================== '以下在窗体中 '============================== Option ExplicitPrivate Declare Function FindWindow Lib "user32" _ Alias "FindWindowA" _ (ByVal lpClassName As String, _ ByVal lpWindowName As String) As Long Private Declare Function SetParent Lib "user32" _ (ByVal hWndChild As Long, _ ByVal hWndNewParent As Long) As Long Private Declare Function SendMessage Lib "user32" _ Alias "SendMessageA" _ (ByVal hWnd As Long, _ ByVal wMsg As Long, _ ByVal wParam As Long, _ lParam As Any) As Long Private Declare Function EnumChildWindows Lib "user32" _ (ByVal hWndParent As Long, _ ByVal lpEnumFunc As Long, _ ByVal lParam As Long) As LongPrivate Const WM_CLOSE = &H10 Private RetVal As Long Private Sub Command1_Click() Shell "calc.exe", vbNormalFocus RetVal = FindWindow(vbNullString, "计算器") SetParent RetVal, Me.hWnd End Sub Private Sub Command2_Click() '演示如何使用EnumChildWindows,此语句不是必需的。 Call EnumChildWindows(Me.hWnd, AddressOf EnumChildProc, 0)
'也许是你写错了,应是WM_CLOSE而非MW_CLOSE, '建议在所有模块中都加上Option Explicit语句 Call SendMessage(RetVal, WM_CLOSE, 0, 0) End Sub '============================== '以下在模块中 '============================== Option ExplicitPrivate Declare Function IsWindowVisible Lib "user32" _ (ByVal hWnd As Long) As Long Private Declare Function GetWindowText Lib "user32" _ Alias "GetWindowTextA" _ (ByVal hWnd As Long, _ ByVal lpString As String, _ ByVal cch As Long) As LongPublic Function EnumChildProc(ByVal hWnd As Long, ByVal lParam As Long) As Long Dim strWindowText As String * 128
If IsWindowVisible(hWnd) Then Call GetWindowText(hWnd, strWindowText, 128) Debug.Print hWnd, Left(strWindowText, InStr(strWindowText, Chr(0)) - 1) End If
EnumChildProc = True End Function
解铃还需系铃人,你用SHELLEXECUTE打开,当然还是用它关闭了。 shellexecute me.hwnd,"close",app.path _ & "\captureUp.exe",VBNullstring,VBNullstring,1 如果不行,你找到它的process id也可以把它关掉。 另外以下例子是FOXAPI上面的,你自己慢慢看吧。 'Example Name:EnumWindows and EnumChildWindows Callbacks '------------------------------------------------------------------------------ ' ' BAS Moduel Code ' '------------------------------------------------------------------------------ Option Explicit Private Const LVIF_INDENT As Long = &H10 Private Const LVIF_TEXT As Long = &H1 Private Const LVM_FIRST As Long = &H1000 Private Const LVM_SETITEM As Long = (LVM_FIRST + 6)Private Type LVITEM mask As Long iItem As Long iSubItem As Long state As Long stateMask As Long pszText As String cchTextMax As Long iImage As Long lParam As Long iIndent As Long End TypePublic Declare Function EnumWindows Lib "user32" _ (ByVal lpEnumFunc As Long, _ ByVal lParam As Long) As Long
Public Declare Function EnumChildWindows Lib "user32" _ (ByVal hWndParent As Long, _ ByVal lpEnumFunc As Long, _ ByVal lParam As Long) As LongPrivate Declare Function GetWindowTextLength Lib "user32" _ Alias "GetWindowTextLengthA" _ (ByVal hwnd As Long) As Long
Private Declare Function GetWindowText Lib "user32" _ Alias "GetWindowTextA" _ (ByVal hwnd As Long, _ ByVal lpString As String, _ ByVal cch As Long) As Long
Private Declare Function GetClassName Lib "user32" _ Alias "GetClassNameA" _ (ByVal hwnd As Long, _ ByVal lpClassName As String, _ ByVal nMaxCount As Long) As LongPrivate Declare Function IsWindowVisible Lib "user32" _ (ByVal hwnd As Long) As Long
Private Declare Function GetParent Lib "user32" _ (ByVal hwnd As Long) As LongPrivate Declare Function SendMessage Lib "user32" _ Alias "SendMessageA" _ (ByVal hwnd As Long, _ ByVal wMsg As Long, _ ByVal wParam As Long, _ lParam As Any) As Long Public Function EnumWindowProc(ByVal hwnd As Long, _ ByVal lParam As Long) As Long
'working vars Dim nSize As Long Dim sTitle As String Dim sClass As String
Dim sIDType As String Dim itmX As ListItem Dim nodX As Node
'eliminate windows that are not top-level. If GetParent(hwnd) = 0& And _ IsWindowVisible(hwnd) Then
'get the window title / class name sTitle = GetWindowIdentification(hwnd, sIDType, sClass) 'add to the listview Set itmX = Form1.ListView1.ListItems.Add(Text:=sTitle, Key:=CStr(hwnd) & "h") itmX.SmallIcon = Form1.ImageList1.ListImages("parent").Key itmX.SubItems(1) = CStr(hwnd) itmX.SubItems(2) = sIDType itmX.SubItems(3) = sClass
End If
'To continue enumeration, return True 'To stop enumeration return False (0). 'When 1 is returned, enumeration continues 'until there are no more windows left. EnumWindowProc = 1
End Function Private Function GetWindowIdentification(ByVal hwnd As Long, _ sIDType As String, _ sClass As String) As String Dim nSize As Long Dim sTitle As String 'get the size of the string required 'to hold the window title nSize = GetWindowTextLength(hwnd)
'if the return is 0, there is no title If nSize > 0 Then
'no title, so get the class name instead sTitle = Space$(64) Call GetClassName(hwnd, sTitle, 64) sClass = sTitle sIDType = "class"
End If
GetWindowIdentification = TrimNull(sTitle)End Function Public Function EnumChildProc(ByVal hwnd As Long, _ ByVal lParam As Long) As Long
'working vars Dim sTitle As String Dim sClass As String Dim sIDType As String Dim itmX As ListItem 'get the window title / class name sTitle = GetWindowIdentification(hwnd, sIDType, sClass) 'add to the listview Set itmX = Form2.ListView1.ListItems.Add(Text:=sTitle) itmX.SmallIcon = Form2.ImageList1.ListImages("child").Key itmX.SubItems(1) = CStr(hwnd) itmX.SubItems(2) = sIDType itmX.SubItems(3) = sClass
End Function Private Function TrimNull(startstr As String) As String Dim pos As Integer pos = InStr(startstr, Chr$(0))
If pos Then TrimNull = Left$(startstr, pos - 1) Exit Function End If
'if this far, there was 'no Chr$(0), so return the string TrimNull = startstr
End Function Private Sub Listview_IndentItem(hwnd As Long, _ nItem As Long, _ nIndent As Long) Dim LV As LVITEM 'if nIndent indicates that indentation 'is requested nItem is the item to indent If nIndent > 0 Then
With LV .mask = LVIF_INDENT .iItem = nItem - 1 'have to subtract 1 .iIndent = nIndent End With
Call SendMessage(hwnd, LVM_SETITEM, 0&, LV)
End If
End Sub '--end block--' '------------------------------------------------------------------------------ ' ' Form Code ' '------------------------------------------------------------------------------ Option ExplicitPrivate Sub Command1_Click() ListView1.ListItems.Clear Call EnumWindows(AddressOf EnumWindowProc, &H0)End Sub Private Sub Form_Load() Me.Move (Screen.Width - Me.Width) / 2, (Screen.Height - Me.Height) / 2End Sub Private Sub ListView1_DblClick() Dim hwndSelected As Long
外部檔案的執行及終止
請問VB5是用shell來執行外部檔案,那執行後,要怎樣用VB的語法來終止此檔案的執行呢!?老怪答:Dim FHandle As Variant '(儲存視窗代碼的變數Private Sub Command1_Click()
FHandle = Shell("C:\WIND98\CALC.EXE", 1) '(開啟外部執行檔)
End SubPrivate Sub Command2_Click()
AppActivate FHandle '讓先前開啟的視窗取得焦點。
SendKeys "%{f4}", True '送出 [Alt]+[F4] Windows 系統的關閉組合鍵。
End Sub改寫成能處理錯誤的呼叫函數則如下:開啟 Windows 應用程式
'varAppName 是程式路徑及名稱之傳遞參數
'varWinState 是應用程式視窗開啟狀態,設定方式請參考 Shell
'的 WindowsStyle 說明
Private Function OpenApp(ByVal varAppName As String, _
Optional ByVal varWinState As Integer)
'傳回應用程式之視窗代碼
Dim varWinTitle As Variant'錯誤處理
On Error GoTo OpenAppErrvarWinTitle = Shell(varAppName, varWinState)
OpenApp = varWinTitle
Exit FunctionOpenAppErr:
Select Case Err.Number
Case 53
MsgBox "程式路徑或名稱錯誤", vbOKOnly, "開啟應用程式"
End Select
End Function'關閉 Windows 應用程式
'varWinTitle 是開啟程式時 Windows 系統給的代碼
Private Sub CloseApp(ByVal varWinTitle As Variant)'錯誤處理
On Error GoTo CloseAppErrAppActivate varWinTitle
'用 SendKeys 陳述模擬鍵盤 [ALT]+[F4]
SendKeys "%{F4}"
Exit SubCloseAppErr:
Select Case Err.Number
Case 5
MsgBox "程式視窗已被關閉", vbOKOnly, "關閉應用程式"
End Select
End Sub'上面是改寫 Shell 和 AppActivate 的兩個函數,呼叫方式如下:'宣告一個儲存視窗代碼的變數
Private WinTitle As Variant'開程式
Private Sub Command1_Click()
Dim AppName As StringAppName = "你的程式路徑及名稱"
WinTitle = OpenApp(AppName)
End Sub'關程式
Private Sub Command2_Click()
CloseApp WinTitle
End Sub
ShellExecute能不能也这样类似得处理?
ALT+F4方式关闭就会出现内存不能读错误。这是为何呀,急死我了
enumchildwindows这个API如何用?谁有例子
我的视频采集程序上有一个退出按钮,只有按退出按钮或CTRL+ALT+DEL组合键结束进程才能正常关闭。
那位大侠能解决此问题另外开问题奖励200分。
现在我该如何向窗体发送ALT+X这个组合键,我没做过,应该不是很难。
第一个提供正确答案的这里的100分全是你的。
本示例使用 Shell 函数来运行 Microsoft Windows 所附的计算器程序;然后使用 SendKeys 语句来按下计算器的某些数字键,最后退出计算器。(若要观察示例运行过程,可将示例粘贴到过程中,再运行过程即可。因为 AppActivate 会将焦点转移到计算器应用程序,故本示例不能以单步方式来运行。)。Dim ReturnValue, I
ReturnValue = Shell("Calc.EXE", 1) ' 运行计算器。
AppActivate ReturnValue ' 激活计算器。
For I = 1 To 100 ' 设置计数循环。
SendKeys I & "{+}", True ' 按下按键给计算器
Next I ' 将所有 I 值相加。
SendKeys "=", True ' 取得总合。
SendKeys "%{F4}", True ' 按 ALT+F4 关闭计算器。
SendMessage(退出按钮句柄,&HF5,0,0)
试试看?
根据一开始的思路,
直接用PostQuitMessage
或用PostMessage发送WM_QUIT不就行了?
再说,为什么你要SetParent?
如在不同的进程或许可用PostThreadMessage尝试,注意要获得ThreadID,而不是你已得到的Handle。
建议找API-Guide看看。
SetParent是不是最后要还原
private sub CmdQuit_Click()retval=findwindow(vbnullstring,"captureup")
setparent retval,me.hwndend sub
'以下在窗体中
'==============================
Option ExplicitPrivate Declare Function FindWindow Lib "user32" _
Alias "FindWindowA" _
(ByVal lpClassName As String, _
ByVal lpWindowName As String) As Long
Private Declare Function SetParent Lib "user32" _
(ByVal hWndChild As Long, _
ByVal hWndNewParent As Long) As Long
Private Declare Function SendMessage Lib "user32" _
Alias "SendMessageA" _
(ByVal hWnd As Long, _
ByVal wMsg As Long, _
ByVal wParam As Long, _
lParam As Any) As Long
Private Declare Function EnumChildWindows Lib "user32" _
(ByVal hWndParent As Long, _
ByVal lpEnumFunc As Long, _
ByVal lParam As Long) As LongPrivate Const WM_CLOSE = &H10
Private RetVal As Long
Private Sub Command1_Click()
Shell "calc.exe", vbNormalFocus
RetVal = FindWindow(vbNullString, "计算器")
SetParent RetVal, Me.hWnd
End Sub
Private Sub Command2_Click()
'演示如何使用EnumChildWindows,此语句不是必需的。
Call EnumChildWindows(Me.hWnd, AddressOf EnumChildProc, 0)
'也许是你写错了,应是WM_CLOSE而非MW_CLOSE,
'建议在所有模块中都加上Option Explicit语句
Call SendMessage(RetVal, WM_CLOSE, 0, 0)
End Sub
'==============================
'以下在模块中
'==============================
Option ExplicitPrivate Declare Function IsWindowVisible Lib "user32" _
(ByVal hWnd As Long) As Long
Private Declare Function GetWindowText Lib "user32" _
Alias "GetWindowTextA" _
(ByVal hWnd As Long, _
ByVal lpString As String, _
ByVal cch As Long) As LongPublic Function EnumChildProc(ByVal hWnd As Long, ByVal lParam As Long) As Long
Dim strWindowText As String * 128
If IsWindowVisible(hWnd) Then
Call GetWindowText(hWnd, strWindowText, 128)
Debug.Print hWnd, Left(strWindowText, InStr(strWindowText, Chr(0)) - 1)
End If
EnumChildProc = True
End Function
shellexecute me.hwnd,"close",app.path _ & "\captureUp.exe",VBNullstring,VBNullstring,1
如果不行,你找到它的process id也可以把它关掉。
另外以下例子是FOXAPI上面的,你自己慢慢看吧。
'Example Name:EnumWindows and EnumChildWindows Callbacks '------------------------------------------------------------------------------
'
' BAS Moduel Code
'
'------------------------------------------------------------------------------
Option Explicit Private Const LVIF_INDENT As Long = &H10
Private Const LVIF_TEXT As Long = &H1
Private Const LVM_FIRST As Long = &H1000
Private Const LVM_SETITEM As Long = (LVM_FIRST + 6)Private Type LVITEM
mask As Long
iItem As Long
iSubItem As Long
state As Long
stateMask As Long
pszText As String
cchTextMax As Long
iImage As Long
lParam As Long
iIndent As Long
End TypePublic Declare Function EnumWindows Lib "user32" _
(ByVal lpEnumFunc As Long, _
ByVal lParam As Long) As Long
Public Declare Function EnumChildWindows Lib "user32" _
(ByVal hWndParent As Long, _
ByVal lpEnumFunc As Long, _
ByVal lParam As Long) As LongPrivate Declare Function GetWindowTextLength Lib "user32" _
Alias "GetWindowTextLengthA" _
(ByVal hwnd As Long) As Long
Private Declare Function GetWindowText Lib "user32" _
Alias "GetWindowTextA" _
(ByVal hwnd As Long, _
ByVal lpString As String, _
ByVal cch As Long) As Long
Private Declare Function GetClassName Lib "user32" _
Alias "GetClassNameA" _
(ByVal hwnd As Long, _
ByVal lpClassName As String, _
ByVal nMaxCount As Long) As LongPrivate Declare Function IsWindowVisible Lib "user32" _
(ByVal hwnd As Long) As Long
Private Declare Function GetParent Lib "user32" _
(ByVal hwnd As Long) As LongPrivate Declare Function SendMessage Lib "user32" _
Alias "SendMessageA" _
(ByVal hwnd As Long, _
ByVal wMsg As Long, _
ByVal wParam As Long, _
lParam As Any) As Long
Public Function EnumWindowProc(ByVal hwnd As Long, _
ByVal lParam As Long) As Long
'working vars
Dim nSize As Long
Dim sTitle As String
Dim sClass As String
Dim sIDType As String
Dim itmX As ListItem
Dim nodX As Node
'eliminate windows that are not top-level.
If GetParent(hwnd) = 0& And _
IsWindowVisible(hwnd) Then
'get the window title / class name
sTitle = GetWindowIdentification(hwnd, sIDType, sClass) 'add to the listview
Set itmX = Form1.ListView1.ListItems.Add(Text:=sTitle, Key:=CStr(hwnd) & "h")
itmX.SmallIcon = Form1.ImageList1.ListImages("parent").Key
itmX.SubItems(1) = CStr(hwnd)
itmX.SubItems(2) = sIDType
itmX.SubItems(3) = sClass
End If
'To continue enumeration, return True
'To stop enumeration return False (0).
'When 1 is returned, enumeration continues
'until there are no more windows left.
EnumWindowProc = 1
End Function
Private Function GetWindowIdentification(ByVal hwnd As Long, _
sIDType As String, _
sClass As String) As String Dim nSize As Long
Dim sTitle As String 'get the size of the string required
'to hold the window title
nSize = GetWindowTextLength(hwnd)
'if the return is 0, there is no title
If nSize > 0 Then
sTitle = Space$(nSize + 1)
Call GetWindowText(hwnd, sTitle, nSize + 1)
sIDType = "title"
sClass = Space$(64)
Call GetClassName(hwnd, sClass, 64)
Else
'no title, so get the class name instead
sTitle = Space$(64)
Call GetClassName(hwnd, sTitle, 64)
sClass = sTitle
sIDType = "class"
End If
GetWindowIdentification = TrimNull(sTitle)End Function
Public Function EnumChildProc(ByVal hwnd As Long, _
ByVal lParam As Long) As Long
'working vars
Dim sTitle As String
Dim sClass As String
Dim sIDType As String
Dim itmX As ListItem 'get the window title / class name
sTitle = GetWindowIdentification(hwnd, sIDType, sClass) 'add to the listview
Set itmX = Form2.ListView1.ListItems.Add(Text:=sTitle)
itmX.SmallIcon = Form2.ImageList1.ListImages("child").Key
itmX.SubItems(1) = CStr(hwnd)
itmX.SubItems(2) = sIDType
itmX.SubItems(3) = sClass
Listview_IndentItem Form2.ListView1.hwnd, CLng(itmX.Index), 1
EnumChildProc = 1
End Function
Private Function TrimNull(startstr As String) As String Dim pos As Integer pos = InStr(startstr, Chr$(0))
If pos Then
TrimNull = Left$(startstr, pos - 1)
Exit Function
End If
'if this far, there was
'no Chr$(0), so return the string
TrimNull = startstr
End Function
Private Sub Listview_IndentItem(hwnd As Long, _
nItem As Long, _
nIndent As Long) Dim LV As LVITEM 'if nIndent indicates that indentation
'is requested nItem is the item to indent
If nIndent > 0 Then
With LV
.mask = LVIF_INDENT
.iItem = nItem - 1 'have to subtract 1
.iIndent = nIndent
End With
Call SendMessage(hwnd, LVM_SETITEM, 0&, LV)
End If
End Sub
'--end block--'
'------------------------------------------------------------------------------
'
' Form Code
'
'------------------------------------------------------------------------------
Option ExplicitPrivate Sub Command1_Click() ListView1.ListItems.Clear
Call EnumWindows(AddressOf EnumWindowProc, &H0)End Sub
Private Sub Form_Load() Me.Move (Screen.Width - Me.Width) / 2, (Screen.Height - Me.Height) / 2End Sub
Private Sub ListView1_DblClick() Dim hwndSelected As Long
hwndSelected = Val(ListView1.SelectedItem.Key)
Load Form2
Call Form2.EnumSelectedWindow(ListView1.SelectedItem.Text, hwndSelected)
End Sub
'--end block--'
Form2 Code
Add the following code to Form2: --------------------------------------------------------------------------------
Option ExplicitPublic Sub EnumSelectedWindow(sItem As String, hwnd As Long)
ListView1.ListItems.Clear
ListView1.ListItems.Add Text:=sItem, SmallIcon:="parent"
Call EnumChildWindows(hwnd, AddressOf EnumChildProc, &H0)
Me.Show vbModal
End Sub
Private Sub Form_Load() Me.Move (Screen.Width - Me.Width) / 2, (Screen.Height - Me.Height) / 2
End Sub
Private Sub Form_Load() 初始化
Vedio_X = 330
Vedio_Y = -20
Vedio_Width = 460
Vedio_Height = 340
ShellExecute Me.hwnd, "open", App.Path & "\CaptureUp.exe", vbNullString, vbNullString, 1
'RetVal = FindWindow(vbNullString, "")
Do
RetVal = FindWindow(vbNullString, "CaptureUp")
DoEvents
Loop Until RetVal > 0
SetParent RetVal, Me.hwnd
SetWindowPos RetVal, HWND_NOTOPMOST, Vedio_X, Vedio_Y, Vedio_Width, Vedio_Height, SWP_NOMOVE
Sleep 1000
SetWindowPos Me.Picture5.hwnd, HWND_TOPMOST, Vedio_X, Vedio_Y, Vedio_Width, Vedio_Height, SWP_NOMOVE
End SubPrivate Sub Option1_Click() 'checkbox切换显示
If Option1.Value = 1 Then
SetWindowPos Me.Picture5.hwnd, HWND_NOTOPMOST, Vedio_X, Vedio_Y, Vedio_Width, Vedio_Height, SWP_NOMOVE
SetWindowPos RetVal, HWND_TOPMOST, Vedio_X, Vedio_Y, Vedio_Width, Vedio_Height, SWP_NOMOVE
Else
SetWindowPos RetVal, HWND_NOTOPMOST, Vedio_X, Vedio_Y, Vedio_Width, Vedio_Height, SWP_NOMOVE
SetWindowPos Me.Picture5.hwnd, HWND_TOPMOST, Vedio_X, Vedio_Y, Vedio_Width, Vedio_Height, SWP_NOMOVE
End If
End SubPrivate Sub Command1_Click() '退出
Dim dwProcessId As Long
dwProcessId = FindWindow("Progman", vbNullString)
SetParent RetVal, dwProcessId SendKeys "%{F4}", True
Sleep 1000
Beep
MsgBox "即将退出本系统,请点击确定后,稍后....", vbOKOnly + vbExclamation, " 退出"
Sleep 1000 End
End Sub
Call ShellExecute(Me.hWnd, "Close",App.Path _ & "\CaptureUp.exe","" , "", 4)
试一下