因项目需要,自己做了demo,从中学习很多,所以分享出来,希望有这方面需求的少走一些弯路,opencv怎么安装网上教程多多,这里不加详细说明,我安装的opencv-3.3.0

如上图所示,找到相应的jar包,这里讲一下如何这个jar如何导入Maven仓库

mvn install:install-file -Dfile=D:\opencv-3.0.\opencv\build\java\opencv-.jar 
-DgroupId=com.suibian -DartifactId=opencv- -Dversion=3.3. -Dpackaging=jar -DgeneratePom=true -DcreateChecksum=true

<groupId>com.suibian</groupId>
<artifactId>opencv-</artifactId>
<version>3.3.</version>

好了,这样java可以通过这个jar操作opencv,那我们看一下,当然你能这样想,说明你很单纯,让我们看一下opencv 中includ中的路径和jar中包的对比

哈哈,全景图的关键stitching并没有,而且面向java的2015以后就一直没有更新,如下图所示一个全景图(傻瓜)合成的关键类没有,但是C++给我提供了

那怎么办呢,如何用java调用C++的代码,我们知道和操作系统打交道,C/C++无疑比Java更合适,opencv图形处理的这方面的应用,大多数是C++开发比较多,java中的一个关键字native大家都不陌生吧,然而我们想点进去,想看看是怎么实现的,怎么也点不进去,因为他就不是java写的,可能是C/C++,native对应都是java中jre下bin目录的XXX.dll文件,所以把我们要使用的C++代码打包成dll格式的文件放到bin目录即可,当然这涉及到方法的参数和返回值,废话不多说,安装visual  studio  2017,安装教程网上教程很多

点击  文件-->新建--->项目--->windows桌面-->动态链接库(Dll),这样项目就新建成功,接下来上代码

这是全景图合成的C++代码

#include "stdafx.h"
#include <iostream>
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/opencv.hpp>
using namespace std;
using namespace cv;
bool try_use_gpu = false;
vector<Mat> imgs;
string result_name = "D:/result1.jpg";
int _tmain(int argc, char * argv[])
{
Mat img1 = imread("D:/quanjingtu/hh/1.jpg");
Mat img2 = imread("D:/quanjingtu/hh/2.jpg");
Mat img3 = imread("D:/quanjingtu/hh/3.jpg");
Mat img4 = imread("D:/quanjingtu/hh/4.jpg");
Mat img5 = imread("D:/quanjingtu/hh/5.jpg");
Mat img6 = imread("D:/quanjingtu/hh/6.jpg");
Mat img7 = imread("D:/quanjingtu/hh/7.jpg");
Mat img8 = imread("D:/quanjingtu/hh/8.jpg");
Mat img9 = imread("D:/quanjingtu/hh/9.jpg");
Mat img10 = imread("D:/quanjingtu/hh/10.jpg"); //Mat img6 = imread("6.jpg");
if (img1.empty() || img2.empty())
{
cout << "Can't read image" << endl;
return -;
}
imgs.push_back(img1);
imgs.push_back(img2);
imgs.push_back(img3);
imgs.push_back(img4);
imgs.push_back(img5);
imgs.push_back(img6);
imgs.push_back(img7);
imgs.push_back(img8);
imgs.push_back(img9);
imgs.push_back(img10); //imgs.push_back(img6);
Stitcher stitcher = Stitcher::createDefault(try_use_gpu);
// 使用stitch函数进行拼接
Mat pano;
Stitcher::Status status = stitcher.stitch(imgs, pano);
imwrite(result_name, pano);
Mat pano2 = pano.clone();
// 显示源图像,和结果图像
//imshow("全景图像", pano);
if (waitKey() == )
return ;
//imwrite(result_name, pano);
}

那么java如何和C++进行交互呢,通过java中jni技术

让我们了解一下java中JNI

  Java Native Interface(简称JNI),Java是跨平台语言,有时候需要调用本地代码,Sun公司提供JNI接口,通过这个接口与操作系统本地代码相互调用,如下图所示是Java中native的调用原理

脉络都理通了,那就开始吧

