Home > Mobile >  Parallel Processing in merging two camera streams
Parallel Processing in merging two camera streams

Time:05-26

I need some help in speeding up the merging process from two camera sources. The merge_fn is like kind of a panorama generation function and it takes a very minimal time. The frame rate is reduced because I am reading the camera sources one by one and I need to speed up that process (like separate threads?).

how to parallelize that?

my code:

import numpy as np
import cv2

leftStream = cv2.VideoCapture(0)
rightStream = cv2.VideoCapture(1)

def merge_fn(left, right):
    pass

while True:
    _, left = leftStream.read()
    _, right = rightStream.read()
    merge = merge_fn(left, right)    
    cv2.imshow("Merge", merge)
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break
    
# Release the windows and the cameras
leftStream.release()
rightStream.release()
cv2.destroyAllWindows()

CodePudding user response:

Worked well for me.

from multiprocessing import Process, Pipe

import cv2
import numpy as np


def start_camera_1(chi_c, camera):
    cam = cv2.VideoCapture(camera)
    while True:
        ret, frame = cam.read()
        if ret:
            chi_c.send(frame)


def start_camera_2(chi_c, camera):
    cam = cv2.VideoCapture(camera)
    while True:
        ret, frame = cam.read()
        if ret:
            chi_c.send(frame)


def start_stream():
    par_c_1, chi_c_1 = Pipe()
    par_c_2, chi_c_2 = Pipe()
    process = Process(target=start_camera_1,
                      args=(chi_c_1, 0))
    process.start()

    process = Process(target=start_camera_2,
                      args=(chi_c_2, 1))
    process.start()

    while True:
        result_1 = par_c_1.recv()
        result_2 = par_c_2.recv()

        frame = np.hstack((result_1, result_2))
        
        frame = cv2.resize(frame, (1600, 900)) # resize according to your need
        cv2.imshow('frame', frame)
        if cv2.waitKey(1) & 0xFF == ord('q'):
            break
    cv2.destroyAllWindows()



if __name__ == '__main__':
    start_stream()

CodePudding user response:

Here's a threaded version that acquires from two separate cameras in two separate threads and then stacks the images side-by-side:

#!/usr/bin/env python3

import cv2
import time
import threading
import numpy as np

class VideoStream():
   """
   Class that acquires video frames continuously, as fast as possible on a 
   separate thread and makes them available to caller, via 'latestFrame()'
   method.
   """
   def __init__(self, width=1920, height=1080, stream=0):
      self.width  = width
      self.height = height
      self.stream = stream
      self.frame  = None
      self.thread = threading.Thread(target=self.acquireFrames, args=())
      self.thread.daemon = True
      self.thread.start()

   def acquireFrames(self):
      cap = cv2.VideoCapture(self.stream)
      if cap.isOpened():
         cap.set(cv2.CAP_PROP_FRAME_WIDTH,  self.width)
         cap.set(cv2.CAP_PROP_FRAME_HEIGHT, self.height)
         while True:
            ret, self.frame = cap.read()
            if not ret:
               print(f'ERROR: Stream: {stream}, error reading frame')

   def latestFrame(self):
      if not self.frame is None:
         return self.frame
      # Return blank frame if none available
      return np.zeros((self.height, self.width, 3), dtype=np.uint8)


def main():

   # Start streaming from two cameras
   Stream0 = VideoStream(stream=0)
   Stream1 = VideoStream(stream=1)

   frames = 0
   t0 = time.time()
   while True:
      # Grab latest frame from each camera
      frame0 = Stream0.latestFrame()
      frame1 = Stream1.latestFrame()

      # Stack frames side-by-side
      combined = np.hstack((frame0, frame1))
      cv2.imshow('Streams', combined)
      if cv2.waitKey(1) & 0xFF == ord('q'):
         break

      # Show frame rate in case anyone is interested
      frames  = 1
      if frames % 100 == 0:
         elapsed = time.time() - t0
         print(f'FPS: {int(frames/elapsed)}')
   
   cv2.destroyAllWindows()

if __name__ == '__main__':
   main()
  • Related