JAVA实现种子填充算法
种子填充算法原理在网上很多地方都能找到,这篇是继上篇扫描线算法后另一种填充算法,直接上实现代码啦0.0
我的实现只是实现了种子填充算法,但是运行效率不快,如果大佬有改进方法,欢迎和我交流,谢谢!
最后还是贴个截图(先在面板里点击点,鼠标移出面板填充):
package PolygonScanningAndFilling;
public class location {
public int x;
public int y;
}
package PolygonScanningAndFilling; import java.util.ArrayList;
import java.util.Iterator;
import java.util.Stack;
import java.util.Timer;
import java.util.TimerTask;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.io.IOException; public class SeedFulling extends JPanel { static int X0;
static int Y0;
static int X1;
static int Y1;
static int a[]=new int [10]; //保存点击的10个x坐标
static int b[]=new int [10]; //保存点击的10个y坐标
static int index=0;
static int time=0;
static int time2=0;
static boolean add;
ArrayList<Point>allPoint=new ArrayList<Point>();
ArrayList<Point>drawPoint=new ArrayList<Point>();
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
this.addMouseListener(new MouseAdapter() {
public void mouseExited(MouseEvent e) {
time++;
repaint(); }
public void mouseClicked(MouseEvent e) {
allPoint.clear();
if(e.getButton() == e.BUTTON1) {
add=true;
if(index!=0)
{
for(int i=0;i<index;i++)
{
if(a[i]==e.getX()&&b[i]==e.getY())
add=false;
}
}
if(add)
{ a[index]=e.getX();
b[index]=e.getY(); System.out.println("坐标为("+a[index]+","+b[index]+")");
index++; //frame.setVisible(true);
repaint();
System.out.print(time2);
if(time2==0)
time2++;
}
} // if(e.getButton() == e.BUTTON3)
// {
//
// }
} }); Graphics2D g2d = (Graphics2D)g; int Ymax=0;
for(int i=0;i<b.length;i++)
{
if(Ymax<b[i])
Ymax=b[i];
}
// System.out.println("Ymax"+Ymax); /*
* 画出多边形
*/
if(time2!=0)
{ int Sum=0;
for(;Sum<=index;Sum++) {
if(Sum==index-1)
{
drawLine(a[Sum], b[Sum], a[0],b[0],g2d); break;
}
else
{
drawLine(a[Sum], b[Sum], a[Sum+1],b[Sum+1],g2d); } }
}
/*
* 得到边界点
*/ if(time!=0) {
boolean spanNeedFill;
location l=new location();
l.x=a[0]+10;
l.y=b[0]+10;
Stack<location> stack=new Stack<location>(); //将第一个点压入栈
stack.push(l);
int a=0;
while(!stack.empty())
{
a++;
System.out.print("第"+a+"次");
location lo=stack.pop();
int x=lo.x;
int y=lo.y;
if(a>50)
{ System.out.println("开始画上时x"+x);
System.out.println("开始画上时y"+y);
}
// System.out.print("y"+y); while(!allPoint.contains(new Point(x,y))&&!drawPoint.contains(new Point(x,y)))
{
//System.out.print(x);
drawPoint.add(new Point(x,y));
//System.out.println("需画点"+x+","+y);
x++;
} int xr=x-1;
x=lo.x-1;
while(!allPoint.contains(new Point(x,y))&&!drawPoint.contains(new Point(x,y)))
{
drawPoint.add(new Point(x,y));
//System.out.println("需画点"+x+","+y);
//g2d.drawString(".", x,y);
x--;
} int xl=x+1;
//处理上面的扫描线
x=xl;
y=y+1; while(x<=xr) { spanNeedFill=false;
while(!allPoint.contains(new Point(x,y))&&!drawPoint.contains(new Point(x,y)))
{
spanNeedFill=true;
x++; //System.out.println("上扫描线边界为"+x);
}
if(spanNeedFill)
{
//System.out.print("入栈1"); location lc=new location();
lc.x=x-1;
lc.y=y;
stack.push(lc);
//System.out.println("入栈1,此时 x="+lc.x);
//System.out.println("入栈1,此时 y="+lc.y);
spanNeedFill=false; }
while(allPoint.contains(new Point(x,y))||drawPoint.contains(new Point(x,y))&&x<=xr)
x++;
} //下扫描线
x=xl;
y=y-2;
while(x<=xr)
{
spanNeedFill=false;
while(!allPoint.contains(new Point(x,y))&&!drawPoint.contains(new Point(x,y)))
{
spanNeedFill=true;
x++;
}
if(spanNeedFill)
{
//System.out.print("入栈2");
lo.x=x-1;
lo.y=y;
stack.push(lo);
System.out.print("入栈2");
spanNeedFill=false; }
while(allPoint.contains(new Point(x,y))||drawPoint.contains(new Point(x,y))&&x<=xr)
x++; }
}
for(int i=0;i<drawPoint.size();i++)
{
//System.out.println("画的y"+p.y);
Point p=drawPoint.get(i);
System.out.println("画的x"+p.x+"画的y"+p.y);
g2d.drawString(".",p.x,p.y); }
} } private static void createAndShowGUI() {
JFrame frame = new JFrame(); frame.setLocationRelativeTo(null); frame.setLayout(null);
JPanel jp=new JPanel();
frame.setVisible(true); frame.setContentPane(new SeedFulling()); frame.setSize(600, 600);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLocationRelativeTo(null);
frame.setVisible(true);
} public void drawLine(int x0,int y0,int x1,int y1,Graphics2D g) {
int x = x0;
int y = y0; int w = x1 - x0;
int h = y1 - y0; int dx1 = w < 0 ? -1: (w > 0 ? 1 : 0);
int dy1 = h < 0 ? -1: (h > 0 ? 1 : 0); int dx2 = w < 0 ? -1: (w > 0 ? 1 : 0);
int dy2 = 0; int fastStep = Math.abs(w);
int slowStep = Math.abs(h);
if (fastStep <=slowStep) {
fastStep= Math.abs(h);
slowStep= Math.abs(w); dx2= 0;
dy2= h < 0 ? -1 : (h > 0 ? 1 : 0);
}
int numerator = fastStep>> 1; for (int i = 0; i <=fastStep; i++) { g.drawString(".", x, y);
Point p=new Point(x,y);
allPoint.add(p);
numerator+= slowStep;
if (numerator >=fastStep) {
numerator-= fastStep;
x+= dx1;
y+= dy1;
}else {
x+= dx2;
y+= dy2;
}
}
} public static void main(String[] args) throws IOException { createAndShowGUI(); }
}


