1
2
3
4
5
6
7
8
9
10
11 package edu.uci.ics.jung.visualization;
12
13 import java.awt.Graphics;
14 import java.awt.Graphics2D;
15 import java.awt.Image;
16 import java.awt.Shape;
17 import java.awt.geom.AffineTransform;
18 import java.awt.geom.GeneralPath;
19 import java.awt.geom.Line2D;
20 import java.awt.geom.Point2D;
21 import java.awt.image.BufferedImage;
22 import java.io.IOException;
23
24 import javax.imageio.ImageIO;
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41 public class PivotingImageShaper {
42
43
44
45
46
47 static int sample = 1;
48
49
50
51
52 static int firstx = 0;
53
54 public static Shape getShape(String fileName) {
55 return getShape(fileName, Integer.MAX_VALUE);
56 }
57 public static Shape getShape(String fileName, int max) {
58 BufferedImage image = null;
59 try {
60 image = ImageIO.read(FourPassImageShaper.class.getResource(fileName));
61 } catch(IOException ex) {
62 ex.printStackTrace();
63 }
64 return getShape(image, max);
65 }
66
67
68
69
70
71
72
73 public static Shape getShape(Image image) {
74 return getShape(image, Integer.MAX_VALUE);
75 }
76 public static Shape getShape(Image image, int max) {
77 BufferedImage bi =
78 new BufferedImage(image.getWidth(null), image.getHeight(null),
79 BufferedImage.TYPE_INT_ARGB);
80 Graphics g = bi.createGraphics();
81 g.drawImage(image, 0, 0, null);
82 g.dispose();
83 return getShape(bi, max);
84 }
85
86
87
88
89
90
91
92 public static Shape getShape(BufferedImage image, int max) {
93
94 float width = image.getWidth();
95 float height = image.getHeight();
96 if(width > max || height > max) {
97 BufferedImage smaller =
98 new BufferedImage(max, max, BufferedImage.TYPE_INT_ARGB);
99 Graphics g = smaller.createGraphics();
100 AffineTransform at = AffineTransform.getScaleInstance(max/width,max/height);
101 AffineTransform back = AffineTransform.getScaleInstance(width/max,height/max);
102 Graphics2D g2 = (Graphics2D)g;
103 g2.drawImage(image, at, null);
104 g2.dispose();
105 return back.createTransformedShape(getShape(smaller));
106 } else {
107 return getShape(image);
108 }
109 }
110
111
112
113
114
115
116
117 public static Shape getShape(BufferedImage image) {
118 firstx = 0;
119 return leftEdge(image, new GeneralPath());
120 }
121
122 private static Point2D detectLine(Point2D p1, Point2D p2, Point2D p,
123 Line2D line, GeneralPath path) {
124 if(p2 == null) {
125 p2 = p;
126 line.setLine(p1,p2);
127 }
128
129 else if(line.ptLineDistSq(p) < 1) {
130
131 p2.setLocation(p);
132 } else {
133 p1.setLocation(p2);
134 p2.setLocation(p);
135 line.setLine(p1,p2);
136 path.lineTo((float)p1.getX(), (float)p1.getY());
137 }
138 return p2;
139 }
140
141
142
143
144
145
146 private static Shape leftEdge(BufferedImage image, GeneralPath path) {
147 int lastj = 0;
148 Point2D p1 = null;
149 Point2D p2 = null;
150 Line2D line = new Line2D.Float();
151 for(int i=0; i<image.getHeight(); i+=sample) {
152 boolean aPointExistsOnThisLine = false;
153
154 for(int j=0; j<image.getWidth(); j+=sample) {
155 if((image.getRGB(j,i) & 0xff000000) != 0) {
156
157 Point2D p = new Point2D.Float(j,i);
158 aPointExistsOnThisLine = true;
159 if(path.getCurrentPoint() != null) {
160
161 p2 = detectLine(p1,p2,p,line,path);
162 } else {
163
164 path.moveTo(j,i);
165 firstx = j;
166 p1 = p;
167 }
168 lastj = j;
169 break;
170 }
171 }
172 if(aPointExistsOnThisLine == false) {
173 break;
174 }
175 }
176 return bottomEdge(image, path, lastj);
177 }
178
179
180
181
182
183
184
185
186 private static Shape bottomEdge(BufferedImage image, GeneralPath path, int start) {
187 int lastj = 0;
188 Point2D p1 = path.getCurrentPoint();
189 Point2D p2 = null;
190 Line2D line = new Line2D.Float();
191 for(int i=start; i<image.getWidth(); i+=sample) {
192 boolean aPointExistsOnThisLine = false;
193 for(int j=image.getHeight()-1; j>=0; j-=sample) {
194 if((image.getRGB(i,j) & 0xff000000) != 0) {
195
196 Point2D p = new Point2D.Float(i,j);
197 aPointExistsOnThisLine = true;
198 p2 = detectLine(p1,p2,p,line,path);
199 lastj = j;
200 break;
201 }
202 }
203 if(aPointExistsOnThisLine == false) {
204 break;
205 }
206 }
207 return rightEdge(image, path, lastj);
208 }
209
210
211
212
213
214
215
216
217 private static Shape rightEdge(BufferedImage image, GeneralPath path, int start) {
218 int lastj = 0;
219 Point2D p1 = path.getCurrentPoint();
220 Point2D p2 = null;
221 Line2D line = new Line2D.Float();
222 for(int i=start; i>=0; i-=sample) {
223 boolean aPointExistsOnThisLine = false;
224
225 for(int j=image.getWidth()-1; j>=0; j-=sample) {
226 if((image.getRGB(j,i) & 0xff000000) != 0) {
227
228 Point2D p = new Point2D.Float(j,i);
229 aPointExistsOnThisLine = true;
230 p2 = detectLine(p1,p2,p,line,path);
231 lastj=j;
232 break;
233 }
234 }
235 if(aPointExistsOnThisLine == false) {
236 break;
237 }
238 }
239 return topEdge(image, path, lastj);
240 }
241
242
243
244
245
246
247
248
249 private static Shape topEdge(BufferedImage image, GeneralPath path, int start) {
250 Point2D p1 = path.getCurrentPoint();
251 Point2D p2 = null;
252 Line2D line = new Line2D.Float();
253 for(int i=start; i>=firstx; i-=sample) {
254 boolean aPointExistsOnThisLine = false;
255 for(int j=0; j<image.getHeight(); j+=sample) {
256 if((image.getRGB(i,j) & 0xff000000) != 0) {
257
258 Point2D p = new Point2D.Float(i,j);
259 aPointExistsOnThisLine = true;
260 p2 = detectLine(p1,p2,p,line,path);
261 break;
262 }
263 }
264 if(aPointExistsOnThisLine == false) {
265 break;
266 }
267 }
268 path.closePath();
269 return path;
270 }
271 }