VB批处理后重定向输出

批处理后重定向输出,今天找VB.NET资料时收集到的.NET调用JAVA可能能借鉴的资料,不过看下面这么一堆API,觉得在条件允许的情况下还是使用文件的方式更简便些。

'新建工程,添加两个文本框txtMessage与txtCommand.
'前者的MultLine=True,用于显示命令行程序的回显;
'后者用于输入命令.
Option Explicit

Private Declare Function CreateProcess Lib "kernel32" Alias "CreateProcessA" (ByVal lpApplicationName As String, ByVal lpCommandLine As String, lpProcessAttributes As Any, lpThreadAttributes As Any, ByVal bInheritHandles As Long, ByVal dwCreationFlags As Long, lpEnvironment As Any, ByVal lpCurrentDriectory As String, lpStartupInfo As STARTUPINFO, lpProcessInformation As PROCESS_INFORMATION) As Long
Private Declare Function CloseHandle Lib "kernel32" (ByVal hObject As Long) As Long
Private Declare Function CreatePipe Lib "kernel32" (phReadPipe As Long, phWritePipe As Long, lpPipeAttributes As Any, ByVal nSize As Long) As Long
Private Declare Function WriteFile Lib "kernel32" (ByVal hFile As Long, lpBuffer As Any, ByVal nNumberOfBytesToWrite As Long, lpNumberOfBytesWritten As Long, lpOverlapped As Any) As Long
Private Declare Function ReadFile Lib "kernel32" (ByVal hFile As Long, lpBuffer As Any, ByVal nNumberOfBytesToRead As Long, lpNumberOfBytesRead As Long, lpOverlapped As Any) As Long
Private Declare Function SetHandleInformation Lib "kernel32" (ByVal hObject As Long, ByVal dwMask As Long, ByVal dwFlags As Long) As Long
Private Declare Function SetNamedPipeHandleState Lib "kernel32" (ByVal hNamedPipe As Long, lpMode As Long, lpMaxCollectionCount As Long, lpCollectDataTimeout As Long) As Long
Private Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long)

Private Type STARTUPINFO
    cb As Long
    lpReserved As String
    lpDesktop As String
    lpTitle As String
    dwX As Long
    dwY As Long
    dwXSize As Long
    dwYSize As Long
    dwXCountChars As Long
    dwYCountChars As Long
    dwFillAttribute As Long
    dwFlags As Long
    wShowWindow As Integer
    cbReserved2 As Integer
    lpReserved2 As Long
    hStdInput As Long
    hStdOutput As Long
    hStdError As Long
End Type

Private Type PROCESS_INFORMATION
    hProcess As Long
    hThread As Long
    dwProcessId As Long
    dwThreadId As Long
End Type

Private Const STARTF_USESTDHANDLES = &H100
Private Const HANDLE_FLAG_INHERIT = 1
Private Const DETACHED_PROCESS = &H8
Private Const PIPE_NOWAIT = &H1

Dim hReadPipe As Long
Dim hWritePipe As Long
Dim hChildReadPipe As Long
Dim hChildWritePipe As Long



'上面是公共部分.

Private Sub Form_Load()
    txtCommand.Text = ""
    txtMessage.Text = ""
    txtMessage.Locked = True
    
    ' 创建管道
    CreatePipe hReadPipe, hWritePipe, ByVal 0, ByVal 0
    CreatePipe hChildReadPipe, hChildWritePipe, ByVal 0, ByVal 0
    SetHandleInformation hWritePipe, HANDLE_FLAG_INHERIT, HANDLE_FLAG_INHERIT
    SetHandleInformation hChildReadPipe, HANDLE_FLAG_INHERIT, HANDLE_FLAG_INHERIT
    Dim dwMode As Long
    dwMode = PIPE_NOWAIT
    SetNamedPipeHandleState hReadPipe, dwMode, ByVal 0, ByVal 0
    
    ' 创建CMD进程
    Dim stProcessInfo As PROCESS_INFORMATION
    Dim stStartInfo As STARTUPINFO
    stStartInfo.cb = LenB(stStartInfo)
    stStartInfo.dwFlags = STARTF_USESTDHANDLES
    stStartInfo.hStdError = hWritePipe
    stStartInfo.hStdOutput = hWritePipe
    stStartInfo.hStdInput = hChildReadPipe
    
    Dim strExe As String
    strExe = "cmd"
    If False = CreateProcess(ByVal vbNullString, ByVal strExe, ByVal 0, ByVal 0, ByVal True, ByVal DETACHED_PROCESS, ByVal 0, ByVal vbNullString, stStartInfo, stProcessInfo) Then
        MsgBox "启动进程失败!"
        Exit Sub
    Else
        CloseHandle stProcessInfo.hThread
        CloseHandle stProcessInfo.hProcess
    End If
    ReadFromChildPipe
End Sub

Private Sub Form_Unload(Cancel As Integer)
    CloseHandle hReadPipe
    CloseHandle hWritePipe
    CloseHandle hChildReadPipe
    CloseHandle hChildWritePipe
End Sub

Private Sub txtCommand_KeyPress(KeyAscii As Integer)
    If KeyAscii = vbKeyReturn Then
        Dim nWrite As Long
        Dim strBuffer As String
        strBuffer = txtCommand.Text & vbCrLf
        Dim bResult As Boolean
        bResult = WriteFile(ByVal hChildWritePipe, ByVal strBuffer, ByVal Len(strBuffer), nWrite, ByVal 0)
        If bResult = True Then
            ReadFromChildPipe
        Else
            MsgBox "写入失败."
        End If
        txtCommand.Text = ""
    End If
End Sub

Private Sub ReadFromChildPipe()
    Dim nRead As Long
    Dim strBuffer As String
    Dim nBufferLen As Long
    nRead = -1
    Do While nRead <> 0
        nBufferLen = 65536
        strBuffer = String(nBufferLen, Chr(0))
        Sleep 10
        ReadFile hReadPipe, ByVal strBuffer, ByVal nBufferLen, nRead, ByVal 0
        Sleep 10
        If nRead <> 0 Then
            strBuffer = Left(strBuffer, nRead)
            txtMessage.Text = txtMessage.Text & strBuffer
            txtMessage.SelStart = Len(txtMessage.Text)
        End If
    Loop
End Sub



  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值