Java基于OpenCV实现走迷宫(图片+路线展示)

由于疫情,待在家中,太过无聊。同学发了我张迷宫图片,让我走迷宫来缓解暴躁,于是乎就码了一个程序出来。特此记录。

原图:

这张图,由于不是非常清晰,所以我们要进行处理。首先转换为灰度图:

public static Mat RGB2Gray(Mat image) {
// Gray = R*0.299 + G*0.587 + B*0.114
Mat gray = new Mat();
Imgproc.cvtColor(image, gray, Imgproc.COLOR_BGR2GRAY);
return gray;
}

主要思路:

  • 转换为灰度图
  • 设置Threshold来区分黑白点,转换为黑白图
  • 规定起点、终点
  • 处理图像,封住边框,这样就不会从外边框走
  • 使用bfs算法来求解走迷宫的最短路径,并通过记录上一个节点嵌套的方式记录下路径
  • 渲染在图片上,输出

代码:

package edu.sfls.Jeff.JavaDev.Maze;

import edu.sfls.Jeff.JavaDev.CVLib.SmartConverter;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.highgui.HighGui;
import org.opencv.imgcodecs.Imgcodecs; import java.util.LinkedList;
import java.util.Queue; public class SolveMaze { public static void main(String[] args) throws InterruptedException {
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
Mat src_maze = Imgcodecs.imread("src/IMG_2679.JPG");
HighGui.imshow("src_maze", src_maze);
Mat pre_maze = SmartConverter.RGB2Gray(src_maze);
Mat color_maze = src_maze.clone();
for (int i = 0; i < pre_maze.rows(); i ++)
for (int j = 0; j < pre_maze.cols(); j ++)
if (pre_maze.get(i, j)[0] < 100)
color_maze.put(i, j, 0, 0, 0);
else
color_maze.put(i, j, 255, 255, 255);
for (int i = 0; i < pre_maze.rows(); i ++)
for (int j = 0; j < 32; j ++)
color_maze.put(i, color_maze.cols() - j - 1, 0, 255, 0);
Point startPoint = new Point(color_maze.cols() - 32 - 1 - 2, 347 + 5 - 1);
Point endPoint = new Point(17, 351);
color_maze.put(startPoint.y, startPoint.x, 0, 0, 255); boolean[][] vis = new boolean[1078][702];
for (int i = 0; i < 1078; i ++)
for (int j = 0; j < 702; j ++)
vis[i][j] = false;
vis[startPoint.x][startPoint.y] = true; Point successPoint = new Point(17, 351); Queue<Point> queue = new LinkedList<>();
queue.offer(startPoint);
while (!queue.isEmpty()) {
Point p = queue.poll();
System.out.println(p.x + " " + p.y);
vis[p.x][p.y] = true;
if (p.x == endPoint.x && p.y == endPoint.y) {
System.out.println("success");
successPoint = p;
break;
}
if (p.x - 1 >= 0)
if (!vis[p.x - 1][p.y] && color_maze.get(p.y, p.x - 1)[0] == 255) {
queue.offer(new Point(p.x - 1, p.y, p));
vis[p.x - 1][p.y] = true;
}
if (p.y - 1 >= 0)
if (!vis[p.x][p.y - 1] && color_maze.get(p.y - 1, p.x)[0] == 255) {
queue.offer(new Point(p.x, p.y - 1, p));
vis[p.x][p.y - 1] = true;
}
if (p.x + 1 < 1078)
if (!vis[p.x + 1][p.y] && color_maze.get(p.y, p.x + 1)[0] == 255) {
queue.offer(new Point(p.x + 1, p.y, p));
vis[p.x + 1][p.y] = true;
}
if (p.y + 1 < 702)
if (!vis[p.x][p.y + 1] && color_maze.get(p.y + 1, p.x)[0] == 255) {
queue.offer(new Point(p.x, p.y + 1, p));
vis[p.x][p.y + 1] = true;
}
} System.out.println("out"); Point pre = successPoint.pre;
color_maze.put(pre.y, pre.x, 0, 0, 255);
while (pre.pre != null) {
pre = pre.pre;
color_maze.put(pre.y, pre.x, 0, 0, 255);
} HighGui.imshow("color", color_maze);
HighGui.waitKey(0);
} } class Point { int x, y; Point pre; Point(int x, int y) {
this.x = x;
this.y = y;
} Point(int x, int y, Point pre) {
this.x = x;
this.y = y;
this.pre = pre;
}
}

