首页 技术 正文
技术 2022年11月18日
0 收藏 619 点赞 4,587 浏览 5157 个字

交叉编译OpenCV的Android版本

OpenCV作为一个强大的图像处理库,在Android上也有强大的应用。

OpenCV官网提供了SDK的下载,可以直接下载使用

OpenCV官网地址:https://opencv.org/

不过有时候也会有自定义编译的需求

下面来记录一下最近在交叉编译OpenCV所作的笔记

避免以后走弯路。

编译Host系统是Ubuntu 16.04

准备工作

下载opencv:

 git clone git@github.com:opencv/opencv.git
git checkout 3.4

下载opencv依赖的库

 git clone git@github.com:opencv/opencv_contrib.git
git checkout 3.4

这里我们使用的版本都是3.4。

配置环境:

1. 安装ant

编译Java代码需要用到ant或者gradle

但是我还没搞清楚怎么配置使用gradle编译

而且我这次是在服务器上工作,没有x11环境

没装Android Studio,所以,姑且使用ant编译Java。

修改opencv/CMakeLists.txt文件

激活ant编译

set(ANDROID_PROJECTS_SUPPORT_ANT ON)
sudo apt-get install ant

2. 安装ndk

安装ndk需要翻wall,请自备梯子

这里写了一个python程序,用于枚举NDK的版本,

然后手动输入选择下载对应的版本,

这里我下载的r17c版本NDK,下载完成之后配置NDK_ROOT环境变量

 #!/usr/bin/env python import urllib2
import collections
import json
import os def init():
"""
Return name/link dict @return: name-to-link dict
"""
with open('table.json') as data_file:
url_table = json.load(data_file) if url_table is None or len(url_table) <= 0:
print('\033[91m' + ' There is no item in table.json ' + '\033[0m')
os.sys.exit(0) # Sort alphabetically
url_table = collections.OrderedDict(sorted(url_table.items()))
index = 0
for key in url_table:
index = index + 1
print str(index) + '] ' + key return url_table def getTargetLink(desired_index, url_table):
"""
Return download link @type desired_index: number
@param desired_index: Desired index
@type url_table: dict
@param url_table: name-to-link @return: Download link
"""
index = 0
for key in url_table:
index = index + 1
if desired_index == index:
return url_table[key]
return None def download(url):
if url == None:
return file_name = url.split('/')[-1]
u = urllib2.urlopen(url)
f = open(file_name, 'wb')
meta = u.info()
file_size = int(meta.getheaders("Content-Length")[0])
print "Downloading: %s Bytes: %s" % (file_name, file_size) file_size_dl = 0
block_sz = 8192
while True:
buffer = u.read(block_sz)
if not buffer:
break file_size_dl += len(buffer)
f.write(buffer)
status = r"%10d [%3.2f%%]" % (file_size_dl, file_size_dl * 100. / file_size)
status = status + chr(8)*(len(status)+1)
print status, f.close() if __name__ == '__main__':
url_table = init()
var = raw_input("Please enter the numer you want to download: ")
link = getTargetLink(int(var), url_table)
download(link)

3. 安装SDK

由于我们需要编译的android版本,需要用到SDK的build tools和sdk的platform版本库

这里使用SDK的build tools版本是24.0.3

往上的版本,Google去掉了aidl,会导致没法编译Java端的代码,也无法生成libopencv_java3.so

所以在下载的SDK版本中,build tools只能保留不高于24.0.3的版本

platform版本库使用android-21

下载SDK的方法:

找一台装有Android Studio的电脑,使用SDK Manager下载对应的版本即可

然后将SDK拷贝至交叉编译的电脑上,配置SDK环境变量

export NDK_ROOT=/path/to/android-ndk-r17c
export ANDROID_HOME=path/to/sdk

4. 配置SDK tools版本

在我们的SDK中,有个tools目录

具体的版本,是Android Studio在SDK Manager中配置的

但是OpenCV只能支持到tools_r25.2.5-linux.zip

所以需要手动下载tools_r25.2.5-linux.zip,解压替换SDK目录的tools

下载地址:https://dl.google.com/android/repository/tools_r25.2.5-linux.zip

5. 安装CMake和其它编译环境

sudo apt-get install cmake
sudo apt-get install build-essential make

开始交叉编译

由于OpenCV需要使用cmake编译

需要配置很多参数,所以使用bash脚本是最方便的方式

编译脚本放在opencv和opencv_contrib的同级目录

