How to plot frame per seconds (fps) over time using matplotlib when processing a video?

Viewed 856

the below code calculates the number of processed frames per second for a video and display it on the output processed frame using opencv:

import cv2 as cv 
import numpy as np 
from collections import  deque

from imutils.video import FPS
# matplotlib.pyplot as plt
import datetime
from class22 import pre_processing

pts1 = deque(maxlen=40)
pts2 = deque(maxlen=40)

#ceate a capture object-------------------------------------------------------------------

cap=cv.VideoCapture(r'C:/Users/kjbaili/Documents/Masterarbeit/Praxis/Erste
_Videoeinsatz/Basler_acA 1920-40uc__22823716__20200724_145423423.mp4')

fps_start_time = datetime.datetime.now() #start timer
FPs= 0
total_frames = 0
#-------------------------------------------------------------------
ob1=pre_processing()
ob2=pre_processing()

fps = FPS().start() 

#start reading frames
while cap.isOpened:
 ret,frame=cap.read(())
 
 #----------------------------------------------------------------------------
 total_frames = total_frames + 1  #collect the total number of frames
 fps_end_time = datetime.datetime.now() #stop timer
 time_diff = fps_end_time - fps_start_time
 if time_diff.seconds == 0: 
     FBs = 0.0
 else:
  FBs = (total_frames / time_diff.seconds) #estimate the frame per second
 fps_text = "FPS: {:.2f}".format(FBs)
 cv.rectangle(frame, (10, 2), (100,20), (255,255,255), -1)
 cv.putText(frame, fps_text, (15, 15),cv.FONT_HERSHEY_SIMPLEX, 0.5 , (0,0,0))# display the fps 
 on the output image
 #----------------------------------------------------------------------------

However, I'm trying to plot the fps over time using matplotlib for better illustration, so that the plot would look like the following:

plot_example_fps

So can anyone tells me how can i plot the data shown in the above code using e.g matplotlib as it doesn't seem to be easy since the number of frames changes as time elapses.

Thanks in advance

1 Answers

Since you are allowed to show the plot after the processing has ended, the best way to accomplish this is to have two lists defined where one computes the time elapsed and the other stores the FPS at each point in time. These get updated in your frame loop then we can use matplotlib to show the information afterwards:

## New - lists for storing our information
time_list = []
fps_list = []


#start reading frames
while cap.isOpened:
    ret,frame=cap.read(())

    #----------------------------------------------------------------------------
    total_frames = total_frames + 1  #collect the total number of frames
    fps_end_time = datetime.datetime.now() #stop timer
    time_diff = fps_end_time - fps_start_time
    if time_diff.seconds == 0: 
       FBs = 0.0
    else:
       FBs = (total_frames / time_diff.seconds) #estimate the frame per second
    fps_text = "FPS: {:.2f}".format(FBs)
    cv.rectangle(frame, (10, 2), (100,20), (255,255,255), -1)
    cv.putText(frame, fps_text, (15, 15),cv.FONT_HERSHEY_SIMPLEX, 0.5 , (0,0,0))# display the fps 
 on the output image
    #----------------------------------------------------------------------------

    ## New - Update our lists
    time_list.append(time_diff.seconds)
    fps_list.append(FBs)

import matplotlib.pyplot as plt
plt.figure()
plt.plot(time_list, fps_list)
plt.xlabel('Time (s)')
plt.ylabel('FPS')
plt.show()

I've used the code you have made available at the end which does the actual frame processing. However, I've declared the aforementioned lists too. Once we calculate the time elapsed, we append this to the list and the corresponding estimated FPS. After the processing loop has finished, we use matplotlib to show a plot with time on the horizontal axis and FPS on the vertical axis.

Related