Question / Help [SOLVED] OBS not reloading ip camera stream

Ground Loop

New Member
Hey guys,
I'm on Windows 7 64-bit
OBS 19.0.3 32-bit
VLC 2.2.2 32-bit
I've been experimenting with OBS for a continuous live stream of an ip camera, but for the life of me I can't get it to auto-reconnect to the camera's RTSP stream whenever the connection is temporarily lost.
This happens ocasionally due to network glitches or a power failure.

I tried both the "VLC Video Source" and the "Media Source" options, while fiddling with their parameters back and forth.
Neither of them reconnects...
- Media Source at least goes transparent when the connection is lost, and that is what I want.

Can you help?
Thanks in advance.

Code:
01:16:24.984: [Media Source 'Media Source']: settings:
01:16:24.984:     input:                   rtsp://192.168.1.64:554
01:16:24.984:     input_format:           
01:16:24.984:     is_looping:              no
01:16:24.984:     is_hw_decoding:          yes
01:16:24.984:     is_clear_on_media_end:   yes
01:16:24.984:     restart_on_activate:     yes
01:16:24.984:     close_when_inactive:     yes
01:16:24.984: MP: Failed to open media: 'rtsp://192.168.1.64:554'
 

Ground Loop

New Member
Ok, since no one is coming up with ideas, I think I can make a workaround.

How about this:

OBS settings --> hotkeys:
Show Media Souce: CTRL+ALT+SHIFT+S
Hide Media Source: CTRL+ALT+SHIFT+H​

Then, a script with the following behavior:
//// Monitoring the TCP connection between obs32.exe and the ip camera (RTSP port 554) ////
- While "Connection state" is "ESTABLISHED" --> keep querying the connection state every 10 seconds.
- If "Connection state" changed to something else:
- Send Hide hotkey (this stops the media and makes it invisible)
- Do this (until it works):
- Ping the camera's ip address
- If ping is ok --> attempt to open port 554
- If port 554 is opened --> ok, close it​
- Send Show hotkey (this attempts a new connection in OBS)
- Wait for 10 seconds
- Loop from the beginning.

I will attempt to implement this in a couple of days, and then I'll report back.
 

Kurtfrank

New Member
Hi,

I have the same problem with the IP camera. It works for a couple of hours and does not reconnect automatically.
 

Ground Loop

New Member
Here it is. Something to work on, but it does the job.