public class OpenCVUtil {
static {
//这里的system.load用来加载C++生成的动态链接库,加载实际自己也可以决定不一定非的是静态的。
System.loadLibrary("OpenCVUtil");
} public static native String changeArrValue(String str);
public static void main(String[] args) throws UnsupportedEncodingException {
String base="D:/quanjingtu/gg"+"/";
int length=;
String url=""; for (int i=;i<=length;i++){
if (i==){
url=url+base+i+".jpg";
}else {
url=url+","+base+i+".jpg";
} }
//System.out.println(url);
String temp =new String(changeArrValue(url).getBytes(),"GBK");
System.out.println(temp); ; }
}

定义native方法,将该java文件编译成.class文件

进入cmd命令窗口,打开对应编译好的class文件目录执行javah命令

javah  -classpath <生成XX.h文件存放位置>  -jni <包路径.类名>

生成对应com_lianxi_securitytest_opencv_OpenCVUtil.h文件

#include <jni.h>
/* Header for class com_lianxi_securitytest_opencv_OpenCVUtil */ #ifndef _Included_com_lianxi_securitytest_opencv_OpenCVUtil
#define _Included_com_lianxi_securitytest_opencv_OpenCVUtil
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: com_lianxi_securitytest_opencv_OpenCVUtil
* Method: changeArrValue
* Signature: (Ljava/lang/String;)Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_com_lianxi_securitytest_opencv_OpenCVUtil_changeArrValue
(JNIEnv *, jclass, jstring); #ifdef __cplusplus
}
#endif
#endif

只把native方法处理了,复制该文件,到vs 2017项目所在的位置

#include "stdafx.h"
#include "com_lianxi_securitytest_opencv_OpenCVUtil.h"
#include<iostream>
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/opencv.hpp>
#include <vector>
#include <string>
using namespace std;
using namespace cv;
bool try_use_gpu = false;
vector<Mat> imgs;
string result_name = "D:/result.jpg"; JNIEXPORT jstring JNICALL Java_com_lianxi_securitytest_opencv_OpenCVUtil_changeArrValue
(JNIEnv *env, jclass obj, jstring prompt) {
//这是接收过来的字符串,多个路径
const char* str;
//.................................................................... //........................... //imgs.push_back(img6);
Stitcher stitcher = Stitcher::createDefault(try_use_gpu);
// 使用stitch函数进行拼接
Mat pano;
Stitcher::Status status = stitcher.stitch(imgs, pano);
imwrite(result_name, pano);
Mat pano2 = pano.clone();
// 显示源图像,和结果图像
//imshow("全景图像", pano);
if (waitKey() == ) if (status != Stitcher::OK) {
return env->NewStringUTF("picture failure!!!"); } //return env->NewStringUTF(result_name.c_str);
string newstr = "picture success!!!URL=" + result_name;
return env->NewStringUTF(const_cast<char*>(newstr.c_str())); }

上面就是对应C++代码

点击生成--->重新生成解决方案    生成对应的dll文件,然后放到JDK的jre/bin目录里

运行java程序,结果如下

看一下合成的全景图吧

