android - 将什么传递给 Android 的 NDK 以便可以使用 OpenCV 加载图像?
问题描述
信息
我有一个 Android NDK / OpenCV 项目(运行本机 C++ 代码)。
我正在尝试将图像加载到 NDK,所以我将图像加载为位图,这样我就可以获得它的路径。
我不想将整个图像传递给 NDK(如这个答案、这个答案或其他),我只想将一个字符串(例如图像路径)或一个指针或类似的东西传递给 NDK,然后从NDK 与 OpenCV。
我尝试使用OpenCV 的人脸检测示例作为参考,但它并没有真正做我想做的事情。
为了在 Java 中获取路径字符串,我尝试了这个:
Uri uri = data.getData();
String imagePath = uri.getEncodedPath();
或这个:
Cursor imageCursor;
int imageNameIndex, imageSizeIndex;
Uri uri = data.getData();
imageCursor = getContentResolver().query(uri, null, null, null, null);
imageNameIndex = imageCursor.getColumnIndex(OpenableColumns.DISPLAY_NAME);
String imagePath = imageCursor.getString(nameIndex);
或者那个:
String imageFullPath = Environment.getExternalStorageDirectory() + "/Pictures/" + imagePath;
或者那个:
String imageFullPath = Environment.DIRECTORY_PICTURES + "/" + imagePath;
这让我得到了像/storage/emulated/0/Pictures/my-image.jpg
,Pictures/my-image.jpg
或.my-image.jpg
/document/image%3A167
然后我将字符串传递给 NDK(将其转换为char *
)并尝试使用 OpenCV 在 C++ 上加载图像imread
:
Mat image = imread(image_path, IMREAD_COLOR);
所有上述试验都会产生一个空Mat
对象(所有int
值相等0
且指针为NULL
)。
我也尝试过使用指针的类似方法。
问题
这是一个 OpenCV 问题吗?我应该Mat
以某种方式初始化吗?
如果不是,我应该将什么字符串/指针传递给 NDK 以便它可以加载图像?
解决方案
传球指针
Java端:
Activity.java
:
// create a mat object with CvType.CV_8UC4, for Android's RGBA_8888
Mat passToNativeMat = new Mat(height, width, CvType.CV_8UC4);
// convert (for example) a bitmap image to Mat object
Utils.bitmapToMat(bitmap, passToNativeMat);
// get the native address of the Mat object created
long passToNativeMatAddress = passToNativeMat.getNativeObjAddr();
// call the Native function
String imageToJNIResult = imageToJNI(passToNativeMatAddress);
// native declarations
public native String imageToJNI(long imagePointer);
本机方面:
native-lib.cpp
:
extern "C"
JNIEXPORT jstring JNICALL
Java_package_activity_imageToJNI(
JNIEnv* env,
jobject thiz,
jlong imagePointer) {
Mat& image_in_native = *(Mat*) imagePointer;
// do something with image Mat object
string return_string = "Return string";
return env->NewStringUTF(return_string.c_str());
}
传递字节数组
Java端:
public native String byteToJNI(byte[] myArray);
本机方面:
extern "C" JNIEXPORT jstring JNICALL
Java_package_activity_byteToJNI(
JNIEnv* env,
jobject thiz,
jbyteArray array) {
Mat * mat = ByteToMat(array);
string return_string = "Return string";
return env->NewStringUTF(return_string.c_str());
}
推荐阅读
- iis - IIS Server Windows server 2012 r2 文件删除问题
- javascript - 为什么这些变量不能保持价值?
- c++ - 在另一个方法(同一个类)上使用重载运算符(在一个类中定义)(本征用法)
- java - 与 StringBuilder 不同,回溯更改整数值
- php - PHP字符串仅在页面加载5分钟后运行
- snowflake-cloud-data-platform - 在雪花中查找先前执行的查询的行数
- html - 使用 HTML CSS 从添加到购物车按钮中删除悬停效果
- css - 使用网格区域角度交换元素的位置
- javascript - 除非在服务器上创建空文件夹,否则 node.js 服务器无法接收任何调用
- java - 如何在 Powershell 中运行 Java 命令