Written in AutoIt.
- You need to install AutoIt in order to compile/run this script.
- I recommend you also install SciTE to edit the file (to set some variables such as camera's IP address).​
Tested under Windows 7 64-bit (x86).
Should work on WinXP and above.
No VLC required.



Code:
; 2017-08-03
; //// Monitoring the TCP connection between obs32.exe and the ip camera (RTSP port 554) ////
; - If OBS isn't open yet, opens and starts streaming
; - Attempts to restart ip camera connection when lost
;
; NOTE:
; PRELIMINARY VERSION
; WARNING - as it is, it creates a logfile; if things don't go as planned, the log file can become VERY LARGE!
; (let's say 10MB per hour)
;
;
; ADAPTED FROM:
; NETWORK CONNECTIONS VIEWER, written by trancexx
; https://www.autoitscript.com/forum/topic/87581-check-a-tcp-ip-connection/


; exits if another instance is already running
#include <Misc.au3>
If _Singleton("ConnView_STRIPED_DOWN", 1) = 0 Then
    __Log("FATAL ERROR: Another instance of this program is already running. Exiting...")
    Exit
EndIf


#include <Array.au3>
Global Const $sFullPath = "C:\Program Files (x86)\obs-studio\bin\32bit\"
Global Const $sPIDname = "obs32.exe"
Global Const $sWinTitle = "[TITLE:OBS; CLASS:Qt5QWindowIcon]"
Global Const $sWinText = "obs32"
Global Const $sProfile = "Untitled" ; profile name - if no match, opens profile from last execution
Global Const $sCollection = "Untitled" ; scene collection name - if no match, opens scene collection from last execution
Global Const $sRemoteIP = "192.168.1.64" ; your camera ip
Global Const $iRemotePort = 554 ; RTSP port
Global Const $iSleepTime = 2000 ; delay to check for connection
Global Const $sSendHide = "{CTRLDOWN}{ALTDOWN}{SHIFTDOWN}H{CTRLUP}{ALTUP}{SHIFTUP}" ; OBS hotkey to hide media (stop)
Global Const $sSendShow = "{CTRLDOWN}{ALTDOWN}{SHIFTDOWN}S{CTRLUP}{ALTUP}{SHIFTUP}" ; OBS hotkey to show media (play)


Opt("MustDeclareVars", 1)
Opt("WinWaitDelay", 0) ; 0 ms

Global Const $hNTDLL = DllOpen("ntdll.dll")
Global Const $hKERNEL32 = DllOpen("kernel32.dll")
Global Const $hUSER32 = DllOpen("user32.dll")
Global Const $hIPHLPAPI = DllOpen("iphlpapi.dll")
Global Const $hWS232 = DllOpen("ws2_32.dll")
Global Const $hPSAPI = DllOpen("psapi.dll")
Global Const $hWTSAPI32 = DllOpen("wtsapi32.dll")
Global Const $hADVAPI32 = DllOpen("advapi32.dll")


Global $aTCPArray



Global $hLog = FileOpen("log.txt", 1)
Func __Log($comment)
    Local $sLine =  __DATETIME()&@TAB&$comment
    ConsoleWrite("-> (Logged) " & $sLine & @CRLF)
    FileWriteLine($hLog, $sLine)
EndFunc




; START LOOP
While 1
    While Not ProcessExists($sPIDname)
        __Log("ERROR: Process """ & $sPIDname & """ not found. Starting process...")
        ShellExecute ($sFullPath&$sPIDname, "--profile """&$sProfile&""" --collection """&$sCollection&""" --startstreaming", $sFullPath)
        ProcessWait($sPIDname, $iSleepTime*5)
        ;Exit -2
    WEnd

    $aTCPArray = _CV_GetExtendedTcpTable()
    If @error Then
        __Log("FATAL ERROR: Unable to get TCP table. Exiting...")
        Exit -2
    EndIf

    ;_ArrayDisplay($aTCPArray, "TCP Table")

    If UBound($aTCPArray) < 1 Then
        __Log("Connection not found between """ & $sPIDname & """ and IP address " & $sRemoteIP & " at port " & $iRemotePort)
        __Restart_Media()
    Else
        If UBound($aTCPArray) > 1 Then
            __Log("WARNING: More than one connection exists between """ & $sPIDname & """ and IP address " & $sRemoteIP & " at port " & $iRemotePort)
        EndIf

        For $i = 0 To UBound($aTCPArray) - 1
            If $aTCPArray[$i][2] <> "ESTABLISHED" Then
                __Log("ERROR: Connection between """ & $sPIDname & """ and IP address " & $sRemoteIP & " at port " & $iRemotePort & " has state """ & $aTCPArray[$i][2] & """")
                __Restart_Media()
            Else
                ConsoleWrite("+> " & __DATETIME()&@TAB& "IP Camera stream connection to OBS seems to be ok" & @CRLF)
            EndIf
        Next
    EndIf

    Sleep($iSleepTime)
WEnd



Func _CV_GetExtendedTcpTable()

    Local $aCall = DllCall($hIPHLPAPI, "dword", "GetExtendedTcpTable", _
            "ptr*", 0, _
            "dword*", 0, _
            "int", 1, _ ; 1, sort in ascending order
            "dword", 2, _ ; AF_INET4
            "dword", 5, _ ; TCP_TABLE_OWNER_PID_ALL
            "dword", 0)

    If @error Then
        Return SetError(1, 0, 0)
    EndIf

    If $aCall[0] <> 122 Then ; ERROR_INSUFFICIENT_BUFFER
        Return SetError(2, 0, 0)
    EndIf

    Local $iSize = $aCall[2]

    Local $tByteStructure = DllStructCreate("byte[" & $iSize & "]")

    $aCall = DllCall($hIPHLPAPI, "dword", "GetExtendedTcpTable", _
            "ptr", DllStructGetPtr($tByteStructure), _
            "dword*", $iSize, _
            "int", 1, _ ; 1, sort in ascending order
            "dword", 2, _ ; AF_INET4
            "dword", 5, _ ; TCP_TABLE_OWNER_PID_ALL
            "dword", 0)

    If @error Or $aCall[0] Then
        Return SetError(3, 0, 0)
    EndIf

    Local $tMIB_TCPTABLE_OWNER_PID_DWORDS = DllStructCreate("dword[" & Ceiling($iSize / 4) & "]", DllStructGetPtr($tByteStructure))

    Local $iTCPentries = DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1)

    Local $aConnections[$iTCPentries][3] ; PID_Name | PID_Number | Connection_state

    Local $aState[12] = ["CLOSED", "LISTENING", "SYN_SENT", "SYN_RCVD", "ESTABLISHED", "FIN_WAIT1", "FIN_WAIT2", "CLOSE_WAIT", "CLOSING", "LAST_ACK", "TIME_WAIT", "DELETE_TCB"]

    Local $aProcessList = ProcessList()
    ;_ArrayDisplay($aProcesses)

    Local $iOffset
    Local $iIP

    Local $sIP = ""
    Local $iPort_LOCAL = 0

    TCPStartup()

    Local $iArrayElement = 0

    For $i = 1 To $iTCPentries

        $iOffset = ($i - 1) * 6 + 1 ; going thru array of dwords

        If DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 1) < 3 Then
            ; ignore generic connections
            ContinueLoop
        Else
            $iIP = DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 4)
            $sIP = BitOR(BinaryMid($iIP, 1, 1), 0) & "." & BitOR(BinaryMid($iIP, 2, 1), 0) & "." & BitOR(BinaryMid($iIP, 3, 1), 0) & "." & BitOR(BinaryMid($iIP, 4, 1), 0)
            If $sIP <> $sRemoteIP Then
                ContinueLoop
            Else ; this is the remote IP that we want to monitor
                $iPort_LOCAL = Dec(Hex(BinaryMid(DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 5), 1, 2)))
                If $iPort_LOCAL == $iRemotePort Then ; this is the intended port that we want to monitor
                    ;ConsoleWrite("!!!!! found ip and port" & @CRLF)
                    $aConnections[$iArrayElement][2] = $aState[DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 1) - 1] ; Connection state
                    $aConnections[$iArrayElement][1] = DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 6) ; PID_Number
                    For $j = 1 To $aProcessList[0][0]
                        If $aProcessList[$j][1] == $aConnections[$iArrayElement][1] Then
                            $aConnections[$iArrayElement][0] = $aProcessList[$j][0]
                            ExitLoop
                        EndIf
                    Next
                    If $aConnections[$iArrayElement][0] <> $sPIDname Then
                        ContinueLoop ; ignore this connection because it's not from the intended process name.
                    Else
                        $iArrayElement += 1
                    EndIf
                EndIf
            EndIf
        EndIf

    Next

    TCPShutdown()

    _ArrayDelete($aConnections, $iArrayElement & "-" & UBound($aConnections)-1)

    Return $aConnections

EndFunc   ;==>_CV_GetExtendedTcpTable






Func __Send_Show()
    __Log("Showing Media")
    Local $hWinHandle = WinGetHandle($sWinTitle,$sWinText)
    SendKeepActive($hWinHandle)
    Send($sSendShow)
EndFunc




Func __Send_Hide()
    __Log("Hiding Media")
    Local $hWinHandle = WinGetHandle($sWinTitle,$sWinText)
    SendKeepActive($hWinHandle)
    Send($sSendHide)
EndFunc




Func __Restart_Media()
    __Send_Hide()

    __Log("Ping")
    While Ping($sRemoteIP,1000) == 0
        ConsoleWrite("!> " & __DATETIME()&@TAB& "Ping timeout" & @CRLF)
    WEnd

    __Log("Port test")
    TCPStartup()
    While TCPConnect($sRemoteIP, $iRemotePort) < 1
        ConsoleWrite("!> " & __DATETIME()&@TAB& "Can't open ip camera port "&$iRemotePort & @CRLF)
        Sleep(1000)
    WEnd
    TCPShutdown()

    __Send_Show()
EndFunc



Func __DATETIME()
    Return @YEAR&"-"&@MON&"-"&@MDAY&" "&@HOUR&":"&@MIN&":"&@SEC&"."&@MSEC
EndFunc
 

hoerich

New Member
Thanks for the workaround, I am about to give it a try.
But first I have to understand this completely ;-)

Does it matter which version of AutoIT I use to execute the script? Or use the same as obs is installed?
Running multiple scripts for 2 or 3 cameras is okay?

thanksalot
 

hoerich

New Member
source is an rtsp-stream, so no loop-function available.
"restarting the source if source becomes active" is activated.

I see in the AutoIT-script that this code is also scene-based.
So it will be necessary to execute one script per scene?
And how to handle a IP Cam if it is present in two or more scenes?
 

Ground Loop

New Member
[EDIT] shortcut = hotkey

Does it matter which version of AutoIT I use to execute the script? Or use the same as obs is installed?
In the official AutoIt site, there is only one AutoIt installer available for download, and that's the one you should install.
AutoIt --> Downloads --> AutoIt full installation

Running multiple scripts for 2 or 3 cameras is okay?
Haven't tested, should work, but:
- the script checks if obs32.exe is running, and starts obs32.exe if it's not. Multiple scripts will be doing this. Not a big concern, but just so you know, it would be better to rewrite the one script to support multiple cameras.
- you need to create a different hotkey for each camera, and adjust each script accordingly.

source is an rtsp-stream, so no loop-function available.
"restarting the source if source becomes active" is activated.
Indeed I confirm that no option in OBS works flawlessly, neither with Media Source nor with VLC source.
Eventually the VLC source stopped working altogether. Just a frozen frame. But VLC standalone runs fine.

I see in the AutoIT-script that this code is also scene-based.
So it will be necessary to execute one script per scene?
And how to handle a IP Cam if it is present in two or more scenes?
The script isn't scene-based. It's:
- process-based - checks that obs32.exe is running;
- IP-based - checks that obs32.exe is connected to the ip camera on the specified port;
- and hotkey-based - sends the hotkey to hide/show media when the IP connection is lost and then reestablished.
 

Kurtfrank

New Member
Hi,

I tried the above script and it does not work for me.

It will restart the camera once when I run the script.

Can you please help please.

Thanks,
 

StreamTwitch

New Member
Thanks for this script Ground Loop. I have been successful in deploying this with multiple cameras and it appears to work well as a workaround. I did modify it a bit as you suggested with regard to only checking once if the instance of OBS is running and then each camera connection separately. Wish there was more effort with regard to RTSP stream and making sure it is restarted properly upon disconnection from dev's of OBS, as I feel it is vital for anyone looking to use OBS in a live cam stream scenario. Until then, this can be a temporary bandaid to keep it limping. Thanks again for sharing!
 
I had the exact problem with three Ubiquiti Aircams running on Firmware 1.2.

OBS Studio would always loose comnnection and the frame would freeze, no matter what settings I choose. I then deleted all sources and added the cams back as VLC sources and now it works. Even when I reboot the cams while livestreaming OBS Studio picks up the stream a few seconds afterwards and continues as nothing has ever happend.

Hope this helps someone.
 

Jaom

New Member
This is riddiculous. OBS Classic did not have this issue at all. All of a sudden OBS Studio cannot reconnect to a RSTP stream (there are reports about the issue from a long time ago, this is not the only ), someone writes a crazy workaround out of the box and half a year later the problem is still there. I was even reported on the bugrtracker but ended with... no priority.
 

Ground Loop

New Member
I know, right?
And the solution seems simple enough to implement into OBS.
However, this is free software, and it's up to the developers to choose what they want to spend their time with.

Back in August 2017, I've tried what Manuel mentioned above, but it didn't work for me.
Still, I'm glad that we have workarounds, and a couple of people did manage to make it work one way or another.

Sorry for not replying here in a while. The script has been working flawlessly for me since then.
24/7 never touched that computer again :)
 

Ground Loop

New Member
Actually I think you're quite on the money (pun intended); donation-based development.
With cryptocurrency they could open a new wallet for each request, and essentially donations could serve as priority votes.
They could even set donation targets, or even smart contracts for that (kickstarter style).

Although for the time being I'd favor something other than Bitcoin or Bitcoin Cash. Average per transaction fees at current USD rates:
BTC fee: 10 USD
BCH fee: 0,20 USD
ETH (Ethereum) fee: 1,06 USD
LTC (Litecoin) fee: 0,30 USD
XLM (Stellar Lumens) fee: 0,00001 USD

This creates a trust issue however; dev teams could in theory "implement" bugs in order to collect $ for fixing them.
 
Here it is. Something to work on, but it does the job.

Written in AutoIt.
- You need to install AutoIt in order to compile/run this script.
- I recommend you also install SciTE to edit the file (to set some variables such as camera's IP address).​
Tested under Windows 7 64-bit (x86).
Should work on WinXP and above.
No VLC required.



Code:
; 2017-08-03
; //// Monitoring the TCP connection between obs32.exe and the ip camera (RTSP port 554) ////
; - If OBS isn't open yet, opens and starts streaming
; - Attempts to restart ip camera connection when lost
;
; NOTE:
; PRELIMINARY VERSION
; WARNING - as it is, it creates a logfile; if things don't go as planned, the log file can become VERY LARGE!
; (let's say 10MB per hour)
;
;
; ADAPTED FROM:
; NETWORK CONNECTIONS VIEWER, written by trancexx
; https://www.autoitscript.com/forum/topic/87581-check-a-tcp-ip-connection/


; exits if another instance is already running
#include <Misc.au3>
If _Singleton("ConnView_STRIPED_DOWN", 1) = 0 Then
    __Log("FATAL ERROR: Another instance of this program is already running. Exiting...")
    Exit
EndIf


#include <Array.au3>
Global Const $sFullPath = "C:\Program Files (x86)\obs-studio\bin\32bit\"
Global Const $sPIDname = "obs32.exe"
Global Const $sWinTitle = "[TITLE:OBS; CLASS:Qt5QWindowIcon]"
Global Const $sWinText = "obs32"
Global Const $sProfile = "Untitled" ; profile name - if no match, opens profile from last execution
Global Const $sCollection = "Untitled" ; scene collection name - if no match, opens scene collection from last execution
Global Const $sRemoteIP = "192.168.1.64" ; your camera ip
Global Const $iRemotePort = 554 ; RTSP port
Global Const $iSleepTime = 2000 ; delay to check for connection
Global Const $sSendHide = "{CTRLDOWN}{ALTDOWN}{SHIFTDOWN}H{CTRLUP}{ALTUP}{SHIFTUP}" ; OBS hotkey to hide media (stop)
Global Const $sSendShow = "{CTRLDOWN}{ALTDOWN}{SHIFTDOWN}S{CTRLUP}{ALTUP}{SHIFTUP}" ; OBS hotkey to show media (play)


Opt("MustDeclareVars", 1)
Opt("WinWaitDelay", 0) ; 0 ms

Global Const $hNTDLL = DllOpen("ntdll.dll")
Global Const $hKERNEL32 = DllOpen("kernel32.dll")
Global Const $hUSER32 = DllOpen("user32.dll")
Global Const $hIPHLPAPI = DllOpen("iphlpapi.dll")
Global Const $hWS232 = DllOpen("ws2_32.dll")
Global Const $hPSAPI = DllOpen("psapi.dll")
Global Const $hWTSAPI32 = DllOpen("wtsapi32.dll")
Global Const $hADVAPI32 = DllOpen("advapi32.dll")


Global $aTCPArray



Global $hLog = FileOpen("log.txt", 1)
Func __Log($comment)
    Local $sLine =  __DATETIME()&@TAB&$comment
    ConsoleWrite("-> (Logged) " & $sLine & @CRLF)
    FileWriteLine($hLog, $sLine)
EndFunc




; START LOOP
While 1
    While Not ProcessExists($sPIDname)
        __Log("ERROR: Process """ & $sPIDname & """ not found. Starting process...")
        ShellExecute ($sFullPath&$sPIDname, "--profile """&$sProfile&""" --collection """&$sCollection&""" --startstreaming", $sFullPath)
        ProcessWait($sPIDname, $iSleepTime*5)
        ;Exit -2
    WEnd

    $aTCPArray = _CV_GetExtendedTcpTable()
    If @error Then
        __Log("FATAL ERROR: Unable to get TCP table. Exiting...")
        Exit -2
    EndIf

    ;_ArrayDisplay($aTCPArray, "TCP Table")

    If UBound($aTCPArray) < 1 Then
        __Log("Connection not found between """ & $sPIDname & """ and IP address " & $sRemoteIP & " at port " & $iRemotePort)
        __Restart_Media()
    Else
        If UBound($aTCPArray) > 1 Then
            __Log("WARNING: More than one connection exists between """ & $sPIDname & """ and IP address " & $sRemoteIP & " at port " & $iRemotePort)
        EndIf

        For $i = 0 To UBound($aTCPArray) - 1
            If $aTCPArray[$i][2] <> "ESTABLISHED" Then
                __Log("ERROR: Connection between """ & $sPIDname & """ and IP address " & $sRemoteIP & " at port " & $iRemotePort & " has state """ & $aTCPArray[$i][2] & """")
                __Restart_Media()
            Else
                ConsoleWrite("+> " & __DATETIME()&@TAB& "IP Camera stream connection to OBS seems to be ok" & @CRLF)
            EndIf
        Next
    EndIf

    Sleep($iSleepTime)
WEnd



Func _CV_GetExtendedTcpTable()

    Local $aCall = DllCall($hIPHLPAPI, "dword", "GetExtendedTcpTable", _
            "ptr*", 0, _
            "dword*", 0, _
            "int", 1, _ ; 1, sort in ascending order
            "dword", 2, _ ; AF_INET4
            "dword", 5, _ ; TCP_TABLE_OWNER_PID_ALL
            "dword", 0)

    If @error Then
        Return SetError(1, 0, 0)
    EndIf

    If $aCall[0] <> 122 Then ; ERROR_INSUFFICIENT_BUFFER
        Return SetError(2, 0, 0)
    EndIf

    Local $iSize = $aCall[2]

    Local $tByteStructure = DllStructCreate("byte[" & $iSize & "]")

    $aCall = DllCall($hIPHLPAPI, "dword", "GetExtendedTcpTable", _
            "ptr", DllStructGetPtr($tByteStructure), _
            "dword*", $iSize, _
            "int", 1, _ ; 1, sort in ascending order
            "dword", 2, _ ; AF_INET4
            "dword", 5, _ ; TCP_TABLE_OWNER_PID_ALL
            "dword", 0)

    If @error Or $aCall[0] Then
        Return SetError(3, 0, 0)
    EndIf

    Local $tMIB_TCPTABLE_OWNER_PID_DWORDS = DllStructCreate("dword[" & Ceiling($iSize / 4) & "]", DllStructGetPtr($tByteStructure))

    Local $iTCPentries = DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1)

    Local $aConnections[$iTCPentries][3] ; PID_Name | PID_Number | Connection_state

    Local $aState[12] = ["CLOSED", "LISTENING", "SYN_SENT", "SYN_RCVD", "ESTABLISHED", "FIN_WAIT1", "FIN_WAIT2", "CLOSE_WAIT", "CLOSING", "LAST_ACK", "TIME_WAIT", "DELETE_TCB"]

    Local $aProcessList = ProcessList()
    ;_ArrayDisplay($aProcesses)

    Local $iOffset
    Local $iIP

    Local $sIP = ""
    Local $iPort_LOCAL = 0

    TCPStartup()

    Local $iArrayElement = 0

    For $i = 1 To $iTCPentries

        $iOffset = ($i - 1) * 6 + 1 ; going thru array of dwords

        If DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 1) < 3 Then
            ; ignore generic connections
            ContinueLoop
        Else
            $iIP = DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 4)
            $sIP = BitOR(BinaryMid($iIP, 1, 1), 0) & "." & BitOR(BinaryMid($iIP, 2, 1), 0) & "." & BitOR(BinaryMid($iIP, 3, 1), 0) & "." & BitOR(BinaryMid($iIP, 4, 1), 0)
            If $sIP <> $sRemoteIP Then
                ContinueLoop
            Else ; this is the remote IP that we want to monitor
                $iPort_LOCAL = Dec(Hex(BinaryMid(DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 5), 1, 2)))
                If $iPort_LOCAL == $iRemotePort Then ; this is the intended port that we want to monitor
                    ;ConsoleWrite("!!!!! found ip and port" & @CRLF)
                    $aConnections[$iArrayElement][2] = $aState[DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 1) - 1] ; Connection state
                    $aConnections[$iArrayElement][1] = DllStructGetData($tMIB_TCPTABLE_OWNER_PID_DWORDS, 1, $iOffset + 6) ; PID_Number
                    For $j = 1 To $aProcessList[0][0]
                        If $aProcessList[$j][1] == $aConnections[$iArrayElement][1] Then
                            $aConnections[$iArrayElement][0] = $aProcessList[$j][0]
                            ExitLoop
                        EndIf
                    Next
                    If $aConnections[$iArrayElement][0] <> $sPIDname Then
                        ContinueLoop ; ignore this connection because it's not from the intended process name.
                    Else
                        $iArrayElement += 1
                    EndIf
                EndIf
            EndIf
        EndIf

    Next

    TCPShutdown()

    _ArrayDelete($aConnections, $iArrayElement & "-" & UBound($aConnections)-1)

    Return $aConnections

EndFunc   ;==>_CV_GetExtendedTcpTable






Func __Send_Show()
    __Log("Showing Media")
    Local $hWinHandle = WinGetHandle($sWinTitle,$sWinText)
    SendKeepActive($hWinHandle)
    Send($sSendShow)
EndFunc




Func __Send_Hide()
    __Log("Hiding Media")
    Local $hWinHandle = WinGetHandle($sWinTitle,$sWinText)
    SendKeepActive($hWinHandle)
    Send($sSendHide)
EndFunc




Func __Restart_Media()
    __Send_Hide()

    __Log("Ping")
    While Ping($sRemoteIP,1000) == 0
        ConsoleWrite("!> " & __DATETIME()&@TAB& "Ping timeout" & @CRLF)
    WEnd

    __Log("Port test")
    TCPStartup()
    While TCPConnect($sRemoteIP, $iRemotePort) < 1
        ConsoleWrite("!> " & __DATETIME()&@TAB& "Can't open ip camera port "&$iRemotePort & @CRLF)
        Sleep(1000)
    WEnd
    TCPShutdown()

    __Send_Show()
EndFunc



Func __DATETIME()
    Return @YEAR&"-"&@MON&"-"&@MDAY&" "&@HOUR&":"&@MIN&":"&@SEC&"."&@MSEC
EndFunc



Hello,
How are you?

Please, where I put the script?
Inside OBS....where? A folder?
Thanks for attention and help
 

Ground Loop

New Member
The script goes wherever you want it to.
Read the post, you need to install AutoIt.
If you're not technically inclined, you'll have to spend some time figuring out what to change for your case.
It's not "plug and play".
You need to set the variables for the OBS location, and camera IP address and so on.
 

JaredC18

New Member
[EDIT] shortcut = hotkey


In the official AutoIt site, there is only one AutoIt installer available for download, and that's the one you should install.
AutoIt --> Downloads --> AutoIt full installation


Haven't tested, should work, but:
- the script checks if obs32.exe is running, and starts obs32.exe if it's not. Multiple scripts will be doing this. Not a big concern, but just so you know, it would be better to rewrite the one script to support multiple cameras.
- you need to create a different hotkey for each camera, and adjust each script accordingly.


Indeed I confirm that no option in OBS works flawlessly, neither with Media Source nor with VLC source.
Eventually the VLC source stopped working altogether. Just a frozen frame. But VLC standalone runs fine.


The script isn't scene-based. It's:
- process-based - checks that obs32.exe is running;
- IP-based - checks that obs32.exe is connected to the ip camera on the specified port;
- and hotkey-based - sends the hotkey to hide/show media when the IP connection is lost and then reestablished.

What needs to be changed to make two instances of the code work? I have one instance of it working perfectly. But when I try to open a second code for another camera it will not open. It will only let me run one code at a time.
 
Top