build(opencv): support OpenCV 5, add standalone header smoke test (#5326)

Find OpenCV via its exported CMake config (PREFER_CONFIG) so OpenCV 5 is
located correctly.

Modify our imagebufalgo_opencv.h to work with OpenCV 5. But how to test
whether we did it correctly?

We never had an actual test for the OpenCV interop. So set one up.

Assisted-by: Claude Code / Sonnet 5

Signed-off-by: Larry Gritz <lg@larrygritz.com>
This commit is contained in:
Larry Gritz
2026-07-16 19:54:25 -07:00
committed by GitHub
parent c5e085eee3
commit 5b4a231634
8 changed files with 116 additions and 3 deletions
+1 -1
View File
@@ -63,7 +63,7 @@ NEW or CHANGED MINIMUM dependencies since the last major release are **bold**.
* TBB >= 2018 (tested through 2021 and OneTBB)
* If you want support for converting to and from OpenCV data structures,
or for capturing images from a camera:
* OpenCV 4.x (tested through 4.13)
* OpenCV 4.x or 5.x (tested through 5.0)
* If you want support for GIF images:
* giflib >= 5.0 (tested through 6.1.2)
* If you want support for HEIF/HEIC or AVIF images:
+2 -1
View File
@@ -151,7 +151,8 @@ if (NOT OPENCOLORIO_INCLUDES)
endif ()
include_directories(BEFORE ${OPENCOLORIO_INCLUDES})
checked_find_package (OpenCV 4.0
checked_find_package (OpenCV VERSION_MIN 4.0
PREFER_CONFIG
DEFINITIONS USE_OPENCV=1)
# Intel TBB
+2
View File
@@ -380,6 +380,8 @@ macro (oiio_add_all_tests)
URL http://www.itu.int/net/ITU-T/sigdb/speimage/ImageForm-s.aspx?val=10100803)
oiio_add_tests (jxl
FOUNDVAR JXL_FOUND)
oiio_add_tests (imagebufalgo-opencv
FOUNDVAR OpenCV_FOUND)
set (all_openexr_tests
openexr-suite openexr-multires openexr-chroma openexr-decreasingy
openexr-v2 openexr-window perchannel oiiotool-deep)
@@ -22,6 +22,7 @@
#pragma once
#define OPENIMAGEIO_IMAGEBUFALGO_OPENCV_H
#include <OpenImageIO/half.h>
#include <OpenImageIO/imagebufalgo.h>
#include <OpenImageIO/imagebufalgo_util.h>
#include <OpenImageIO/platform.h>
@@ -49,7 +50,9 @@ OIIO_PRAGMA_WARNING_PUSH
// # pragma GCC diagnostic ignored "-Wunused-but-set-variable"
#endif
#include <opencv2/opencv.hpp>
#if OIIO_OPENCV_VERSION >= 40000
#if OIIO_OPENCV_VERSION >= 50000
# include <opencv2/imgproc.hpp>
#elif OIIO_OPENCV_VERSION >= 40000
# include <opencv2/core/core_c.h>
# include <opencv2/imgproc/imgproc_c.h>
#else
@@ -0,0 +1,29 @@
# Copyright Contributors to the OpenImageIO project.
# SPDX-License-Identifier: Apache-2.0
# https://github.com/AcademySoftwareFoundation/OpenImageIO
cmake_minimum_required (VERSION 3.18)
project (oiio-imagebufalgo-opencv
LANGUAGES CXX)
if (NOT CMAKE_BUILD_TYPE)
set (CMAKE_BUILD_TYPE "Release")
endif ()
set (CMAKE_CXX_STANDARD 17 CACHE STRING "C++ standard to prefer (17, 20, etc.)")
set (CMAKE_CXX_STANDARD_REQUIRED ON)
set (CMAKE_CXX_EXTENSIONS OFF)
find_package (OpenImageIO CONFIG REQUIRED)
find_package (Imath CONFIG REQUIRED)
find_package (OpenCV REQUIRED)
# Special for OIIO testsuite when running in sanitize mode
if (DEFINED ENV{SANITIZE})
add_compile_options (-fsanitize=$ENV{SANITIZE})
add_link_options (-fsanitize=$ENV{SANITIZE})
endif ()
add_executable (opencv-roundtrip src/opencv-roundtrip.cpp)
target_include_directories (opencv-roundtrip PRIVATE ${OpenCV_INCLUDE_DIRS})
target_link_libraries (opencv-roundtrip PRIVATE OpenImageIO::OpenImageIO Imath::Imath ${OpenCV_LIBS})
@@ -0,0 +1,3 @@
to_OpenCV: PASS
from_OpenCV: PASS
round trip: PASS
+26
View File
@@ -0,0 +1,26 @@
#!/usr/bin/env python
# Copyright Contributors to the OpenImageIO project.
# SPDX-License-Identifier: Apache-2.0
# https://github.com/AcademySoftwareFoundation/OpenImageIO
# Minimal smoke test for imagebufalgo_opencv.h: build a tiny standalone
# program (linked against the already-installed OpenImageIO and OpenCV) that
# round-trips an ImageBuf through cv::Mat, and check that it compiles, links,
# and runs cleanly. Only enabled if OpenCV was found (see FOUNDVAR OpenCV_FOUND
# in src/cmake/testing.cmake).
redirect = " >> out.txt 2>&1 "
if platform.system() == 'Windows' :
prefix = ".\\build\\Release\\"
else :
prefix = "./build/"
# Build and run the standalone OpenCV round-trip test. The cmake
# configure/build steps are redirected to build.txt instead of out.txt since
# their output (paths, compiler banners, timings) isn't reproducible across
# machines and would break the ref comparison.
command += run_app("cmake -S " + test_source_dir + " -B build -DCMAKE_BUILD_TYPE=Release >> build.txt 2>&1", silent=True)
command += run_app("cmake --build build --config Release >> build.txt 2>&1", silent=True)
command += run_app(prefix + "opencv-roundtrip")
@@ -0,0 +1,49 @@
// Copyright Contributors to the OpenImageIO project.
// SPDX-License-Identifier: Apache-2.0
// https://github.com/AcademySoftwareFoundation/OpenImageIO
// Minimal, standalone exercise of imagebufalgo_opencv.h: build a small
// gradient ImageBuf, round-trip it through cv::Mat via to_OpenCV() /
// from_OpenCV(), and verify the pixels survive unchanged. This is meant to
// smoke-test that the header still compiles and links correctly against
// whatever OpenCV version is installed (the header does version-dependent
// things internally based on OIIO_OPENCV_VERSION).
#include <opencv2/opencv.hpp>
#include <OpenImageIO/imagebufalgo_opencv.h>
using namespace OIIO;
int
main()
{
ImageBuf src
= ImageBufAlgo::fill({ 1.0f, 0.0f, 0.0f }, { 0.0f, 1.0f, 0.0f },
{ 0.0f, 0.0f, 1.0f }, { 1.0f, 1.0f, 1.0f },
ROI(0, 64, 0, 64, 0, 1, 0, 3));
cv::Mat mat;
bool to_ok = ImageBufAlgo::to_OpenCV(mat, src);
if (to_ok && !mat.empty()) {
OIIO::print("to_OpenCV: PASS\n");
} else {
OIIO::print("to_OpenCV FAIL: {}\n", OIIO::geterror());
return 1;
}
ImageBuf dst = ImageBufAlgo::from_OpenCV(mat);
if (!dst.has_error()) {
OIIO::print("from_OpenCV: PASS\n");
} else {
OIIO::print("from_OpenCV FAIL: {}\n", dst.geterror());
return 1;
}
auto comp = ImageBufAlgo::compare(src, dst, 0.0f, 0.0f);
bool roundtrip_ok = !comp.error && comp.maxerror == 0.0f;
OIIO::print("round trip: {}\n", roundtrip_ok ? "PASS" : "FAIL");
return roundtrip_ok ? 0 : 1;
}