diff --git a/.idea/ImgJava.iml b/.idea/ImgJava.iml index d6ebd48..28f496d 100644 --- a/.idea/ImgJava.iml +++ b/.idea/ImgJava.iml @@ -1,8 +1,11 @@ - + - + + + + diff --git a/.idea/misc.xml b/.idea/misc.xml index 8fcbe9d..1c80b4e 100644 --- a/.idea/misc.xml +++ b/.idea/misc.xml @@ -1,5 +1,8 @@ + + + \ No newline at end of file diff --git a/run/moscov.png b/run/moscov.png index ff9ddd7..29f3714 100644 Binary files a/run/moscov.png and b/run/moscov.png differ diff --git a/src/main/java/io/gitlab/jfronny/ImgJava/Main.java b/src/main/java/io/gitlab/jfronny/ImgJava/Main.java index 9097878..a03b5dd 100644 --- a/src/main/java/io/gitlab/jfronny/ImgJava/Main.java +++ b/src/main/java/io/gitlab/jfronny/ImgJava/Main.java @@ -25,7 +25,7 @@ public class Main { pict = stackViewer.push(ImageUtil.rotate(pict, ImageUtil.RotateMode.Right)); pict = stackViewer.push(ImageUtil.mirror(pict, ImageUtil.MirrorMode.Vertical)); //pict = stackViewer.push(ImageUtil.blurBox(pict, 10)); - pict = stackViewer.push(ImageUtil.blurGauss(pict, 3)); + pict = stackViewer.push(ImageUtil.blurGauss(pict, 3, 2)); pict = stackViewer.push(ImageUtil.sharpen(pict, 3)); pict.save(run.resolve("moscov.png")); stackViewer.repaint(); diff --git a/src/main/java/io/gitlab/jfronny/ImgJava/imageProcessing/ImageUtil.java b/src/main/java/io/gitlab/jfronny/ImgJava/imageProcessing/ImageUtil.java index f235ddd..d669c7a 100644 --- a/src/main/java/io/gitlab/jfronny/ImgJava/imageProcessing/ImageUtil.java +++ b/src/main/java/io/gitlab/jfronny/ImgJava/imageProcessing/ImageUtil.java @@ -77,78 +77,25 @@ public class ImageUtil { public static Picture blurBox(Picture picture, int amount) { - int w = picture.getWidth(); - int h = picture.getHeight(); - - Color[][] pixel; - Color[][] pixelNeu = picture.getPixelArray(); - - for (int i = 0; i < amount; i++) { - pixel = pixelNeu; - pixelNeu = new Color[w][h]; - for (int x = 0; x < w; x++) { - for (int y = 0; y < h; y++) { - if (x < 1 || y < 1 || x + 1 >= w || y + 1 >= h) { - pixelNeu[x][y] = pixel[x][y]; - continue; - } - pixelNeu[x][y] = pixel[x][y]; - //p p p - //p 0 p - //p p p - MColor sum = new MColor(pixel[x - 1][y + 1]) - .add(pixel[x + 0][y + 1]) - .add(pixel[x + 1][y + 1]) - .add(pixel[x - 1][y + 0]) - .add(pixel[x + 0][y + 0]) - .add(pixel[x + 1][y + 0]) - .add(pixel[x - 1][y - 1]) - .add(pixel[x + 0][y - 1]) - .add(pixel[x + 1][y - 1]); - - pixelNeu[x][y] = sum.div(9).get(); - } - } - } - - picture.setPixelArray(pixelNeu); - return picture; + return applyMatrix(picture, new double[][]{ + new double[] {1, 1, 1}, + new double[] {1, 1, 1}, + new double[] {1, 1, 1} + }, amount); } - public static Picture blurGauss(Picture picture, int radius) { - int w = picture.getWidth(); - int h = picture.getHeight(); - - Color[][] pixel = picture.getPixelArray(); - Color[][] pixelNeu = new Color[w][h]; - + public static Picture blurGauss(Picture picture, int radius, int amount) { double sigma = radius / 2d; - - for (int x = 0; x < w; x++) { - for (int y = 0; y < h; y++) { - - pixelNeu[x][y] = pixel[x][y]; - - MColor sum = new MColor(); - - double gSum = 0; - - for (int dx = -radius; dx <= radius; dx++) { - for (int dy = -radius; dy <= radius; dy++) { - if (x + dx >= 0 && y + dy >= 0 && x + dx < w && y + dy < h) { - double g = gauss(dx, dy, sigma); - gSum += g; - sum.addM(pixel[x + dx][y + dy], g); - } - } - } - - pixelNeu[x][y] = sum.div(gSum).get(); + int bl = radius * 2 + 1; + double[][] matrix = new double[bl][bl]; + + for (int x = 0; x < bl; x++) { + for (int y = 0; y < bl; y++) { + matrix[x][y] = gauss(x - radius, y - radius, sigma); } } - picture.setPixelArray(pixelNeu); - return picture; + return applyMatrix(picture, matrix, amount); } private static double gauss(double dX, double dY, double stDev) { @@ -156,32 +103,52 @@ public class ImageUtil { } public static Picture sharpen(Picture picture, int amount) { + return applyMatrix(picture, new double[][]{ + new double[] {0, -1, 0}, + new double[] {-1, 5, -1}, + new double[] {0, -1, 0} + }, amount); + } + + public static Picture applyMatrix(Picture picture, double[][] matrix, int amount) { int w = picture.getWidth(); int h = picture.getHeight(); + int mW = matrix.length; + int mH = matrix[0].length; + if ((mW % 2 != 1) || (mH % 2 != 1)) + throw new IndexOutOfBoundsException("matrix must not have round length"); + + mW /= 2; + mH /= 2; + Color[][] pixel; Color[][] pixelNeu = picture.getPixelArray(); - + for (int i = 0; i < amount; i++) { pixel = pixelNeu; pixelNeu = new Color[w][h]; + for (int x = 0; x < w; x++) { for (int y = 0; y < h; y++) { - if (x < 1 || y < 1 || x + 1 >= w || y + 1 >= h) { - pixelNeu[x][y] = pixel[x][y]; - continue; - } - pixelNeu[x][y] = pixel[x][y]; - //p p p - //p 0 p - //p p p - MColor sum = new MColor(pixel[x + 0][y + 1]).mult(-1) - .addM(pixel[x - 1][y + 0], -1) - .addM(pixel[x + 0][y + 0], 5) - .addM(pixel[x + 1][y + 0], -1) - .addM(pixel[x + 0][y - 1], -1); - pixelNeu[x][y] = sum.get(); + pixelNeu[x][y] = pixel[x][y]; + + MColor sum = new MColor(); + + double gSum = 0; + + for (int dx = -mW; dx <= mW; dx++) { + for (int dy = -mH; dy <= mH; dy++) { + if (x + dx >= 0 && y + dy >= 0 && x + dx < w && y + dy < h) { + double g = matrix[mW + dx][mH + dy]; + gSum += g; + sum.addM(pixel[x + dx][y + dy], g); + } + } + } + + pixelNeu[x][y] = sum.div(gSum).get(); } } } diff --git a/src/main/java/io/gitlab/jfronny/ImgJava/util/MColor.java b/src/main/java/io/gitlab/jfronny/ImgJava/util/MColor.java index bde8f77..6fd09dd 100644 --- a/src/main/java/io/gitlab/jfronny/ImgJava/util/MColor.java +++ b/src/main/java/io/gitlab/jfronny/ImgJava/util/MColor.java @@ -3,10 +3,10 @@ package io.gitlab.jfronny.ImgJava.util; import java.awt.*; public class MColor { - public int r; - public int g; - public int b; - public int a; + public double r; + public double g; + public double b; + public double a; public MColor(Color c) { this(c.getRed(), c.getGreen(), c.getBlue(), c.getAlpha()); @@ -24,7 +24,11 @@ public class MColor { } public Color get() { - return new Color(Math.max(r, 0), Math.max(g, 0), Math.max(b, 0), Math.max(a, 0)); + return new Color(clamp(r), clamp(g), clamp(b), clamp(a)); + } + + private static int clamp(double d) { + return (int)Math.round(Math.max(Math.min(d, 255), 0)); } public MColor add(Color c) {