2021-04-13 20:06:16 +00:00
|
|
|
#!/usr/bin/env python3
|
|
|
|
import sys
|
|
|
|
|
|
|
|
oldexcepthook = sys.excepthook
|
|
|
|
def newexcepthook(type,value,traceback):
|
|
|
|
oldexcepthook(type,value,traceback)
|
|
|
|
input("Press ENTER to quit.")
|
|
|
|
sys.excepthook = newexcepthook
|
|
|
|
|
|
|
|
import os
|
|
|
|
p = os.path.join
|
|
|
|
pUp = os.path.dirname
|
|
|
|
s = False
|
|
|
|
if getattr(sys, 'frozen', False) and hasattr(sys, '_MEIPASS'):
|
|
|
|
s = os.path.realpath(sys.executable)
|
|
|
|
else:
|
|
|
|
s = os.path.realpath(__file__)
|
|
|
|
sp = pUp(s)
|
|
|
|
|
|
|
|
# script start
|
2021-04-13 18:33:16 +00:00
|
|
|
import threading
|
|
|
|
import queue
|
|
|
|
import socket
|
|
|
|
import subprocess
|
|
|
|
|
|
|
|
threads = {}
|
|
|
|
threadId = 0
|
|
|
|
threadsLock = threading.Lock()
|
|
|
|
|
|
|
|
serverAddr = ("127.0.0.1",12000)
|
|
|
|
serverSocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
|
|
|
|
|
|
|
|
bufferSize = 1000 # buffer size in bytes
|
|
|
|
|
|
|
|
proc = subprocess.Popen([
|
|
|
|
# binary
|
|
|
|
"ffmpeg",
|
|
|
|
# input: audio
|
|
|
|
"-f","dshow","-audio_buffer_size","10","-i","audio=virtual-audio-capturer",
|
|
|
|
# input: video
|
|
|
|
"-f","gdigrab","-framerate","30","-i","desktop","-vf","scale=-1:480",
|
|
|
|
# output-codec: video
|
|
|
|
"-c:v","libx264","-pix_fmt","yuv420p","-preset","fast","-tune","zerolatency",
|
|
|
|
# output-codec: audio
|
|
|
|
"-c:a","aac",
|
|
|
|
# output properties:
|
|
|
|
"-bufsize","2M","-maxrate","1M",
|
|
|
|
# output-file:
|
|
|
|
"-f","mpegts",
|
|
|
|
"-"
|
|
|
|
],stdout=subprocess.PIPE,stdin=subprocess.PIPE)
|
|
|
|
|
|
|
|
class outThread(threading.Thread):
|
|
|
|
def __init__(self,threadId,connection,address):
|
|
|
|
threading.Thread.__init__(self)
|
|
|
|
self.threadId = threadId
|
|
|
|
self.queue = queue.Queue()
|
|
|
|
self.connection = connection
|
|
|
|
self.address = address
|
|
|
|
self.connection.settimeout(15)
|
|
|
|
|
|
|
|
def run(self):
|
|
|
|
try:
|
|
|
|
while True:
|
|
|
|
data = self.queue.get()
|
|
|
|
self.connection.sendall(data)
|
|
|
|
except:
|
|
|
|
with threadsLock:
|
|
|
|
del threads[str(self.threadId)]
|
|
|
|
raise
|
|
|
|
|
|
|
|
class ffmpegThread(threading.Thread):
|
|
|
|
def __init__(self):
|
|
|
|
threading.Thread.__init__(self)
|
|
|
|
|
|
|
|
def run(self):
|
|
|
|
while proc.poll() is None:
|
|
|
|
data = proc.stdout.read(bufferSize)
|
|
|
|
with threadsLock:
|
|
|
|
for thread in threads:
|
|
|
|
thread = threads[thread]
|
|
|
|
thread.queue.put(data)
|
|
|
|
|
|
|
|
def main():
|
|
|
|
global threadId
|
2021-04-13 20:06:16 +00:00
|
|
|
serverSocket.bind(serverAddr)
|
|
|
|
serverSocket.listen(1024)
|
2021-04-13 18:33:16 +00:00
|
|
|
ffmpegThread().start()
|
2021-04-13 20:06:16 +00:00
|
|
|
|
2021-04-13 18:33:16 +00:00
|
|
|
while True:
|
|
|
|
connection, address = serverSocket.accept()
|
|
|
|
with threadsLock:
|
|
|
|
threadId += 1
|
|
|
|
while str(threadId) in threads:
|
|
|
|
threadId += 1
|
|
|
|
|
|
|
|
thread = outThread(threadId,connection,address)
|
|
|
|
threads[str(threadId)] = thread
|
|
|
|
thread.start()
|
|
|
|
|
2021-04-13 20:06:16 +00:00
|
|
|
if __name__ == '__main__':
|
|
|
|
main()
|