Source code for pftracker.modules.interfacingUI

"""
particle_tracker class interfaces all the algorithms and parameters
in the particle filter framework.

@author: Bessie Domínguez-Dáger
"""

import cv2
from imutils.video import VideoStream
import time

from pftracker.modules.models import FaceTracking_2D
from pftracker.modules.models import createMovModel

from pftracker.modules.models import ObsMod
from pftracker.modules.models.colorhist.HSVModel import hsvModel
from pftracker.modules.models.lbp.LBPModel import lbpModel

from pftracker.modules.runFilter import RunFilter
   

[docs]class ParticleTracker(): """Class interfaces particle filter to handle face tracking problem. This class interfaces particle filter algorithms to work in the face tracking in video sequences task. Video sequences can be recorded from computer's webcam or .mp4 or .avi files loaded from disk. Args: video(str, optional): Path to the input video file (.mp4 or .avi format). Default is the reference to the webcam algorithm(str): Particle filter algorithm n_particles(int): Number of particles detector(str): Face detector algorithm estimate(str): Estimate method resample(str): Resampling method resamplePercent(int): Resampling percent robustPercent(int): Resampling percent obsmodel(str): Observation model stateSpace(str): State space model Supported PF algorithms: - 'SIS': Sequential Importance Sampling filter - 'SIR': Sequential Importance Resampling filter - 'G_PF': Generic particle filter - 'APF': Auxilliary particle filter Supported Face detectors: - 'HaarCascade': Viola and Jones (V&J) detector - 'CaffeModel': Single Shot Detector (SSD) - 'dlib': Histogram of Oriented Gradient (HOG) Supported estimate methods: - 'weighted_mean': Weighted mean method - 'MAP': Maximum weight method - 'robust_mean': Robust mean method Supported resampling methods: - 'systematic': Systematic resampling - 'stratified': Stratified resampling - 'residual': Residual resampling - 'multinomial': Multinomial resampling Supported observation models: - 'HSV color-based': Color model for weighing the particles - 'LBP-based': Texture model for weighing the particles Supported state space models: - 'dynamic_bbox': Self updating bounding box model - '5_variables': Five variables state space model - '6_variables': Six variables state space model """ def __init__(self, video, algorithm, n_particles, detector, estimate, resample, resamplePercent, robustPercent, obsmodel, stateSpace): self.video = video self.algorithm = algorithm self.n_particles = n_particles self.obsmodel = obsmodel self.detector = detector self.estimate = estimate self.resample = resample self.resamplePercent = resamplePercent self.robustPercent = robustPercent self.stateSpace = stateSpace if self.resample == "Systematic": self.resample = "systematic" elif self.resample == "Stratified": self.resample = "stratified" elif self.resample == "Residual": self.resample = "residual" elif self.resample == "Multinomial": self.resample = "multinomial" if self.estimate == "Weighted mean": self.estimate = "weighted_mean" elif self.estimate == "Maximum weight": self.estimate = "MAP" elif self.estimate == "Robust mean": self.estimate = "robust_mean" if self.detector == "Viola and Jones (V&J)": self.detector = "HaarCascade" elif self.detector == "Single Shot Detector (SSD)": self.detector = "CaffeModel" elif self.detector == "Histogram of Oriented Gradient (HOG)": self.detector = "dlib" elif self.detector == "Non-Max Suppression": self.detector = "nms" if self.stateSpace == "[x, y, Vx, Vy] (dynamic bbox)": self.stateSpace = "dynamic_bbox" elif self.stateSpace == "[x, y, Vx, Vy, w]": self.stateSpace = "5_variables" elif self.stateSpace == "[x, y, Vx, Vy, w, Vw]": self.stateSpace = "6_variables"
[docs] def face_tracking(self, saveVideo): """ Run the especified particle filter algorithm for face tracking. Args: saveVideo(str): Path to the output video file. None means do not save video Returns: 2-element tuple containing - **t_elapsed** (*float*): Approximate execution time of the algorithm in the face tracking task. - **fps** (*float*): Approximate number of fps. Raises: AssertionError: Exception raised if the reference to the webcam failed. AssertionError: Exception raised if the reference to the input video failed. """ # If a video path was not supplied, grab the reference to the webcam if not self.video: print("[INFO] starting video stream...") v = VideoStream(src=0).start() # Otherwise, grab a reference to the video file else: v = cv2.VideoCapture(self.video) # Allow the camera or video file to warm up time.sleep(2.0) # Read first frame frame = v.read() # If the first frame couldn´t be read raise an error to explain it # webcam reference webcam_error = not(frame is None and self.video is None) assert webcam_error, "The reference to the webcam has failed." # If the first frame couldn´t be read raise an error to explain it # video file reference video_file_error = not(frame[1] is None and self.video is not None) error_text = ("Incorrect path to the input video file.\n" + "\t\t\t\tFile " + str(self.video) + " can't be open. " "No such file or directory") assert video_file_error, error_text # Handle the frame from VideoCapture or VideoStream, # vide_stream bool variable indicate if we're working # with VideoCapture or VideoStream frame, video_stream = (frame[1], False) if self.video else (frame, True) ## Initializations # Particle motion model: discrete gaussian linear model; # size_ve: state vector size movModel, size_ve = createMovModel(self.stateSpace) # Observation model initialization --------------------------- if self.obsmodel == "HSV color-based": # Observation model: HSV histogram obsModel = ObsMod(hsvModel, self.n_particles) elif self.obsmodel == "LBP-based": # Observation model: LBP histogram obsModel = ObsMod(lbpModel, self.n_particles) #------------------------------------------------------------- # 2D-Face model faceModel = FaceTracking_2D(movModel, obsModel, self.n_particles, size_ve, frame, self.detector, v, video_stream, saveVideo) # Initialize run_filter class self.run = RunFilter(faceModel, self.algorithm, self.n_particles, self.estimate, self.resample, self.resamplePercent, self.robustPercent) # Run the particle filter algorithm t_elapsed, fps, video_closed = self.run.tracking() print("[INFO] elapsed time: {:.2f} sec".format(t_elapsed)) print("[INFO] approx. FPS: {:.2f}".format(fps)) # If we are not using a video file, stop the camera video stream if video_stream: v.stop() # Otherwise, release the camera else: v.release() # Close all windows cv2.destroyAllWindows() return t_elapsed, fps, video_closed
[docs] def save_estimation(self, file_name): """ Save the particle estimation for each frame into a .txt file Args: file_name(str): path to output .txt file """ self.run.save_estimate(file_name)
[docs] def eval_pf(self, gt): """ Evaluate particle filter algorithm results. This function calculate precision and recall metrics for the resulting tracking. Args: gt(str): path to ground truth .txt file Returns: 8-element tuple containing - **P** (*array*): precision value per frame, array with (1, number_of_frames) dimension - **R** (*array*): recall value per frame, array with (1, number_of_frames) dimension - **P_mean** (*float*): precision mean value - **R_mean** (*float*): recall mean value - **P_std** (*float*): precision standard deviation value - **R_std** (*float*): recall standard deviation value - **F1Score** (*float*): F-1-score metric """ return self.run.eval_alg(gt)
def get_pf_est(self): return self.run.get_pf_estimation()