I am unable to capture any frames from a webcam, as I always get the following error:
[ WARN:0@32.309] global cap_msmf.cpp:1759 CvCapture_MSMF::grabFrame videoio(MSMF): can't grab frame. Error: -2147483638
The camera opens OK, as the light next to the webcam turns on, and vid.isOpened() returns true.I have tried with a secondary external USB Webcam (Logitec) and I have the same behaviour. If I run it with the cv2.CAP_DSHOW
backend then the warning goes away, however the image is still no displayed. The camera works in other apps such as MS Teams, Google Meet, and the built-in camera app that comes with windows.
I have tried removing and re-adding OpenCV and it did not help. I also Tried compiling it from source and still no luck. I also tried the contrib build but this had no effect. I believe this maybe related to my hardware in some way, as I can run the same script on a colleagues laptop without issue. However both cameras I tried work with other apps, so I don't know what could be causing it to fail.
If I run it through the Python debugger (either with python -m pdb webcam.py
or through VS Code runner), then strangely it works. The first thing I checked was that there were not multiple versions installed and that the debugger wasn't calling one version rather than the other, but their appears to be no change. Its the same version of Python and the same version of OpenCV for both.
I found another person with exactly the same issue, but it doesn't appear to have been resolved: https://answers.opencv.org/question/220309/videocapture-from-camera-works-only-in-debug-python/
I have also tried it in C++ (OpenCV), and using a different library in Rust (Non-OpenCV), but neither were able to successfully capture a frame from the built-in webcam, or the external one.
Code to replicate the issue, nothing fancy going on:
# import the opencv library
import cv2
import sys
print(sys.version_info)
print("OPEN CV: ", cv2.__version__)
# define a video capture object
vid = cv2.VideoCapture(0)
# vid = cv2.VideoCapture(0, cv2.CAP_DSHOW)
cv2.namedWindow('Test Window', cv2.WINDOW_NORMAL)
print("Camera Opened: ", vid.isOpened())
while(True):
# Capture the video frame
ret, frame = vid.read()
if ret:
cv2.imshow('Test Window', frame)
else:
print("Error Drawing Frame")
if cv2.waitKey(1) & 0xFF == ord('q'):
break
# After the loop release the cap object
vid.release()
# Destroy all the windows
cv2.destroyAllWindows()
If I enable the OPENCV_VIDEOIO_DEBUG
enviroment variable ( Set-Item -Path Env:OPENCV_VIDEOIO_DEBUG -Value ($Env:OPENCV_VIDEOIO_DEBUG + ";1"
) Then it gives a different error, however this may be a red herring. I have posted it here for completeness:
Traceback (most recent call last):
File "C:\Users\user1\AppData\Local\Programs\Python\Python38\lib\site-packages\cv2\__init__.py", line 181, in <module>
bootstrap()
File "C:\Users\user1\AppData\Local\Programs\Python\Python38\lib\site-packages\cv2\__init__.py", line 153, in bootstrap
native_module = importlib.import_module("cv2")
File "C:\Users\user1\AppData\Local\Programs\Python\Python38\lib\importlib\__init__.py", line 127, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
ImportError: DLL load failed while importing cv2: A dynamic link library (DLL) initialization routine failed.
I Don't know which DLL is causing this issue though, and since I can get it to work if I run it in the debugger, this seems unrelated.
Usually this error occurred to me when some application like Antivirus interfering OpenCV, blocking it from accessing the camera. It might be the case that some antivirus software has tendency to block OpenCV when run in non debug mode. My current hypothesis is that in debug mode, the OpenCV libraries may be more transparent, which may not trigger the same behavior in your antivirus software.
You can temporarily try disabling antivirus and if it works you can add an exception for OpenCV in your antivirus software to prevent it from being blocked in the future.