Ho un setup in Python dove uso la libreria OpenCV per leggere i frame di un video come array 2D - questi video sono in scala di grigi, quindi sono utilizzando numeri interi a 8 bit senza segno per i valori dei pixel.Mostra array 2D da OpenCV in Matplotlib.pyplot.imshow()
Nel passaggio successivo, sto cercando di utilizzare pyplot.imshow()
da matplotlib per visualizzare la cornice del video. Sfortunatamente, sto ricevendo qualcosa che non ha alcun senso.
Ecco il codice per leggere il video:
import numpy as np
import cv
def read_video(filename):
video = cv.CaptureFromFile('%s' % filename)
num_frames = int(cv.GetCaptureProperty(video, cv.CV_CAP_PROP_FRAME_COUNT))
frames = []
for i in range(0, num_frames):
frame = cv.QueryFrame(video)
if frame is None:
quit('Failed to extract frame %s of %s!' % (i, num_frames))
toadd = cv2numpy(frame, 'uint8')
frames.append(np.array(toadd))
return np.array(frames)
cv2numpy
è una funzione di utilità che converte l'array OpenCV in una matrice NumPy (solo una chiamata al fromstring
e poi un reshape
). Ecco il codice che sto usando per tracciare il primo fotogramma del video:
import matplotlib.pyplot as plot
import matplotlib.cm as cm
frames = read_video('video.avi')
plot.imshow(frames[0], cmap = cm.gray)
plot.show()
In qualche altro codice, ho usato l'OpenCV SaveImage
su un singolo fotogramma per fornire un riferimento per quello che ci si aspetterebbe da imshow
. Here's the image I get from the former e here's the image I get from the code above.
Come potete vedere sono molto diversi. L'unica cosa che posso ricavare dall'immagine reale è lo striping: sembra quasi che abbia sbagliato le dimensioni, che ci siano più pixel nella larghezza dell'altezza (questa immagine dovrebbe essere 128 x 256). Ma ho provato a trasporre l'array prima di tracciarlo, modificando i parametri e come per lo imshow documentation e, con l'eccezione di alcuni strani strappi di pixel, non ho trovato una soluzione.
Qualche idea?
EDIT 1: Immagino può essere prudente per aggiungere il codice cv2numpy
, nel caso in cui rimodellamento è in qualche modo cavarsela cose (dal momento che la mia immagine "verità" di cui sopra non utilizzare quel codice e quindi cv2numpy
è coinvolto solo nella conduttura discutibile).
def cv2numpy(cvarr, the_type):
a = np.fromstring(
cvarr.tostring(),
dtype = the_type,
count = cvarr.width * cvarr.height)
a.shape = (cvarr.height, cvarr.width)
return a
Questo era esattamente il problema. OpenCV stava ancora leggendo i video come RGB, quindi ho aggiunto in 'cv.CreateImage' e' cv.CvtColor', ho stampato l'immagine e sembra esattamente come mi aspettavo. Grazie mille! Apparentemente la conversione degli array OpenCV in array numpy tramite stringhe non è ottimale. – Magsol