Java图像处理能力较差,需要调用openCV本地函数,为了减少IO次数,直接把直接流传递到本地函数中,然后使用imdecode转换成Mat对象
Java代码
import com.bcx.util.WebpJniUtil;
import org.apache.commons.io.FileUtils;
import org.apache.commons.io.IOUtils;
import org.scijava.nativelib.DefaultJniExtractor;
import org.scijava.nativelib.JniExtractor;
import org.scijava.nativelib.NativeLibraryUtil;
import javax.imageio.ImageIO;
import javax.imageio.stream.FileImageInputStream;
import javax.imageio.stream.ImageInputStream;
import java.awt.image.BufferedImage;
import java.awt.image.DataBuffer;
import java.awt.image.Raster;
import java.io.*;
public class JNItest {
private static boolean NATIVE_LIBRARY_LOADED = false;
static {
loadNativeLibrary();
}
static synchronized void loadNativeLibrary() {
if (!NATIVE_LIBRARY_LOADED) {
NATIVE_LIBRARY_LOADED = true;
try {
JniExtractor jniExtractor = new DefaultJniExtractor(WebpJniUtil.class);
NativeLibraryUtil.loadNativeLibrary(jniExtractor,"JNItest");
} catch (IOException e) {
e.printStackTrace();
}
}
}
public static native void testArray2Mat(byte[] nativeByteArra,String destFile);
public static void main(String[] args) throws IOException {
JNItest test=new JNItest();
File file = new File("C:\\Users\\mafx\\Pictures\\225044047022496.jpg");
InputStream in = new FileInputStream(file);
byte[] nativeByteArra = IOUtils.toByteArray(in);
testArray2Mat(nativeByteArra,"C:\\Users\\mafx\\Pictures\\225044047022496-JNI.jpg");
}
}
C++代码:
JNIEXPORT void JNICALL Java_com_bcx_test_JNItest_testArray2Mat
(JNIEnv* env, jobject obj, jbyteArray jbyteArra, jstring dest) {
try
{
//复制java数组到C++
jsize len = env->GetArrayLength(jbyteArra);
signed char* pData = new signed char[len];
env->GetByteArrayRegion(jbyteArra, 0, len, pData);
//! 解码内存数据,变成cv::Mat数据
cv::Mat img_decode;
vector<uchar> data;
for (int i = 0; i < len; ++i) {
data.push_back(pData[i]);
}
img_decode = cv::imdecode(data, IMREAD_COLOR);
const char* destPtr = env->GetStringUTFChars(dest, false);
imwrite(destPtr, img_decode);
}
catch (exception e) {
cerr<<"发生错误:"<<e.what();
}
编译成dll:
cl -I"%JAVA_HOME%\include" -I"%JAVA_HOME%\include\win32" -I"D:\Program Files\opencv-4.1.0\build\include" -I"D:\Program Files\opencv-4.1.0\build\include\opencv2" -LD JNItest.cpp -FeJNItest.dll /link "D:\Program Files\opencv-4.1.0\build\x64\vc14\lib\opencv_world410.lib"
最后,将JNItest.dll放到java class/natives/windows_64/目录