From 4c7f56263e450329267f38c44f4106e21b425947 Mon Sep 17 00:00:00 2001 From: Olivier Le Doeuff Date: Fri, 29 Jan 2021 11:18:09 +0100 Subject: [PATCH] Merge pull request #19370 from OlivierLDff:patch-dshow-convertrgb MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit VideoCapture/DSHOW : Allow to set CAP_PROP_CONVERT_RGB before FOURCC/FPS/CHANNEL/WIDTH/HEIGHT. * 🐛 cap_dshow : Allow to set CAP_PROP_CONVERT_RGB before FOURCC/FPS/CHANNEL * 🐛 cap_dshow : fix g_VI.setConvertRGB not being called with correct boolean value on first property set. * ✅ cap_dshow : Test CAP_PROP_CONVERT_RGB persistence * 🚨 Fix cast from bool to double * 🚨 Fix trailing whitespace --- modules/videoio/src/cap_dshow.cpp | 11 ++++++++++- modules/videoio/src/cap_dshow.hpp | 1 + modules/videoio/test/test_camera.cpp | 21 +++++++++++++++++++++ 3 files changed, 32 insertions(+), 1 deletion(-) diff --git a/modules/videoio/src/cap_dshow.cpp b/modules/videoio/src/cap_dshow.cpp index 3909c60f88..0c92217be7 100644 --- a/modules/videoio/src/cap_dshow.cpp +++ b/modules/videoio/src/cap_dshow.cpp @@ -3341,6 +3341,7 @@ VideoCapture_DShow::VideoCapture_DShow(int index) , m_fourcc(-1) , m_widthSet(-1) , m_heightSet(-1) + , m_convertRGBSet(true) { CoInitialize(0); open(index); @@ -3450,6 +3451,7 @@ bool VideoCapture_DShow::setProperty(int propIdx, double propVal) break; g_VI.stopDevice(m_index); g_VI.setupDevice(m_index, cvFloor(propVal)); + g_VI.setConvertRGB(m_index, m_convertRGBSet); break; case CV_CAP_PROP_FPS: @@ -3463,6 +3465,7 @@ bool VideoCapture_DShow::setProperty(int propIdx, double propVal) g_VI.setupDevice(m_index, m_widthSet, m_heightSet); else g_VI.setupDevice(m_index); + g_VI.setConvertRGB(m_index, m_convertRGBSet); } return g_VI.isDeviceSetup(m_index); } @@ -3481,7 +3484,11 @@ bool VideoCapture_DShow::setProperty(int propIdx, double propVal) case CV_CAP_PROP_CONVERT_RGB: { - return g_VI.setConvertRGB(m_index, cvRound(propVal) == 1); + const bool convertRgb = cvRound(propVal) == 1; + const bool success = g_VI.setConvertRGB(m_index, convertRgb); + if(success) + m_convertRGBSet = convertRgb; + return success; } } @@ -3497,6 +3504,7 @@ bool VideoCapture_DShow::setProperty(int propIdx, double propVal) g_VI.stopDevice(m_index); g_VI.setIdealFramerate(m_index, fps); g_VI.setupDeviceFourcc(m_index, m_width, m_height, m_fourcc); + g_VI.setConvertRGB(m_index, m_convertRGBSet); } bool success = g_VI.isDeviceSetup(m_index); @@ -3602,6 +3610,7 @@ void VideoCapture_DShow::close() m_index = -1; } m_widthSet = m_heightSet = m_width = m_height = -1; + m_convertRGBSet = true; } Ptr create_DShow_capture(int index) diff --git a/modules/videoio/src/cap_dshow.hpp b/modules/videoio/src/cap_dshow.hpp index edb694efbb..9a3b9da3bd 100644 --- a/modules/videoio/src/cap_dshow.hpp +++ b/modules/videoio/src/cap_dshow.hpp @@ -37,6 +37,7 @@ protected: int m_index, m_width, m_height, m_fourcc; int m_widthSet, m_heightSet; + bool m_convertRGBSet; static videoInput g_VI; }; diff --git a/modules/videoio/test/test_camera.cpp b/modules/videoio/test/test_camera.cpp index 274c8227fe..c8a5598dcc 100644 --- a/modules/videoio/test/test_camera.cpp +++ b/modules/videoio/test/test_camera.cpp @@ -72,6 +72,27 @@ TEST(DISABLED_videoio_camera, basic) capture.release(); } +// Test that CAP_PROP_CONVERT_RGB remain to false (default is true) after other supported property are set. +// The test use odd value to be almost sure to trigger code responsible for recreating the device. +TEST(DISABLED_videoio_camera, dshow_convert_rgb_persistency) +{ + VideoCapture capture(CAP_DSHOW); + ASSERT_TRUE(capture.isOpened()); + ASSERT_TRUE(capture.set(CAP_PROP_CONVERT_RGB, 0)); + ASSERT_DOUBLE_EQ(capture.get(CAP_PROP_CONVERT_RGB), 0); + capture.set(CAP_PROP_FRAME_WIDTH, 641); + capture.set(CAP_PROP_FRAME_HEIGHT, 481); + capture.set(CAP_PROP_FPS, 31); + capture.set(CAP_PROP_CHANNEL, 1); + capture.set(cv::CAP_PROP_FOURCC, cv::VideoWriter::fourcc('Y', '1', '6', ' ')); + std::cout << "Camera 0 via " << capture.getBackendName() << " backend" << std::endl; + std::cout << "Frame width: " << capture.get(CAP_PROP_FRAME_WIDTH) << std::endl; + std::cout << " height: " << capture.get(CAP_PROP_FRAME_HEIGHT) << std::endl; + std::cout << "Capturing FPS: " << capture.get(CAP_PROP_FPS) << std::endl; + ASSERT_DOUBLE_EQ(capture.get(CAP_PROP_CONVERT_RGB), 0); + capture.release(); +} + TEST(DISABLED_videoio_camera, v4l_read_mjpg) { VideoCapture capture(CAP_V4L2);