JAVA实现种子填充算法的更多相关文章
- Atitit Seed-Filling种子填充算法attilax总结
Atitit Seed-Filling种子填充算法attilax总结 种子填充的原理,4联通与8联通区域的选择.. 三个队列 waitProcessPixList tempPixList Proces ...
- 种子填充算法描述及C++代码实现
项目需要看了种子填充算法,改进了算法主要去除面积小的部分.种子填充算法分为两种,简单的和基于扫描线的方法,简单的算法如下描述(笔者针对的是二值图像): (1)从上到下,从左到有,依次扫描每个像素: ( ...
- openGL实现图形学扫描线种子填充算法
title: "openGL实现图形学扫描线种子填充算法" date: 2018-06-11T19:41:30+08:00 tags: ["图形学"] cate ...
- CGA填充算法之种子填充算法
CGA填充算法之种子填充算法 平面区域填充算法是计算机图形学领域的一个很重要的算法,区域填充即给出一个区域的边界 (也可以是没有边界,只是给出指定颜色),要求将边界范围内的所有象素单元都修改成指定的颜 ...
- UVA 572 -- Oil Deposits(DFS求连通块+种子填充算法)
UVA 572 -- Oil Deposits(DFS求连通块) 图也有DFS和BFS遍历,由于DFS更好写,所以一般用DFS寻找连通块. 下述代码用一个二重循环来找到当前格子的相邻8个格子,也可用常 ...
- [计算机图形学] 基于C#窗口的Bresenham直线扫描算法、种子填充法、扫描线填充法模拟软件设计(二)
上一节链接:http://www.cnblogs.com/zjutlitao/p/4116783.html 前言: 在上一节中我们已经大致介绍了该软件的是什么.可以干什么以及界面的大致样子.此外还详细 ...
- Open gl 的不规则图形的4联通种子递归填充和扫描线种子递归填充算法实现
实验题目:不规则区域的填充算法 实验目的:验证不规则区域的填充算法 实验内容:利用VC与OpenGL,实现不规则区域的填充算法. 1.必做:实现简单递归的不规则区域填充算法. 2.选做:针对简单递归算 ...
- [OpenGL] 不规则区域的填充算法
不规则区域的填充算法 一.简单递归 利用Dfs实现简单递归填充. 核心代码: // 简单深度搜索填充 (四连通) void DfsFill(int x, int y) { || y < || x ...
- 图像处理之泛洪填充算法(Flood Fill Algorithm)
泛洪填充算法(Flood Fill Algorithm) 泛洪填充算法又称洪水填充算法是在很多图形绘制软件中常用的填充算法,最熟悉不过就是 windows paint的油漆桶功能.算法的原理很简单,就 ...
随机推荐
- windows 下的Python虚拟环境(vitrualen)pycharm创建Django项目
问题:MySQL Strict Mode is not set for database connection 'default' 初学Django遇到问题-MySQL Strict Mode is ...
- springIoC注解
一.通过注解注入Bean @Component:组件(spring扫描包下有该注解的类) @ComponentScan(包名):组件扫描(spring扫描该包名下的类) @Configuration: ...
- Laya微信小游戏本地缓存
测试版本2.1.1.1 查看bin/libs/laya.wxmini.js. 发现只会缓存png,jpg. 声音和atlas,json不会缓存. 对比白鹭,白鹭是将png,jpg,atlas,json ...
- 数据标记系列——图像分割 & Curve-GCN
在之前的文章中(参考:),我们提到了Polygon-RNN++在数据标注中的应用.今天不得不提到多伦多大学与英伟达联合公布的一项最新研究:Curve-GCN的应用结果显示图像标注速度提升10倍. Cu ...
- MySQL 8中使用全文检索示例
首先建议张册测试用的表test,并使用fulltext说明将title和body两列的数据加入全文检索的索引列中: drop table if exists test; create table te ...
- MYSQL 递归操作
MYSQL 递归? ===================== 表: t_node node_id int node_name varchar2(45) parent_id int 级, ...
- [OpenCV开发]OpenCV图像编码和解码 imencode和imdecode使用,用于网络传输图片
在很多应用中,经常会直接把图片的二进制数据进行交换,比如说利用 socket 通信传送图片二进制数据,或者直接用内存数据库(例如 Redis)来传递图片二进制数据. 这个时候,当你的应用程序读到内存里 ...
- Python赋值、浅拷贝、深拷贝
一.赋值(assignment) >>> a = [1, 2, 3] >>> b = a >>> print(id(a), id(b), sep= ...
- c# 无法加载DLL:找不到指定的模块(异常来自HRESULT:0X8007007E)
c# 无法加载DLL“xxxx”:找不到指定的模块(异常来自HRESULT:0X8007007E)的一个解决方法 以前的一个c#项目,今天运行的时候突然发现调用DLL时出现了下面的错误. 心中很诧异, ...
- mysql数据库表的查询
一. 设有一数据库,包括四个表:学生表(Student).课程表(Course).成绩表(Score)以及教师信息表(Teacher).四个表的结构分别如表1-1的表(一)~表( ...