EMMA Coverage Report (generated Sat Oct 08 11:41:37 CEST 2011)
[all classes][com.jhlabs.image]

COVERAGE SUMMARY FOR SOURCE FILE [ConvolveFilter.java]

nameclass, %method, %block, %line, %
ConvolveFilter.java0%   (0/1)0%   (0/20)0%   (0/842)0%   (0/162)

COVERAGE BREAKDOWN BY CLASS AND METHOD

nameclass, %method, %block, %line, %
     
class ConvolveFilter0%   (0/1)0%   (0/20)0%   (0/842)0%   (0/162)
ConvolveFilter (): void 0%   (0/1)0%   (0/5)0%   (0/2)
ConvolveFilter (Kernel): void 0%   (0/1)0%   (0/12)0%   (0/5)
ConvolveFilter (float []): void 0%   (0/1)0%   (0/9)0%   (0/2)
ConvolveFilter (int, int, float []): void 0%   (0/1)0%   (0/9)0%   (0/2)
convolve (Kernel, int [], int [], int, int, boolean, int): void 0%   (0/1)0%   (0/35)0%   (0/6)
convolve (Kernel, int [], int [], int, int, int): void 0%   (0/1)0%   (0/9)0%   (0/2)
convolveH (Kernel, int [], int [], int, int, boolean, int): void 0%   (0/1)0%   (0/199)0%   (0/37)
convolveHV (Kernel, int [], int [], int, int, boolean, int): void 0%   (0/1)0%   (0/233)0%   (0/41)
convolveV (Kernel, int [], int [], int, int, boolean, int): void 0%   (0/1)0%   (0/214)0%   (0/38)
createCompatibleDestImage (BufferedImage, ColorModel): BufferedImage 0%   (0/1)0%   (0/19)0%   (0/3)
filter (BufferedImage, BufferedImage): BufferedImage 0%   (0/1)0%   (0/53)0%   (0/10)
getBounds2D (BufferedImage): Rectangle2D 0%   (0/1)0%   (0/10)0%   (0/1)
getEdgeAction (): int 0%   (0/1)0%   (0/3)0%   (0/1)
getKernel (): Kernel 0%   (0/1)0%   (0/3)0%   (0/1)
getPoint2D (Point2D, Point2D): Point2D 0%   (0/1)0%   (0/14)0%   (0/4)
getRenderingHints (): RenderingHints 0%   (0/1)0%   (0/2)0%   (0/1)
hasAlpha (): boolean 0%   (0/1)0%   (0/3)0%   (0/1)
setEdgeAction (int): void 0%   (0/1)0%   (0/4)0%   (0/2)
setKernel (Kernel): void 0%   (0/1)0%   (0/4)0%   (0/2)
toString (): String 0%   (0/1)0%   (0/2)0%   (0/1)