java 实现基于opencv全景图合成的更多相关文章

  1. java实现,使用opencv合成全景图,前端使用krpano展示

    这周花三天做了一demo,算上之前的,怎么也有五天,上一篇是opencv介绍,以及定义native方法,通过本地图片路径传参,底层调用Opencv图像库合成,有兴趣的可以看看,这篇重点在于krpano ...

  2. Java基于opencv实现图像数字识别(五)—投影法分割字符

    Java基于opencv实现图像数字识别(五)-投影法分割字符 水平投影法 1.水平投影法就是先用一个数组统计出图像每行黑色像素点的个数(二值化的图像): 2.选出一个最优的阀值,根据比这个阀值大或小 ...

  3. Java基于opencv实现图像数字识别(四)—图像降噪

    Java基于opencv实现图像数字识别(四)-图像降噪 我们每一步的工作都是基于前一步的,我们先把我们前面的几个函数封装成一个工具类,以后我们所有的函数都基于这个工具类 这个工具类呢,就一个成员变量 ...

  4. Java基于opencv实现图像数字识别(三)—灰度化和二值化

    Java基于opencv实现图像数字识别(三)-灰度化和二值化 一.灰度化 灰度化:在RGB模型中,如果R=G=B时,则彩色表示灰度颜色,其中R=G=B的值叫灰度值:因此,灰度图像每个像素点只需一个字 ...

  5. Java基于opencv实现图像数字识别(二)—基本流程

    Java基于opencv实现图像数字识别(二)-基本流程 做一个项目之前呢,我们应该有一个总体把握,或者是进度条:来一步步的督促着我们来完成这个项目,在我们正式开始前呢,我们先讨论下流程. 我做的主要 ...

  6. 基于OpenCv和swing的图片/视频展示Java实现

    基于OpenCv和swing实现图片/视频的展示 图片的展示 swing展示图片,多为操作BufferedImage,这里要关注的核心是将Mat转为BufferedImage. 代码如下: publi ...

  7. Java基于opencv实现图像数字识别(一)

    Java基于opencv实现图像数字识别(一) 最近分到了一个任务,要做数字识别,我分配到的任务是把数字一个个的分开:当时一脸懵逼,直接百度java如何分割图片中的数字,然后就百度到了用Buffere ...

  8. 基于opencv将视频转化为字符串Java版

    基于opencv将视频转化为字符串Java版 opencv java  先上一个效果图吧 首先,弄清一下原理 我们要将视频转化为字符画,那么就需要获取画面的每一帧,也就是每一张图片,然后将图片进行转化 ...

  9. Canny边缘检测算法(基于OpenCV的Java实现)

    目录 Canny边缘检测算法(基于OpenCV的Java实现) 绪论 Canny边缘检测算法的发展历史 Canny边缘检测算法的处理流程 用高斯滤波器平滑图像 彩色RGB图像转换为灰度图像 一维,二维 ...

随机推荐

  1. 【linux】【jenkins】自动化运维五 整合邮件提醒

    1.安装插件 Email Extension Template Plugin 安装教程参考:https://www.cnblogs.com/jxd283465/p/11542680.html 2.系统 ...

  2. SpringBoot系列——ElasticSearch

    前言 本文记录安装配置ES环境,在SpringBoot项目中使用SpringData-ElasticSearch对ES进行增删改查通用操作 ElasticSearch官网:https://www.el ...

  3. Splitting into digits CodeForce#1104A

    题目链接:Splitting into digits 题目原文 Vasya has his favourite number 

  4. 基于windows的Redis后台服务安装卸载管理

    首先,需要你进入你的Redis解压根目录,例如,类似于我下图的这样子: 接着打开你的cmd,使用cd命令切换到该目录,或者直接在上图的地址栏输入“cmd”并回车.这里为什么让你先使用资源管理器找到你的 ...

  5. 项目管理知识点-结合Enovia项目管理模块

    核心知识域:整体管理.范围管理.进度管理.成本管理.质量管理.信息安全管理 保障域:人力资源管理.合同管理.采购管理.风险管理.信息(文档)管理.配置管理.知识产权管理.法律法规标准规范管理.职业道德 ...

  6. Java 代理模式 (二) 动态代理

    代理模式 代理(Proxy)是一种设计模式, 提供了对目标对象另外的访问方式:即通过代理访问目标对象. 这样好处: 可以在目标对象实现的基础上,增强额外的功能操作.(扩展目标对象的功能). 代理模式的 ...

  7. 转 Oracle中关于处理小数点位数的几个函数,取小数位数,Oracle查询函数

    关于处理小数点位数的几个oracle函数() 1. 取四舍五入的几位小数 select round(1.2345, 3) from dual; 结果:1.235 2. 保留两位小数,只舍 select ...

  8. 深度解密Go语言之反射

    目录 什么是反射 为什么要用反射 反射是如何实现的 types 和 interface 反射的基本函数 反射的三大定律 反射相关函数的使用 代码样例 未导出成员 反射的实际应用 json 序列化 De ...

  9. 设计模式的七大原则(Java)

    一.OOP三大基本特性 OOP 面向对象程序设计(Object Oriented Programming)作为一种新方法,其本质是以建立模型体现出来的抽象思维过程和面向对象的方法.模型是用来反映现实世 ...

  10. 前端深入之css篇|link和@import到底有什么区别?

    写在前面 在真正的前端开发中,我们很少去写行内样式和内嵌样式,通常都是去引用外部样式. 而在我们学习之初的外部样式表都是用link引入的,但是当后来我们学习的逐渐深入,发现@import也可以引入样式 ...