#!/bin/bash
NDK_ROOT="${1:-${NDK_ROOT}}"### ABIs setup
#declare -a ANDROID_ABI_LIST=("armeabi-v7a with NEON")
declare -a ANDROID_ABI_LIST=("armeabi-v7a")### path setup
SCRIPT=$(readlink -f $)
WD=`dirname $SCRIPT`
OPENCV_ROOT="${WD}/opencv"
N_JOBS=${N_JOBS:-}INSTALL_DIR="${WD}/opencv-build"
rm -rf "${INSTALL_DIR}/opencv"### Make each ABI target iteratly and sequentially
for i in "${ANDROID_ABI_LIST[@]}"
do
ANDROID_ABI="${i}"
echo "Start building ${ANDROID_ABI} version" if [ "${ANDROID_ABI}" = "armeabi" ]; then
API_LEVEL=
else
API_LEVEL=
fi temp_build_dir="${OPENCV_ROOT}/platforms/build_android_${ANDROID_ABI}"
### Remove the build folder first, and create it
#-DANDROID_TOOLCHAIN_NAME=clang
#-DANDROID_TOOLCHAIN_NAME="arm-linux-androideabi-5" \
#-DANDROID_STL=gnustl_static \
rm -rf "${temp_build_dir}"
mkdir -p "${temp_build_dir}"
cd "${temp_build_dir}" cmake -DCMAKE_BUILD_WITH_INSTALL_RPATH=ON \
-DCMAKE_TOOLCHAIN_FILE="${OPENCV_ROOT}/platforms/android/android.toolchain.cmake" \
-DANDROID_NDK="${NDK_ROOT}" \
-DANDROID_NATIVE_API_LEVEL=${API_LEVEL} \
-DANDROID_ABI="${ANDROID_ABI}" \
-DANDROID_CPP_FEATURES="rtti exceptions" \
-DANDROID_ARM_NEON=TRUE \
-DANDROID_STL=gnustl_static \
-DCMAKE_BUILD_TYPE=Release \
-D BUILD_opencv_java=ON \
-D BUILD_ANDROID_PROJECTS=ON \
-D WITH_CUDA=OFF \
-D WITH_MATLAB=OFF \
-D BUILD_ANDROID_EXAMPLES=OFF \
-D BUILD_DOCS=OFF \
-D BUILD_PERF_TESTS=OFF \
-D BUILD_TESTS=OFF \
-DOPENCV_EXTRA_MODULES_PATH="${WD}/opencv_contrib/modules/" \
-DCMAKE_INSTALL_PREFIX="${INSTALL_DIR}/opencv" \
../..
# Build it
make -j${N_JOBS}
# Install it
make install/strip
### Remove temp build folder
cd "${WD}"
rm -rf "${temp_build_dir}"
echo "${temp_build_dir}"
echo "end building ${ANDROID_ABI} version"
done

这里只启用了armeabi-v7a编译目标

其它平台可根据需求添加

目前无法使用ANDROID_TOOLCHAIN_NAME来指定clang编译器

因为OpenCV的makefile在解析clang交叉编译工具链使用的代码没做匹配

而我也暂时没精力自己修改做匹配

有兴趣的同学,可以修改

${OPENCV_ROOT}/platforms/android/android.toolchain.cmake

来匹配clang编译器

STL链接使用的是gnu版本的

因为OpenCV用到了C++11

如果使用c++_static版本,因为Google没做后续支持维护

gcc在这个工具链上不支持很多C++和C++11特性

会导致编译失败,我尝试过使用CrystaX NDK

但是在configure阶段就失败了

只能无疾而终

其它编译选项顾名思义,不做过多解析。

备注:

如果需要使用C++14特性编译

需要修改opencv/CMakeList.txt文件

手动添加,pathch如下所示

--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -, +, @@ endif()
OCV_OPTION(ENABLE_CXX11 "Enable C++11 compilation mode" "${OPENCV_CXX11}")
include(cmake/OpenCVDetectCXXCompiler.cmake)
ocv_cmake_hook(POST_DETECT_COMPILER)
-
+set(CMAKE_CXX_STANDARD )
+set(CMAKE_CXX_STANDARD_REQUIRED ON)
+set(CMAKE_VERBOSE_MAKEFILE ON)
+set(ANDROID_PROJECTS_SUPPORT_ANT ON)
# Add these standard paths to the search paths for FIND_LIBRARY
# to find libraries from these locations first
if(UNIX AND NOT ANDROID)
相关推荐
python开发_常用的python模块及安装方法
adodb:我们领导推荐的数据库连接组件bsddb3:BerkeleyDB的连接组件Cheetah-1.0:我比较喜欢这个版本的cheeta…
日期:2022-11-24 点赞:878 阅读:8,941
Educational Codeforces Round 11 C. Hard Process 二分
C. Hard Process题目连接:http://www.codeforces.com/contest/660/problem/CDes…
日期:2022-11-24 点赞:807 阅读:5,465
下载Ubuntn 17.04 内核源代码
zengkefu@server1:/usr/src$ uname -aLinux server1 4.10.0-19-generic #21…
日期:2022-11-24 点赞:569 阅读:6,280
可用Active Desktop Calendar V7.86 注册码序列号
可用Active Desktop Calendar V7.86 注册码序列号Name: www.greendown.cn Code: &nb…
日期:2022-11-24 点赞:733 阅读:6,094
Android调用系统相机、自定义相机、处理大图片
Android调用系统相机和自定义相机实例本博文主要是介绍了android上使用相机进行拍照并显示的两种方式,并且由于涉及到要把拍到的照片显…
日期:2022-11-24 点赞:512 阅读:7,728
Struts的使用
一、Struts2的获取  Struts的官方网站为:http://struts.apache.org/  下载完Struts2的jar包,…
日期:2022-11-24 点赞:671 阅读:4,765