1// Copyright 2005 Huxtable.com. All rights reserved.
2// For more information, see <http://www.jhlabs.com/ip/blurring.html>.
3package com.jhlabs.image;
4 
5import java.awt.Rectangle;
6import java.awt.RenderingHints;
7import java.awt.geom.Point2D;
8import java.awt.geom.Rectangle2D;
9import java.awt.image.BufferedImage;
10import java.awt.image.ColorModel;
11import java.awt.image.Kernel;
12 
13/**
14 *  A filter which applies a convolution kernel to an image.
15 *
16 * @author    Jerry Huxtable
17 */
18public class ConvolveFilter extends AbstractBufferedImageOp
19{
20    public static final int CLAMP_EDGES = 1;
21    public static final int WRAP_EDGES = 2;
22    public static final int ZERO_EDGES = 0;
23    static final long serialVersionUID = 2239251672685254626L;
24 
25    private boolean alpha = true;
26    private int edgeAction = CLAMP_EDGES;
27    private Kernel kernel;
28 
29    /**
30     *  Construct a filter with a null kernel. This is only useful if you're going to change the
31     *  kernel later on.
32     */
33    public ConvolveFilter() {
34        this(new float[9]);
35    }
36 
37    /**
38     *  Construct a filter with the given 3x3 kernel.
39     *
40     * @param  matrix  an array of 9 floats containing the kernel
41     */
42    public ConvolveFilter(float[] matrix) {
43        this(new Kernel(3, 3, matrix));
44    }
45 
46    /**
47     *  Construct a filter with the given kernel.
48     *
49     * @param  rows    the number of rows in the kernel
50     * @param  cols    the number of columns in the kernel
51     * @param  matrix  an array of rows*cols floats containing the kernel
52     */
53    public ConvolveFilter(int rows, int cols, float[] matrix) {
54        this(new Kernel(cols, rows, matrix));
55    }
56 
57    /**
58     *  Construct a filter with the given 3x3 kernel.
59     *
60     * @param  kernel  Description of the parameter
61     */
62    public ConvolveFilter(Kernel kernel) {
63        this.kernel = kernel;
64    }
65 
66    public void setEdgeAction(int edgeAction) {
67        this.edgeAction = edgeAction;
68    }
69 
70    public void setKernel(Kernel kernel) {
71        this.kernel = kernel;
72    }
73 
74    public Rectangle2D getBounds2D(BufferedImage src) {
75        return new Rectangle(0, 0, src.getWidth(), src.getHeight());
76    }
77 
78    public int getEdgeAction() {
79        return edgeAction;
80    }
81 
82    public Kernel getKernel() {
83        return kernel;
84    }
85 
86    public Point2D getPoint2D(Point2D srcPt, Point2D dstPt) {
87        if (dstPt == null) {
88            dstPt = new Point2D.Double();
89        }
90        dstPt.setLocation(srcPt.getX(), srcPt.getY());
91        return dstPt;
92    }
93 
94    public RenderingHints getRenderingHints() {
95        return null;
96    }
97 
98    public static void convolve(Kernel kernel, int[] inPixels, int[] outPixels, int width, int height, int edgeAction) {
99        convolve(kernel, inPixels, outPixels, width, height, true, edgeAction);
100    }
101 
102    public static void convolve(Kernel kernel, int[] inPixels, int[] outPixels, int width, int height, boolean alpha,
103            int edgeAction) {
104        if (kernel.getHeight() == 1) {
105            convolveH(kernel, inPixels, outPixels, width, height, alpha, edgeAction);
106        } else if (kernel.getWidth() == 1) {
107            convolveV(kernel, inPixels, outPixels, width, height, alpha, edgeAction);
108        } else {
109            convolveHV(kernel, inPixels, outPixels, width, height, alpha, edgeAction);
110        }
111    }
112 
113    /**
114     *  Convolve with a kernel consisting of one row.
115     */
116    public static void convolveH(Kernel kernel, int[] inPixels, int[] outPixels, int width, int height,
117            boolean alpha, int edgeAction) {
118        int index = 0;
119        float[] matrix = kernel.getKernelData(null);
120        int cols = kernel.getWidth();
121        int cols2 = cols / 2;
122 
123        for (int y = 0; y < height; y++) {
124            int ioffset = y * width;
125 
126            for (int x = 0; x < width; x++) {
127                float r = 0;
128                float g = 0;
129                float b = 0;
130                float a = 0;
131                int moffset = cols2;
132 
133                for (int col = -cols2; col <= cols2; col++) {
134                    float f = matrix[moffset + col];
135 
136                    if (f != 0) {
137                        int ix = x + col;
138 
139                        if (ix < 0) {
140                            if (edgeAction == CLAMP_EDGES) {
141                                ix = 0;
142                            } else if (edgeAction == WRAP_EDGES) {
143                                ix = (x + width) % width;
144                            }
145                        } else if (ix >= width) {
146                            if (edgeAction == CLAMP_EDGES) {
147                                ix = width - 1;
148                            } else if (edgeAction == WRAP_EDGES) {
149                                ix = (x + width) % width;
150                            }
151                        }
152                        int rgb = inPixels[ioffset + ix];
153 
154                        a += f * ((rgb >> 24) & 0xff);
155                        r += f * ((rgb >> 16) & 0xff);
156                        g += f * ((rgb >> 8) & 0xff);
157                        b += f * (rgb & 0xff);
158                    }
159                }
160 
161                int ia = alpha ? ImageMath.clamp((int) (a + 0.5)) : 0xff;
162                int ir = ImageMath.clamp((int) (r + 0.5));
163                int ig = ImageMath.clamp((int) (g + 0.5));
164                int ib = ImageMath.clamp((int) (b + 0.5));
165 
166                outPixels[index++] = (ia << 24) | (ir << 16) | (ig << 8) | ib;
167            }
168        }
169    }
170 
171    /**
172     *  Convolve with a 2D kernel.
173     */
174    public static void convolveHV(Kernel kernel, int[] inPixels, int[] outPixels, int width, int height,
175            boolean alpha, int edgeAction) {
176        int index = 0;
177        float[] matrix = kernel.getKernelData(null);
178        int rows = kernel.getHeight();
179        int cols = kernel.getWidth();
180        int rows2 = rows / 2;
181        int cols2 = cols / 2;
182 
183        for (int y = 0; y < height; y++) {
184            for (int x = 0; x < width; x++) {
185                float r = 0;
186                float g = 0;
187                float b = 0;
188                float a = 0;
189 
190                for (int row = -rows2; row <= rows2; row++) {
191                    int iy = y + row;
192                    int ioffset;
193 
194                    if (0 <= iy && iy < height) {
195                        ioffset = iy * width;
196                    } else if (edgeAction == CLAMP_EDGES) {
197                        ioffset = y * width;
198                    } else if (edgeAction == WRAP_EDGES) {
199                        ioffset = ((iy + height) % height) * width;
200                    } else {
201                        continue;
202                    }
203 
204                    int moffset = cols * (row + rows2) + cols2;
205 
206                    for (int col = -cols2; col <= cols2; col++) {
207                        float f = matrix[moffset + col];
208 
209                        if (f != 0) {
210                            int ix = x + col;
211 
212                            if (!(0 <= ix && ix < width)) {
213                                if (edgeAction == CLAMP_EDGES) {
214                                    ix = x;
215                                } else if (edgeAction == WRAP_EDGES) {
216                                    ix = (x + width) % width;
217                                } else {
218                                    continue;
219                                }
220                            }
221                            int rgb = inPixels[ioffset + ix];
222 
223                            a += f * ((rgb >> 24) & 0xff);
224                            r += f * ((rgb >> 16) & 0xff);
225                            g += f * ((rgb >> 8) & 0xff);
226                            b += f * (rgb & 0xff);
227                        }
228                    }
229                }
230 
231                int ia = alpha ? ImageMath.clamp((int) (a + 0.5)) : 0xff;
232                int ir = ImageMath.clamp((int) (r + 0.5));
233                int ig = ImageMath.clamp((int) (g + 0.5));
234                int ib = ImageMath.clamp((int) (b + 0.5));
235 
236                outPixels[index++] = (ia << 24) | (ir << 16) | (ig << 8) | ib;
237            }
238        }
239    }
240 
241    /**
242     *  Convolve with a kernel consisting of one column.
243     */
244    public static void convolveV(Kernel kernel, int[] inPixels, int[] outPixels, int width, int height,
245            boolean alpha, int edgeAction) {
246        int index = 0;
247        float[] matrix = kernel.getKernelData(null);
248        int rows = kernel.getHeight();
249        int rows2 = rows / 2;
250 
251        for (int y = 0; y < height; y++) {
252            for (int x = 0; x < width; x++) {
253                float r = 0;
254                float g = 0;
255                float b = 0;
256                float a = 0;
257 
258                for (int row = -rows2; row <= rows2; row++) {
259                    int iy = y + row;
260                    int ioffset;
261 
262                    if (iy < 0) {
263                        if (edgeAction == CLAMP_EDGES) {
264                            ioffset = 0;
265                        } else if (edgeAction == WRAP_EDGES) {
266                            ioffset = ((y + height) % height) * width;
267                        } else {
268                            ioffset = iy * width;
269                        }
270                    } else if (iy >= height) {
271                        if (edgeAction == CLAMP_EDGES) {
272                            ioffset = (height - 1) * width;
273                        } else if (edgeAction == WRAP_EDGES) {
274                            ioffset = ((y + height) % height) * width;
275                        } else {
276                            ioffset = iy * width;
277                        }
278                    } else {
279                        ioffset = iy * width;
280                    }
281 
282                    float f = matrix[row + rows2];
283 
284                    if (f != 0) {
285                        int rgb = inPixels[ioffset + x];
286 
287                        a += f * ((rgb >> 24) & 0xff);
288                        r += f * ((rgb >> 16) & 0xff);
289                        g += f * ((rgb >> 8) & 0xff);
290                        b += f * (rgb & 0xff);
291                    }
292                }
293 
294                int ia = alpha ? ImageMath.clamp((int) (a + 0.5)) : 0xff;
295                int ir = ImageMath.clamp((int) (r + 0.5));
296                int ig = ImageMath.clamp((int) (g + 0.5));
297                int ib = ImageMath.clamp((int) (b + 0.5));
298 
299                outPixels[index++] = (ia << 24) | (ir << 16) | (ig << 8) | ib;
300            }
301        }
302    }
303 
304    public BufferedImage createCompatibleDestImage(BufferedImage src, ColorModel dstCM) {
305        if (dstCM == null) {
306            dstCM = src.getColorModel();
307        }
308        return new BufferedImage(
309                dstCM,
310                dstCM.createCompatibleWritableRaster(src.getWidth(), src.getHeight()),
311                dstCM.isAlphaPremultiplied(),
312                null);
313    }
314 
315    public BufferedImage filter(BufferedImage src, BufferedImage dst) {
316        int width = src.getWidth();
317        int height = src.getHeight();
318 
319        if (dst == null) {
320            dst = createCompatibleDestImage(src, null);
321        }
322 
323        int[] inPixels = new int[width * height];
324        int[] outPixels = new int[width * height];
325 
326        getRGB(src, 0, 0, width, height, inPixels);
327 
328        convolve(kernel, inPixels, outPixels, width, height, alpha, edgeAction);
329 
330        setRGB(dst, 0, 0, width, height, outPixels);
331        return dst;
332    }
333 
334    public boolean hasAlpha() {
335        return alpha;
336    }
337 
338    public String toString() {
339        return "Blur/Convolve...";
340    }
341}

[all classes][com.jhlabs.image]
EMMA 2.0.4217 (C) Vladimir Roubtsov