2016-07-28 18 views
0

Ich versuche, das Histogramm in Echtzeit von Graustufen meiner Webcam zu zeigen, das Problem ist, dass Histogramm nicht aktualisiert wird und meine Kamera stoppt, bis ich das Fenster des Histogramms schließe. Wie kann ich das beheben? Ich möchte die Graustufen-Img von meiner Webcam und deren Histogramm gleichzeitig anzeigen lassen, ist das möglich?Histogramm meiner Kamera in Echtzeit

import numpy as np 
import cv2 
from matplotlib import pyplot as plt 

cap = cv2.VideoCapture(0) 

while(True): 
    ret, frame = cap.read() 
    gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY) 
    cv2.imshow('Janela', frame) 
    cv2.imshow('Outra', gray) 
    plt.hist(gray.ravel(), 256, [0, 256]) 
    plt.show() 

    if (cv2.waitKey(1) & 0xFF == 27): 
     break 

cap.release() 
cv2.destroyAllWindows() 
+0

'plt.show()' öffnet ein Fenster, das im Gegensatz zu 'cv2.imshow' blockiert, was' cv2.waitkey' zum Blockieren benötigt. Es ist also die beste Option, das Histogramm mit einer anderen Funktion anzuzeigen. – B8vrede

Antwort

2

Ich habe für eine Weile in der gleichen Aufgabe gearbeitet. Nach einiger Zeit habe ich einen Code, der sehr gut funktioniert. Es zeigt das Kamerabild in einem Fenster und ein Histogramm in einem anderen Fenster an. Da ich an Farben interessiert bin, arbeite ich mit dem "Farbton" -Kanal jedes Rahmens.

# import the necessary packages 
import cv2 
import numpy as np 

#Create window to display image 
cv2.namedWindow('colorhist', cv2.CV_WINDOW_AUTOSIZE) 

#Set hist parameters 
hist_height = 64 
hist_width = 256 
nbins = 32 
bin_width = hist_width/nbins 

camera_id = 0 # type fo webcam [0 built-in | 1 external] 
cameraWidth = 320 
cameraHeight = 240 

if camera_id == 0: 
    cameraId = "PC webcam" 
elif camera_id == 1: 
    cameraId = "External webcam" 

camera = cv2.VideoCapture(camera_id) 

# set camera image to 320 x 240 pixels 
camera.set(3,cameraWidth) 
camera.set(4,cameraHeight) 

cameraInfo = "Image size (%d,%d)" % (camera.get(3),camera.get(4)) 

# initialize mask matrix 
mask = np.zeros((cameraHeight,cameraWidth), np.uint8) 

# draw a circle in mask matrix 
cv2.circle(mask,(cameraWidth/2,cameraHeight/2), 50, 255, -1) 

#Create an empty image for the histogram 
h = np.zeros((hist_height,hist_width)) 

#Create array for the bins 
bins = np.arange(nbins,dtype=np.int32).reshape(nbins,1) 

while True: 
    # grab the current frame 
    (grabbed, frame) = camera.read() 

    if not grabbed: 
     "Camera could not be started." 
     break 

    hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV) 
    #Calculate and normalise the histogram 
    hist_hue = cv2.calcHist([hsv],[0],mask,[nbins],[0,256]) 
    cv2.normalize(hist_hue,hist_hue,hist_height,cv2.NORM_MINMAX) 
    hist=np.int32(np.around(hist_hue)) 
    pts = np.column_stack((bins,hist)) 

    #Loop through each bin and plot the rectangle in white 
    for x,y in enumerate(hist): 
     cv2.rectangle(h,(x*bin_width,y),(x*bin_width + bin_width-1,hist_height),(255),-1) 

    #Flip upside down 
    h=np.flipud(h) 

    #Show the histogram 
    cv2.imshow('Color Histogram',h) 
    h = np.zeros((hist_height,hist_width)) 

    frame = cv2.bitwise_and(frame,frame,mask = mask) 
    cv2.putText(frame, cameraInfo, (10, 20), 
    cv2.FONT_HERSHEY_SIMPLEX, 0.5, (0, 0, 255), 2) 

    cv2.imshow(cameraId, frame)    
    key = cv2.waitKey(1) & 0xFF 

    # if the `q` key is pressed, break from the loop 
    if key == ord("q"): 
     break 

camera.release() 
cv2.destroyAllWindows() 

Der Code basiert auf dem Code von JohnLinux (How do I plot a 32-Bin Histogram for a Grayscale Image in Python using OpenCV) und anderen Code-Zeilen kamen von dem, was ich von Adrian Rosenbrock- Website https://www.pyimagesearch.com/ gelernt habe.

+0

Genau das habe ich versucht! Ich musste nur einige Variablen in int umwandeln, weil es einen Fehlertyp gab. '' cv2.circle (Maske, (cameraWidth/2, cameraHeight/2), 50, 255, -1) TypeError: Integer Argument erwartet, habe float'' –