I need a python script that live stream cam and I wanna grayscale the stream using keyboard, but I can't, every time I run the blow code stream change to grayscale but after a second it return to normal, please help me to fix this
import cv2
cap = cv2.VideoCapture(0)
while True:
ret, frame = cap.read()
gray=cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
c = cv2.waitKey(1)
if c & 0xFF == ord('q'):
break
elif c & 0xFF == ord('3'):
frame=gray
cv2.imshow('a',frame)
cap.release()
cv2.destroyAllWindows()
I need to change it using keyboard
Your problem is with the keyboard capture. The code waits for a keyboard input every iteration of the loop, if it gets none then none is passed to the code i.e. it doesnt remember what you typed last time so your elif is not entered the next time around.
Try the following to see what is happening...
import cv2
cap = cv2.VideoCapture(0)
gray_flag = False
while True:
ret, frame = cap.read()
gray=cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
c = cv2.waitKey(1) # only waits for 1 millisecond!!!
if c & 0xFF == ord('q'):
break
elif c & 0xFF == ord('3'):
gray_flag = True
elif c & 0xFF == ord('4'):
gray_flag = False
if gray_flag:
cv2.imshow('a', gray)
else:
cv2.imshow('a', frame)
cap.release()
cv2.destroyAllWindows()
The gray_flag ensures that your choice is remembered
Related
I'm using the below code to capture images from webcam. But i need only some no.of images to be captured on click.
# Opens the inbuilt camera of laptop to capture video.
cap = cv2.VideoCapture(0)
i = 0
while(cap.isOpened()):
ret, frame = cap.read()
# This condition prevents from infinite looping
# incase video ends.
if ret == False:
break
# Save Frame by Frame into disk using imwrite method
cv2.imwrite('Frame'+str(i)+'.jpg', frame)
i += 1
cap.release()
cv2.destroyAllWindows()```
Assuming you want 500 images add this:
...
i+=1
if (i+1)%500==0:
break
that would be easy. you can use k = cv2.waitKey(1) and check what button was pressed. here is a simple example:
import cv2
def main():
cap = cv2.VideoCapture(0)
if not cap.isOpened(): # Check if the web cam is opened correctly
print("failed to open cam")
return -1
else:
print('webcam open')
for i in range(10 ** 10):
success, cv_frame = cap.read()
if not success:
print('failed to capture frame on iter {}'.format(i))
break
cv2.imshow('click t to save image and q to finish', cv_frame)
k = cv2.waitKey(1)
if k == ord('q'):
print('q was pressed - finishing...')
break
elif k == ord('t'):
print('t was pressed - saving image {}...'.format(i))
image_path = 'Frame_{}.jpg'.format(i) # i recommend a folder and not to save locally to avoid the mess
cv2.imwrite(image_path, cv_frame)
cap.release()
cv2.destroyAllWindows()
return
if __name__ == '__main__':
main()
I'm trying to run a visual behaviour experiment where a whole heap of videos in a folder play one after another. I need to do this in python because I have a TTL pulse generator which I need to run at the start and end of each video.
I'm using cv2 and to try and play the videos but for reasons I can't figure out, I can't get them to play sequentially
Attached is my code
import cv2
import os
import random
videofolderPath = '/folderwithfiles'
videos = []
playlist = []
for file in os.listdir(videofolderPath):
if file.lower().endswith(".mp4"):
path=os.path.join('/folderwithfiles/',file)
playlist.append(path)
random.shuffle(playlist)
for i in range (3):
i += 1
cap = cv2.VideoCapture(playlist[i])
print(playlist[i])
while(True):
ret, frame = cap.read()
cv2.imshow('frame',frame)
if cv2.waitKey(1) & 0xFF == ord('q') or ret==False :
cap.release()
cv2.destroyAllWindows()
break
cv2.imshow('frame',frame)
cap.release()
cv2.destroyAllWindows()
The issue I'm having is I think they're all playing at once. When I press q I do see another video behind it but am struggling to get them to play one after another.
It looks like you have an error because you try to show the video before testing if ret == False.
Also, you should update i at the end of the loop as python indexing is zero based
The fix would look like this: (note that I changed the video folder path to test your code)
import cv2
import os
import random
videofolderPath = './videos'
videos = []
playlist = []
for file in os.listdir(videofolderPath):
if file.lower().endswith(".mp4"):
path = os.path.join(videofolderPath, file)
playlist.append(path)
random.shuffle(playlist)
for i in range(3):
cap = cv2.VideoCapture(playlist[i])
print(playlist[i])
while True:
ret, frame = cap.read()
# REMOVE cv2.imshow(f'frame_{i}', frame)
if cv2.waitKey(1) & 0xFF == ord('q') or ret == False:
cap.release()
cv2.destroyAllWindows()
break
cv2.imshow('frame', frame)
cap.release()
cv2.destroyAllWindows()
i += 1 # UPDATE INDEX AT THE END
A better way of writing your code would be something like this:
import cv2
import os
if __name__ == '__main__':
video_folder = "./videos"
for video_name in os.listdir(video_folder):
if not video_name.endswith(".mp4"):
continue
video_path = os.path.join(video_folder, video_name)
video = cv2.VideoCapture(video_path)
while True:
ret, frame = video.read()
if not ret:
break
cv2.imshow("video", frame)
cv2.waitKey(1)
video.release()
cv2.destroyAllWindows()
Also, I would recommend you to look at threading to load your video in "parallel" as it is very cpu intensive
I want to capture frame from my camera when the specific event occurs
my code
import cv2
cap = cv2.VideoCapture("http://192.168.43.1:8080/video")
if int(data) < 45:
return_value, image = cap.read()
cv2.imwrite('Images/'+str(count)+'.png', image)
print("capture")
But its saving older frames when it capture please help i want current frame to be saved
You need to read the frames as they arrive otherwise they just buffer up. You discard the frames you don't want. The following should demonstrate this:
import cv2
cap = cv2.VideoCapture("http://192.168.43.1:8080/video")
while True:
return_value, image = cap.read()
k = cv2.waitKey(10) & 0xFF
if int(data) < 45:
cv2.imwrite('Images/'+str(count)+'.png', image)
print("capture")
if k == ord('q'):
break
am looking devolop something simply with opencv.Am looking to play videos from the web using opencv the way you can play videos from your laptop by passing the location path now a trying to pass the video url and get it to play.so far am getting error any suggestion would be nice.
import cv2
import numpy as np
import urllib3
http = urllib3.PoolManager()
r = http.request('Get','https://www.youtube.com/watch?v=NWdrO4BoCu8&list=RDNWdrO4BoCu8&start_radio=1')
cap = cv2.VideoCapture('https://www.youtube.com/watch?v=NWdrO4BoCu8&list=RDNWdrO4BoCu8&start_radio=1')
if (cap.isOpened()== False):
print("Error opening video file")
while(cap.isOpened()):
ret, frame = cap.read()
if ret == True:
cv2.imshow('Frame', frame)
if cv2.waitKey(25) & 0xFF == ord('q'):
break
else:
break
cap.release()
cv2.destroyAllWindows()
Here you can use pafy to download the video, then use OpenCV to play the video.
url = 'https://youtu.be/W1yKqFZ34y4'
vPafy = pafy.new(url)
play = vPafy.getbest(preftype="webm")
#start the video
cap = cv2.VideoCapture(play.url)
while (True):
ret,frame = cap.read()
"""
your code here
"""
cv2.imshow('frame',frame)
if cv2.waitKey(20) & 0xFF == ord('q'):
break
cap.release()
cv2.destroyAllWindows()
resources for installation:
https://pypi.org/project/pafy/
I'm trying to close a video when it ends by clicking two keys (n and p) using OpenCV (Python).
However, I can't understand why it doesn't work by adding the specific line to the end of the loop.
In fact, using this specific code:
import cv2
import numpy as np
# Create a VideoCapture object and read from input file
cap = cv2.VideoCapture('randomvideo.mpg')
# Check if video opened successfully
if (cap.isOpened()== False):
print("Error opening file")
# Read until video is completed
while(cap.isOpened()):
# Capture frame-by-frame
ret, frame = cap.read()
if ret == True:
# Display the resulting frame
cv2.imshow('Frame',frame)
cv2.waitKey(25)
I can lock the video at the end of its playback, but by adding this:
# Break the loop
else:
if 0xFF == (ord('n')) or 0xFF == (ord('p')):
break
I'm not able to close it by pressing the two keys.
Any suggestions?
P.S. Is there also a way to record which key has been pressed?
Thank you in advance
You can record which key is pressed by checking the return value from cv2.waitKey(). From the documentation:
It returns the code of the pressed key or -1 if no key was pressed before the specified time had elapsed.
So you can check if n or p is pressed like this
key = cv2.waitKey(25)
if key == ord('n') or key == ord('p'):
break
Here's a working version of your code
import cv2
cap = cv2.VideoCapture('randomvideo.mpg')
if not cap.isOpened():
print("Error opening file")
while(cap.isOpened()):
ret, frame = cap.read()
if ret:
cv2.imshow('frame',frame)
key = cv2.waitKey(25)
if key == ord('n') or key == ord('p'):
break