Увеличение разрешения камеры в OpenCV
в моей программе C / C++, я использую OpenCV для захвата изображения с веб-камеры. Камера (Logitech QuickCam IM) можно захватить в разрешениях 320x240,640x480 и 1280x960. Но, по какой-то странной причине, OpenCV дает мне изображения с разрешением 320x240 только. Вызовы для изменения разрешения с помощью cvSetCaptureProperty () с другими значениями разрешения просто не работают. Как я могу захватить изображения с другими разрешениями, возможными с моей веб-камерой?
15 ответов:
Я использую openCV 1.1pre1 под Windows (библиотека videoinput используется по умолчанию этой версией openCv под windows).
С помощью этих инструкций я могу установить разрешение камеры. Обратите внимание, что я называю старый cvCreateCameraCapture вместо cvCaptureFromCam.
capture = cvCreateCameraCapture(cameraIndex); cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_WIDTH, 640 ); cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_HEIGHT, 480 ); videoFrame = cvQueryFrame(capture);Я тестировал его с веб-камерами Logitech, Trust и Philips
там, кажется, нет решения. Разрешение может быть увеличено до 640x480 используя этот хак общий lifebelt77. Вот воспроизводимые детали:
добавить highgui.h:
#define CV_CAP_PROP_DIALOG_DISPLAY 8 #define CV_CAP_PROP_DIALOG_FORMAT 9 #define CV_CAP_PROP_DIALOG_SOURCE 10 #define CV_CAP_PROP_DIALOG_COMPRESSION 11 #define CV_CAP_PROP_FRAME_WIDTH_HEIGHT 12добавить функцию icvSetPropertyCAM_VFW до cvcap.cpp:
static int icvSetPropertyCAM_VFW( CvCaptureCAM_VFW* capture, int property_id, double value ) { int result = -1; CAPSTATUS capstat; CAPTUREPARMS capparam; BITMAPINFO btmp; switch( property_id ) { case CV_CAP_PROP_DIALOG_DISPLAY: result = capDlgVideoDisplay(capture->capWnd); //SendMessage(capture->capWnd,WM_CAP_DLG_VIDEODISPLAY,0,0); break; case CV_CAP_PROP_DIALOG_FORMAT: result = capDlgVideoFormat(capture->capWnd); //SendMessage(capture->capWnd,WM_CAP_DLG_VIDEOFORMAT,0,0); break; case CV_CAP_PROP_DIALOG_SOURCE: result = capDlgVideoSource(capture->capWnd); //SendMessage(capture->capWnd,WM_CAP_DLG_VIDEOSOURCE,0,0); break; case CV_CAP_PROP_DIALOG_COMPRESSION: result = capDlgVideoCompression(capture->capWnd); break; case CV_CAP_PROP_FRAME_WIDTH_HEIGHT: capGetVideoFormat(capture->capWnd, &btmp, sizeof(BITMAPINFO)); btmp.bmiHeader.biWidth = floor(value/1000); btmp.bmiHeader.biHeight = value-floor(value/1000)*1000; btmp.bmiHeader.biSizeImage = btmp.bmiHeader.biHeight * btmp.bmiHeader.biWidth * btmp.bmiHeader.biPlanes * btmp.bmiHeader.biBitCount / 8; capSetVideoFormat(capture->capWnd, &btmp, sizeof(BITMAPINFO)); break; default: break; } return result; }редактировать captureCAM_VFW_vtable следующим образом:
static CvCaptureVTable captureCAM_VFW_vtable = { 6, (CvCaptureCloseFunc)icvCloseCAM_VFW, (CvCaptureGrabFrameFunc)icvGrabFrameCAM_VFW, (CvCaptureRetrieveFrameFunc)icvRetrieveFrameCAM_VFW, (CvCaptureGetPropertyFunc)icvGetPropertyCAM_VFW, (CvCaptureSetPropertyFunc)icvSetPropertyCAM_VFW, // was NULL (CvCaptureGetDescriptionFunc)0 };Теперь перестроил highgui.dll.
Я делал обработку изображений в linux раньше и пропустил встроенную функциональность камеры OpenCV, потому что она (как вы обнаружили) неполная.
в зависимости от вашей ОС вы можете иметь больше удачи, идя прямо к оборудованию через обычные каналы, а не через openCV. Если вы используете Linux, video4linux или video4linux2 должны дать вам относительно тривиальный доступ к веб-камерам USB, и вы можете использовать libavc1394 для firewire. В зависимости от устройства и качества пример кода Вы следуете, вы должны быть в состоянии получить устройство работает с параметрами, которые вы хотите в течение часа или двух.
отредактировано, чтобы добавить: Вы сами по себе, если его окна. Я думаю, что это не намного сложнее, но я никогда не делал этого.
Я настоятельно рекомендую использовать VideoInput lib, Он поддерживает любое устройство DirectShow (даже несколько устройств одновременно) и более настраивается. Вы потратите пять минут, чтобы заставить его играть с OpenCV.
проверьте этот билет: https://code.ros.org/trac/opencv/ticket/376
"решение заключается в использовании более новой оболочки на основе libv4l.
установить libv4l-dev (так это называется в Ubuntu)
повторите cmake, вы увидите "V4L/ V4L2: Using libv4l"
повтор сделать. теперь разрешение может быть изменено. протестировано со встроенным isight на MBP."
этот исправлено это для меня с помощью Ubuntu и может также работать для вас.
код я, наконец, получил работу в Python, как только Аарон Хаун указал, что мне нужно определить аргументы функции set перед их использованием.
#Camera_Get_Set.py #By Forrest L. Erickson of VRX Company Inc. 8-31-12. #Opens the camera and reads and reports the settings. #Then tries to set for higher resolution. #Workes with Logitech C525 for resolutions 960 by 720 and 1600 by 896 import cv2.cv as cv import numpy CV_CAP_PROP_POS_MSEC = 0 CV_CAP_PROP_POS_FRAMES = 1 CV_CAP_PROP_POS_AVI_RATIO = 2 CV_CAP_PROP_FRAME_WIDTH = 3 CV_CAP_PROP_FRAME_HEIGHT = 4 CV_CAP_PROP_FPS = 5 CV_CAP_PROP_POS_FOURCC = 6 CV_CAP_PROP_POS_FRAME_COUNT = 7 CV_CAP_PROP_BRIGHTNESS = 8 CV_CAP_PROP_CONTRAST = 9 CV_CAP_PROP_SATURATION = 10 CV_CAP_PROP_HUE = 11 CV_CAPTURE_PROPERTIES = tuple({ CV_CAP_PROP_POS_MSEC, CV_CAP_PROP_POS_FRAMES, CV_CAP_PROP_POS_AVI_RATIO, CV_CAP_PROP_FRAME_WIDTH, CV_CAP_PROP_FRAME_HEIGHT, CV_CAP_PROP_FPS, CV_CAP_PROP_POS_FOURCC, CV_CAP_PROP_POS_FRAME_COUNT, CV_CAP_PROP_BRIGHTNESS, CV_CAP_PROP_CONTRAST, CV_CAP_PROP_SATURATION, CV_CAP_PROP_HUE}) CV_CAPTURE_PROPERTIES_NAMES = [ "CV_CAP_PROP_POS_MSEC", "CV_CAP_PROP_POS_FRAMES", "CV_CAP_PROP_POS_AVI_RATIO", "CV_CAP_PROP_FRAME_WIDTH", "CV_CAP_PROP_FRAME_HEIGHT", "CV_CAP_PROP_FPS", "CV_CAP_PROP_POS_FOURCC", "CV_CAP_PROP_POS_FRAME_COUNT", "CV_CAP_PROP_BRIGHTNESS", "CV_CAP_PROP_CONTRAST", "CV_CAP_PROP_SATURATION", "CV_CAP_PROP_HUE"] capture = cv.CaptureFromCAM(0) print ("\nCamera properties before query of frame.") for i in range(len(CV_CAPTURE_PROPERTIES_NAMES)): # camera_valeus =[CV_CAPTURE_PROPERTIES_NAMES, foo] foo = cv.GetCaptureProperty(capture, CV_CAPTURE_PROPERTIES[i]) camera_values =[CV_CAPTURE_PROPERTIES_NAMES[i], foo] # print str(camera_values) print str(CV_CAPTURE_PROPERTIES_NAMES[i]) + ": " + str(foo) print ("\nOpen a window for display of image") cv.NamedWindow("Camera", 1) while True: img = cv.QueryFrame(capture) cv.ShowImage("Camera", img) if cv.WaitKey(10) == 27: break cv.DestroyWindow("Camera") #cv.SetCaptureProperty(capture, CV_CAP_PROP_FRAME_WIDTH, 1024) #cv.SetCaptureProperty(capture, CV_CAP_PROP_FRAME_HEIGHT, 768) cv.SetCaptureProperty(capture, CV_CAP_PROP_FRAME_WIDTH, 1600) cv.SetCaptureProperty(capture, CV_CAP_PROP_FRAME_HEIGHT, 896) print ("\nCamera properties after query and display of frame.") for i in range(len(CV_CAPTURE_PROPERTIES_NAMES)): # camera_valeus =[CV_CAPTURE_PROPERTIES_NAMES, foo] foo = cv.GetCaptureProperty(capture, CV_CAPTURE_PROPERTIES[i]) camera_values =[CV_CAPTURE_PROPERTIES_NAMES[i], foo] # print str(camera_values) print str(CV_CAPTURE_PROPERTIES_NAMES[i]) + ": " + str(foo) print ("/nOpen a window for display of image") cv.NamedWindow("Camera", 1) while True: img = cv.QueryFrame(capture) cv.ShowImage("Camera", img) if cv.WaitKey(10) == 27: break cv.DestroyWindow("Camera")
Я использую debian и ubuntu, у меня была та же проблема, я не мог изменить разрешение видеовхода с помощью CV_CAP_PROP_FRAME_WIDTH и CV_CAP_PROP_FRAME_HEIGHT
оказалось, что причиной была пропажа библиотеки. Я установил lib4l-dev через синаптик, восстановлен OpenCV и проблема решена!
Я публикую это, чтобы убедиться, что никто больше не тратит время на эту функцию setproperty. Я потратил 2 дня на это, чтобы увидеть, что ничего, кажется, работает. Поэтому я откопал код (я установил библиотеку в первый раз). Это то, что на самом деле происходит - cvSetCaptureProperty, вызывает setProperty внутри класса CvCapture и вот setProperty ничего не делает. Он просто возвращает false. Вместо этого я возьму с помощью другой библиотеки для подачи OpenCV видео/изображений захвата. Я использую OpenCV 2.2
cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_WIDTH, WIDTH );
cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_HEIGHT, HEIGHT);
cvQueryFrame (capture);
Это не будет работать с OpenCV 2.2, но если вы используете OpenCV 2.1 он будет работать нормально !
Если вы находитесь на платформе windows, попробуйте DirectShow (IAMStreamConfig).
http://msdn.microsoft.com/en-us/library/dd319784%28v=vs.85%29.aspx
под Windows попробуйте использовать библиотеку VideoInput: http://robocraft.ru/blog/computervision/420.html
Я считаю, что в Windows (от Win98 до WinXP SP3) OpenCV часто использует библиотеку VFW Microsoft для доступа к камере. Проблема в том, что это часто очень медленно (скажем, максимум 15 кадров в секунду захвата кадра) и багги (следовательно, почему cvSetCaptureProperty часто не работает). К счастью, вы обычно можете изменить разрешение в другом программном обеспечении (в частности, "AMCAP", который является демонстрационной программой, которая легко доступна), и это повлияет на разрешение, которое будет использовать OpenCV. Например, вы можете запустить AMCAP, чтобы установить разрешение 640x480, а затем OpenCV будет использовать это по умолчанию с этого момента и далее!
но если вы можете использовать другую библиотеку доступа к камере Windows, такую как библиотека "videoInput"http://muonics.net/school/spring05/videoInput/ который обращается к камере с помощью очень эффективного DirectShow (часть DirectX). Или если у вас есть профессиональная качественная камера, то часто она будет поставляться с пользовательским API, который позволяет вам получить доступ к камере, и вы можете использовать что для быстрого доступа с возможностью изменения разрешения и многое другое.
только одна информация, которая может быть ценной для людей, испытывающих трудности с изменением разрешения захвата по умолчанию (640 x 480) ! Я сам экспериментировал с такой проблемой с opencv 2.4.x и одна камера Logitech ... и нашел один обходной путь !
поведение, которое я обнаружил, заключается в том, что формат по умолчанию настраивается как начальные параметры при запуске захвата камеры (cvCreateCameraCapture), и все запросы на изменение высоты или ширины :
cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_WIDTH, ...или
cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_HEIGHT, ...невозможно после этого ! Фактически, я обнаружил с добавлением ошибки возврата функций ioctl, что драйвер V4l2 возвращает EBUSY для этих запросов ! Поэтому одним из обходных путей должно быть изменение значения по умолчанию непосредственно в highgui/cap_v4l.cpp :
*#define DEFAULT_V4L_WIDTH 1280 // Originally 640* *#define DEFAULT_V4L_HEIGHT 720 // Originally 480*после этого, я просто пересобрал opencv ... и прибыл, чтобы получить 1280 х 720 без каких-либо проблем ! Конечно, лучше исправить должно быть, чтобы остановить приобретение, изменить параметры и перезапустить поток после этого, но я недостаточно знаком с opencv для этого !
надеюсь, что это поможет.
Мишель BEGEY
попробуйте это:
capture = cvCreateCameraCapture(-1); //set resolution cvSetCaptureProperty(capture, CV_CAP_PROP_FRAME_WIDTH, frameWidth); cvSetCaptureProperty(capture, CV_CAP_PROP_FRAME_HEIGHT, frameHeight);
cvQueryFrame(capture); cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_WIDTH, any_supported_size ); cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_HEIGHT, any_supported_size); cvQueryFrame(capture);должно быть достаточно!
Comments