Question Capturing screen and webcam video simultaneously?

sspears2020

New member
Joined
Nov 11, 2010
Messages
3
Programming Experience
1-3
Hey guys,

I'm working on a screen capture and webcam capture program that will record both at the same time. I currently have a button that starts the screen cap (while opening a ppt) and a keyboard hook that stops it when I hit F12. I also have a button that starts webcam recording, and a button that stops the recording.

So they are both working individually, but when I try to do both at the same time (calling both actions when I hit the start capture button) it sort of freezes up both processes. I'm thinking maybe they need to be run on different threads but I've tried doing so and I think I'm either doing it wrong or its just not making any difference?

Also on a side note - when I am capturing video from the webcam the keyboard hook no longer works :/

Here is the code for my form, if you want the keyboard hook let me know:

VB.NET:
Imports Microsoft.Expression.Encoder.ScreenCapture
Imports Microsoft.Office.Interop
Imports Microsoft.Office.Interop.PowerPoint
Imports Microsoft.Expression.Encoder.Devices
Imports System.Runtime.InteropServices
Imports System.Windows.Forms
Imports System.Threading

Public Class VideoRecorder
    Inherits System.Windows.Forms.Form

    Dim ScreenCap As New ScreenCaptureJob
    Dim appPowerpoint As PowerPoint.Application = New PowerPoint.Application
    Dim ShutDownAll As Boolean = False
    Dim shortName As String

    ' Create constant using attend in function of DLL file.

    Const WM_CAP As Short = &H400S
    Const WM_CAP_DRIVER_CONNECT As Integer = WM_CAP + 10
    Const WM_CAP_DRIVER_DISCONNECT As Integer = WM_CAP + 11
    Const WM_CAP_EDIT_COPY As Integer = WM_CAP + 30
    Const WM_CAP_SET_PREVIEW As Integer = WM_CAP + 50
    Const WM_CAP_SET_PREVIEWRATE As Integer = WM_CAP + 52
    Const WM_CAP_SET_SCALE As Integer = WM_CAP + 53
    Const WS_CHILD As Integer = &H40000000
    Const WS_VISIBLE As Integer = &H10000000
    Const SWP_NOMOVE As Short = &H2S
    Const SWP_NOSIZE As Short = 1
    Const SWP_NOZORDER As Short = &H4S
    Const HWND_BOTTOM As Short = 1
    Const WM_CAP_FILE_SAVEAS As Integer = WM_CAP + 23
    Const WM_CAP_SEQUENCE As Integer = WM_CAP + 62

    Dim iDevice As Integer = 0  ' Normal device ID 
    Dim hHwnd As Integer  ' Handle value to preview window

    ' Declare function from AVI capture DLL.

    Declare Function SendMessage Lib "user32" Alias "SendMessageA" _
        (ByVal hwnd As IntPtr, ByVal wMsg As Integer, ByVal wParam As Integer, _
         ByVal lParam As String) As Integer

    Declare Function SetWindowPos Lib "user32" Alias "SetWindowPos" (ByVal hwnd As Integer, _
        ByVal hWndInsertAfter As Integer, ByVal x As Integer, ByVal y As Integer, _
        ByVal cx As Integer, ByVal cy As Integer, ByVal wFlags As Integer) As Integer

    Declare Function DestroyWindow Lib "user32" (ByVal hndw As Integer) As Boolean

    Declare Function capCreateCaptureWindowA Lib "avicap32.dll" _
        (ByVal lpszWindowName As String, ByVal dwStyle As Integer, _
        ByVal x As Integer, ByVal y As Integer, ByVal nWidth As Integer, _
        ByVal nHeight As Short, ByVal hWndParent As Integer, _
        ByVal nID As Integer) As Integer

    Declare Function capGetDriverDescriptionA Lib "avicap32.dll" (ByVal wDriver As Short, _
        ByVal lpszName As String, ByVal cbName As Integer, ByVal lpszVer As String, _
        ByVal cbVer As Integer) As Boolean

    Dim WithEvents K As New Keyboard

    Private Sub VideoRecorder_Load1(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
        K.CreateHook()
        OpenPreviewWindow()

    End Sub

    Private Sub VideoRecorder_FormClosing(ByVal sender As Object, ByVal e As System.Windows.Forms.FormClosingEventArgs) Handles Me.FormClosing
        K.DiposeHook()
        ClosePreviewWindow()
    End Sub

    Private Sub K_Down(ByVal Key As String) Handles K.Down
        If Key.ToString = "<F12>" Then
            Label1.Text = Key.ToString
            ShutDownAll = True
            Timer2.Enabled = True
        End If
    End Sub

    Private Sub Timer2_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer2.Tick
        If ShutDownAll = True Then
            'StopVideoCap()
            ScreenCap.Stop()
            ScreenCap.Dispose()
            appPowerpoint.ActivePresentation.Close()
            appPowerpoint.Quit()
            Me.Close()
        End If
    End Sub

    Private Sub btnChooseFile_Click_1(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnChooseFile.Click
        ChooseFileDialog.ShowDialog()
        txtChooseFile.Text = ChooseFileDialog.FileName
        Dim less As Integer
        If txtChooseFile.Text.Contains(".ppt") Then
            less = 4
            If txtChooseFile.Text.Contains(".pptx") Then
                less = 5
            End If
        End If
        shortName = txtChooseFile.Text.Substring(0, txtChooseFile.Text.Length - less)
    End Sub

    Private Sub btnStart_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnStart.Click
        If txtChooseFile.Text = "" Then
            MsgBox("Please choose a PowerPoint file.")
            Exit Sub
        End If

        'open powerpoint slideshow
        Try
            Process.Start(txtChooseFile.Text)
        Catch ex As Exception
            MsgBox(ex.Message)
        End Try

        appPowerpoint.Activate()

        'capture settings
        ScreenCap.CaptureMouseCursor = False
        ScreenCap.CaptureRectangle = Screen.PrimaryScreen.Bounds
        ScreenCap.ShowCountdown = True
        ScreenCap.OutputScreenCaptureFileName = shortName + "_scr" + ".wmv"
        ScreenCap.ScreenCaptureVideoProfile.FrameRate = 60
        ScreenCap.Start()

        Timer1.Start()
    End Sub

    Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
        If appPowerpoint.Presentations.Count = 1 Then
            StartShow()
            Timer1.Enabled = False
        End If
    End Sub

    Private Sub StartShow()
        appPowerpoint.ActivePresentation.SlideShowSettings.Run()
        'StartVideoCap()
    End Sub


    '***************** VIDEO CAPTURE ************************
    Private Sub OpenPreviewWindow()
        Dim iHeight As Integer = picCapture.Height
        Dim iWidth As Integer = picCapture.Width

        ' Open Preview window in picturebox .
        ' Create a child window with capCreateCaptureWindowA so you can display it in a picturebox.

        hHwnd = capCreateCaptureWindowA(iDevice, WS_VISIBLE Or WS_CHILD, 0, 0, 640, _
            480, picCapture.Handle.ToInt32, 0)

        'Label1.Text = SendMessage(hHwnd, WM_CAP_DRIVER_CONNECT, iDevice, 0)
        ' Connect to device
        If SendMessage(hHwnd, WM_CAP_DRIVER_CONNECT, iDevice, 0) Then

            ' Set the preview scale
            SendMessage(hHwnd, WM_CAP_SET_SCALE, True, 0)

            ' Set the preview rate in milliseconds
            SendMessage(hHwnd, WM_CAP_SET_PREVIEWRATE, 15, 0)

            ' Start previewing the image from the camera 
            SendMessage(hHwnd, WM_CAP_SET_PREVIEW, True, 0)

            ' Resize window to fit in picturebox 
            SetWindowPos(hHwnd, HWND_BOTTOM, 0, 0, picCapture.Width, picCapture.Height, _
                                   SWP_NOMOVE Or SWP_NOZORDER)
            'btnSave.Enabled = True
            btnStop.Enabled = True
        Else
            ' Error connecting to device close window 
            DestroyWindow(hHwnd)
        End If
    End Sub

    ' Finally, to close the preview window, disconnect from the device and destroy the preview window. 

    Private Sub ClosePreviewWindow()
        ' Disconnect from device
        SendMessage(hHwnd, WM_CAP_DRIVER_DISCONNECT, iDevice, 0)

        ' close window 
        DestroyWindow(hHwnd)
    End Sub

    Private Sub StartVideoCap()
        Try
            SendMessage(hHwnd, WM_CAP_SEQUENCE, 0, 0)
        Catch ex As Exception
            MsgBox(ex.ToString)
        End Try
    End Sub
    Private Sub StopVideoCap()
        Dim avi As String = shortName & "_avi" & ".avi"

        'SAVE FILE
        Try
            SendMessage(hHwnd, WM_CAP_FILE_SAVEAS, 0, avi)
        Catch ex As Exception
            MsgBox(ex.Message)
        End Try
    End Sub

    Private Sub btnTestStart_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnTestStart.Click
        StartVideoCap()
    End Sub

    Private Sub btnStop_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnStop.Click
        StopVideoCap()
    End Sub

End Class
 
Back
Top