结果:

Java基于OpenCV实现走迷宫(图片+路线展示)的更多相关文章

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

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

  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. Java基于opencv实现图像数字识别(一)

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

  7. Java基于opencv—矫正图像

    更多的时候,我们得到的图像不可能是正的,多少都会有一定的倾斜,就比如下面的 我们要做的就是把它们变成下面这样的 我们采用的是寻找轮廓的思路,来矫正图片:只要有明显的轮廓都可以采用这种思路 具体思路: ...

  8. Java基于opencv—归一化

    Opencv中提供了resize函数,可以把图像调整到相同大小 Java中resize函数的声明,内部调用的都是native方法 public static void resize(Mat src, ...

  9. java基于OpenCV的人脸识别

    基于Java简单的人脸和人眼识别程序 使用这个程序之前必须先安装配置OpenCV详细教程见:https://www.cnblogs.com/prodigal-son/p/12768948.html 注 ...

随机推荐

  1. 第二阶段:2.商业需求分析及BRD:5.商业需求文档1

    三大文档 FSD一般包含在PRD 1.BRD一般是去向决策层汇报 2.产品介绍的各项是可选的 不是必备的 产品线路图就是roodmap.团队一般是偏技术的团队. BRD案例. 痛点.定性的描述.不会非 ...

  2. 聊聊最近撸Spring源码感悟

    一.前言     最近一段时间撸了Spring IOC.AOP.Transactional源码,这篇文章聊聊我写了哪些小玩意,这可能就是阅读源码以后最大收获.希望大家在里面能学习一些什么东西吧: 二. ...

  3. 怎么彻底删除用友通T3财务软件?

    [问题现象]怎么彻底删除用友通T3财务软件? [原因分析]通过"添加或删除程序"无法正常卸载用友通T3,也尝试了360安全卫士强力卸载,都无法完全卸载,有没有办法可以彻底删除用友通 ...

  4. JavaScript中浅拷贝和深拷贝的区别

    JavaScript数据类型 基础数据类型:保存在栈内存中的简单数据段 ,有undefined,boolean,number,string,null 引用数据类型:Array,object,Funct ...

  5. $tarjan$简要学习笔记

    $QwQ$因为$gql$的$tarjan$一直很差所以一直想着要写个学习笔记,,,咕了$inf$天之后终于还是写了嘻嘻. 首先说下几个重要数组的基本定义. $dfn$太简单了不说$QwQ$ 但是因为有 ...

  6. 子网划分及NAT技术总结

    近段项目需要用到网络相关的知识,硬着头皮又回顾了一波,这里做一下记录. 一 分类的IP地址 我们使用的IP地址(IP V4)可以划分为A,B,C,D,E 5个类型,其中的D,为组播地址,E类地址为保留 ...

  7. 「BZOJ1385」「Baltic2000」Division expression 解题报告

    Division expression Description 除法表达式有如下的形式: \(X_1/X_2/X_3.../X_k\) 其中Xi是正整数且\(X_i \le 1000000000(1 ...

  8. C Primer Plus(二)

    重读C Primer Plus ,查漏补缺 重读C Primer Plus,记录遗漏的.未掌握的.不清楚的知识点 分支和跳转 1.ctype.h头文件里包含了一些列用于字符判断的函数,包括判断数字.大 ...

  9. 调试排错 - Java问题排查:Linux命令

    本文原创,更多内容可以参考: Java 全栈知识体系.如需转载请说明原处. Java 在线问题排查主要分两篇:本文是第一篇,通过linux常用命令排查.@pdai 文本操作 文本查找 - grep g ...

  10. Session是怎么实现的?存储在哪里?

    为什么有session? 首先大家知道,http协议是无状态的,即你连续访问某个网页100次和访问1次对服务器来说是没有区别对待的,因为它记不住你. 那么,在一些场合,确实需要服务器记住当前用户怎么办 ...