If someone has the same problem than me, my solution was to edit the Python script which generates the C++ and Java code of the JNI binding: modules/java/generator/gen_java.py.
I added the following code after the declaration of minMaxLoc: line 413, after }, # minMaxLoc
'minMaxIdx' : {
'j_code' : """
// manual port
public static class MinMaxIdxResult {
public double minVal;
public double maxVal;
public MinMaxIdxResult() {
minVal=0; maxVal=0;
}
}
// C++: minMaxIdx(Mat src, double* minVal, double* maxVal=0, int* minIdx=0, int* maxIdx=0, InputArray mask=noArray())
//javadoc: minMaxIdx(src, mask)
public static MinMaxIdxResult minMaxIdx(Mat src, MatOfInt minIdx, MatOfInt maxIdx, Mat mask) {
MinMaxIdxResult res = new MinMaxIdxResult();
long minIdxNativeObj=0;
if (minIdx != null) {
minIdxNativeObj=minIdx.nativeObj;
}
long maxIdxNativeObj=0;
if (maxIdx != null) {
maxIdxNativeObj=maxIdx.nativeObj;
}
long maskNativeObj=0;
if (mask != null) {
maskNativeObj=mask.nativeObj;
}
double resarr[] = n_minMaxIdxManual(src.nativeObj, minIdxNativeObj, maxIdxNativeObj, maskNativeObj);
res.minVal=resarr[0];
res.maxVal=resarr[1];
return res;
}
//javadoc: minMaxIdx(src, minIdx, maxIdx)
public static MinMaxIdxResult minMaxIdx(Mat src, MatOfInt minIdx, MatOfInt maxIdx) {
return minMaxIdx(src, minIdx, maxIdx, null);
}
//javadoc: minMaxIdx(src, minIdx)
public static MinMaxIdxResult minMaxIdx(Mat src, MatOfInt minIdx) {
return minMaxIdx(src, minIdx, null, null);
}
//javadoc: minMaxIdx(src)
public static MinMaxIdxResult minMaxIdx(Mat src) {
return minMaxIdx(src, null, null, null);
}
""",
'jn_code' :
""" private static native double[] n_minMaxIdxManual(long src_nativeObj, long minIdx_nativeObj, long maxIdx_nativeObj, long mask_nativeObj);\n""",
'cpp_code' :
"""
// C++: minMaxIdx(Mat src, double* minVal, double* maxVal=0, int* minIdx=0, int* maxIdx=0, InputArray mask=noArray())
JNIEXPORT jdoubleArray JNICALL Java_org_opencv_core_Core_n_1minMaxIdxManual (JNIEnv*, jclass, jlong, jlong, jlong, jlong);
JNIEXPORT jdoubleArray JNICALL Java_org_opencv_core_Core_n_1minMaxIdxManual
(JNIEnv* env, jclass, jlong src_nativeObj, jlong minIdx_nativeObj, jlong maxIdx_nativeObj, jlong mask_nativeObj)
{
try {
LOGD("Core::n_1minMaxIdx()");
jdoubleArray result;
result = env->NewDoubleArray(2);
if (result == NULL) {
return NULL; /* out of memory error thrown */
}
Mat& src = *((Mat*)src_nativeObj);
double minVal, maxVal;
int minIdx[src.dims];
int maxIdx[src.dims];
if (mask_nativeObj != 0) {
Mat& mask = *((Mat*)mask_nativeObj);
minMaxIdx(src, &minVal, &maxVal, minIdx, maxIdx, mask);
} else {
minMaxIdx(src, &minVal, &maxVal, minIdx, maxIdx);
}
if (minIdx_nativeObj != 0) {
Mat& minIdx_mat = *((Mat*)minIdx_nativeObj);
for(int i = 0; i < src.dims; i++) {
minIdx_mat.at<int>(i) = minIdx[i];
}
}
if (maxIdx_nativeObj != 0) {
Mat& maxIdx_mat = *((Mat*)maxIdx_nativeObj);
for(int i = 0; i < src.dims; i++) {
maxIdx_mat.at<int>(i) = maxIdx[i];
}
}
jdouble fill[2];
fill[0]=minVal;
fill[1]=maxVal;
env->SetDoubleArrayRegion(result, 0, 2, fill);
return result;
} catch(const cv::Exception& e) {
LOGD("Core::n_1minMaxIdx() catched cv::Exception: %s", e.what());
jclass je = env->FindClass("org/opencv/core/CvException");
if(!je) je = env->FindClass("java/lang/Exception");
env->ThrowNew(je, e.what());
return NULL;
} catch (...) {
LOGD("Core::n_1minMaxIdx() catched unknown exception (...)");
jclass je = env->FindClass("java/lang/Exception");
env->ThrowNew(je, "Unknown exception in JNI code {core::minMaxIdx()}");
return NULL;
}
}
""",
}, # minMaxIdx
This code could be greatly improved by merging the structures MinMaxLocResult and MinMaxIdxResult, but I didn't want to change the code of minMaxLoc.