我使用的是OpenCV 4.6.0 Android SDK,我从sourceforge下载并在我的共享库/so中使用它。这个库是从我的android应用程序(aarch64)中调用的。android.toolchain.cmake:
...
set(CMAKE_C_COMPILER /home/username/Android/SDK/ndk/25.1.8937393/toolchains/llvm/prebuilt/linux-x86_64/bin/aarch64-linux-android21-clang)
set(CMAKE_CXX_COMPILER /home/username/Android/SDK/ndk/25.1.8937393/toolchains/llvm/prebuilt/linux-x86_64/bin/aarch64-linux-android21-clang++)
set(CMAKE_SYSTEM_NAME Android)
set(CMAKE_SYSTEM_VERSION 21)
set(CMAKE_ANDROID_ARCH_ABI arm64-v8a)
set(CMAKE_ANDROID_NDK /home/username/Android/Sdk/ndk/25.1.8937393)
set(CMAKE_SYSTEM_PROCESSOR aarch64)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_EXTENSIONS OFF)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
...
和CMakeLists.txt:
...
set(OpenCV_DIR ${CMAKE_CURRENT_LIST_DIR}/opencv-4.6.0-android-sdk/OpenCV-android-sdk/sdk/native/jni/abi-arm64-v8a)
target_include_directories(${PROJECT_NAME} PUBLIC ${CMAKE_CURRENT_LIST_DIR}/opencv-4.6.0-android-sdk/OpenCV-android-sdk/sdk/native/jni/include)
find_package(OpenCV REQUIRED)
...
target_link_libraries(${PROJECT_NAME} PRIVATE opencv_highgui)
...
My.h
#ifdef __cplusplus
extern "C"
{
#endif
bool imwriteC(Bitmap *bitmap, const char *filename);
#ifdef __cplusplus
}
#endif
和.cpp
#include <opencv2/opencv.hpp>
#include "myheader.h"
...
bool imwriteWrapper(Bitmap *bitmap, const char *filename)
{
Mat mat;
// ...
// bitmap to mat conversion here
// ...
return imwrite(filename, mat);
}
bool imwriteC(Bitmap *bitmap, const char *filename) {
return imwriteWrapper(bitmap, filename);
}
我从C-Code调用我的imwriteC
。我的错误信息看起来像名称混淆
Unable to load library 'testlibrary':
"_ZN2cv7imwriteERKNSt6_ndk112basic_stringlcNS0_11char_traitslcEENS0_9allocatorlcEEEERKNS_11_InputArrayERKNS0_6vectorliNS4_liEEEE" referenced by ... "/path/to/testlibrary.so"...
所以似乎OpenCVsimwrite
不能找到由于名称混淆的问题(?)。
这不是关于混乱,你只是没有链接到你需要的所有OpenCV库。
你正在使用OpenCV 4.6.0版本。我看到你正在调用imwrite
,并且你正在链接highgui
模块。嗯,以前(在2.4.x中)这是可行的,但是IIRC从3开始。这个函数驻留在imgcodecs
模块中。所以你应该把target_link_libraries
语句改成
target_link_libraries(${PROJECT_NAME} PRIVATE opencv_imgcodecs)
此外,由于这里使用的是Mat
,因此可能需要core
模块。通常,您可以从文档中找出模块的名称(最好查看URL -对于imwrite
,group__imgcodecs.html
在中间,模块名称在两个下划线之后)。
当然,正如您所发现的,由于您的find_package(OpenCV REQUIRED)
,您也可以采取快捷方式并与${OpenCV_LIBS}
链接,最终尝试所有OpenCV模块。我想这是一个足够好的选择,尽管我个人更喜欢明确地指定我需要什么,而不是更多。