如何构建cv2绑定

How to build cv2 binding

我已按照 opencv doc 创建自己的绑定。

我 运行 文件 gen2.py 生成了一些 header 文件:

./
../
pyopencv_generated_enums.h
pyopencv_generated_funcs.h
pyopencv_generated_include.h
pyopencv_generated_modules_content.h
pyopencv_generated_modules.h
pyopencv_generated_types_content.h
pyopencv_generated_types.h
pyopencv_signatures.json

我应该如何构建它? 我直接在 /opencv/modules/python 中尝试了 运行ning cmake CMakeLists.txt,但是没有找到一些定义。

我在 re-building 运行ning cmake CMakeLists.txt 中尝试了 /opencv/ ,我得到了:

  FATAL: In-source builds are not allowed.

         You should create a separate directory for build files.

我认为这两种方法都是错误的,但我还没有找到任何文档解释如何使用生成的 headers 进行构建。

我正在使用我克隆和构建的 opencv 4.5.5

编辑

我在 /source/opencv/modules/python/bindings/CMakeLists.txt 中找到了这个:

string(REPLACE ";" "\n" opencv_hdrs_ "${opencv_hdrs}")
file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/headers.txt" "${opencv_hdrs_}")
add_custom_command(
    OUTPUT ${cv2_generated_files}
    COMMAND "${PYTHON_DEFAULT_EXECUTABLE}" "${PYTHON_SOURCE_DIR}/src2/gen2.py" "${CMAKE_CURRENT_BINARY_DIR}" "${CMAKE_CURRENT_BINARY_DIR}/headers.txt"
    DEPENDS "${PYTHON_SOURCE_DIR}/src2/gen2.py"
            "${PYTHON_SOURCE_DIR}/src2/hdr_parser.py"
            # not a real build dependency (file(WRITE) result): ${CMAKE_CURRENT_BINARY_DIR}/headers.txt
            ${opencv_hdrs}
    COMMENT "Generate files for Python bindings and documentation"
)

我想我必须在 ${CMAKE_CURRENT_BINARY_DIR}/headers.txt 中添加我的 header 的路径,只是不确定如何获取 CMAKE_CURRENT_BINARY_DIR

的值

编辑 2

按照@berak的建议,我尝试了CMAKE_EXTRA_MODULES_PATH=my/path 这似乎让我非常接近我需要的东西。

它编译我的源代码并生成 .so 文件作为 libopencv_xxx.so 并将它们保存在我的 /usr/local/lib

(当运行宁nm在上面我看到我的class和方法)

但是!当我在脚本中 import cv2 时,我无法加载我的模块。 我尝试了 print(cv2.__dict__)greped,但它不存在。

关于如何将已编译的模块添加到我的 python-opencv 安装中的任何线索?

您不应该手动 运行 gen2.py,cmake 会在某个阶段在内部为您完成此操作。

由于您似乎在某些 linux 上,而不是 follow the build steps here,这也会生成 python 绑定,其要点是:

  • 创建一个特殊的“build 文件夹”并 cd 进去(不要尝试在 src 文件夹中构建,你将永远无法清理任何东西)

  • 运行 cmake <some args> path_to_src_folder(甚至更好 - cmake-gui),检查 python3 是否出现在输出

  • 运行 make install

关于如何创建绑定的文档不多(至少我只找到了this,这很有帮助,但没有所有信息)。

首先,你的模块必须使用以下树结构(我用cmake做了一切):

.
src
└── modules
    └── your_module
        ├── CMakeLists.txt
        ├── include
        │   └── opencv2
        │       └── your_module_bind_lib.hpp
        └── src
            └── your_module_bind_lib.cpp

我的一个例子CMakeLists.txt(当然这可能会根据你的项目而改变):

set(the_description "yourModule LIB")
ocv_define_module(your_module opencv_imgproc WRAP python)
include_directories(${OpenCV_INCLUDE_DIRS})

然后我用

克隆了OpenCV
git clone https://github.com/opencv/opencv.git

创建构建文件夹

mkdir wherever/build

和运行以下命令cmake

cd wherever/build
cmake -DOPENCV_EXTRA_MODULES_PATH=/project_from_previous_tree/src/modules/ -D BUILD_EXAMPLES=OFF -D BUILD_opencv_apps=OFF -D BUILD_DOCS=OFF -D BUILD_PERF_TESTS=OFF -D BUILD_TESTS=OFF -D CMAKE_INSTALL_PREFIX=/usr/local/  your_opencv_location/opencv/
make -j8
make install

在该命令中,唯一“特殊”的是 DOPENCV_EXTRA_MODULES_PATH(感谢@berak 的想法)。

然后呢? python 关卡会发生什么?

确保你的 python 安装实际指向内置的 opencv,或者使用类似的东西:

import sys
sys.path.append('/usr/local/lib/python3.8/site-packages/cv2/python-3.8')
import cv2

其中 /usr/local/lib/python3.8/site-packages/cv2/python-3.8' 是生成的 .so 在我的电脑中的位置。

有了这个你就可以使用

cv2.my_cpp_function()
cv2.my_cpp_class.some_method()
...

其中 my_cpp 东西是在 doc 之后的模块项目中声明和定义的,并且可以“轻松地”将 OpenCV 类型的对象作为参数。

Et voila,现在您可以在 python.

中使用您的 C++ 函数

请注意,此解决方案不会对从 Git.

克隆的 opencv 目录进行 任何 修改