Image Processing Edge Detection in Java

后端 未结 4 536
故里飘歌
故里飘歌 2021-02-06 09:33

This is my situation. It involves aligning a scanned image which will account for incorrect scanning. I must align the scanned image with my Java program.

These are more

4条回答
  •  别跟我提以往
    2021-02-06 10:06

    I researched the libraries but in the end I found it more convenient to code up my own edge detection methods.

    The class below will detect black/grayed out edges of a scanned sheet of paper that contains such edges, and will return the x and y coordinate of the edges of the sheet of paper, starting from the rightmost end (reverse = true) or from lower end (reverse = true) or from the top edge (reverse = false) or from left edge (reverse = false). Also...the program will take ranges along vertical edges (rangex) measured in pixels, and horizontal ranges (rangey) measured in pixels. The ranges determine outliers in the points received.

    The program does 4 vertical cuts using the specified arrays, and 4 horizontal cuts. It retrieves the values of the dark dots. It uses the ranges to eliminate outliers. Sometimes, a little spot on the paper may cause an outlier point. The smaller the range, the fewer the outliers. However, sometimes the edge is slightly tilted, so you don't want to make the range too small.

    Have fun. It works perfectly for me.

    import java.awt.image.BufferedImage;
    import java.awt.Color;
    import java.util.ArrayList;
    import java.lang.Math;
    import java.awt.Point;
    public class EdgeDetection {
    
        public App ap;
            public int[] horizontalCuts = {120, 220, 320, 420};
            public int[] verticalCuts = {300, 350, 375, 400};
    
    
    
        public void printEdgesTest(BufferedImage image, boolean reversex, boolean reversey, int rangex, int rangey){
            int[] mx = horizontalCuts;
            int[] my = verticalCuts;
    
                //you are getting edge points here
                //the "true" parameter indicates that it performs a cut starting at 0. (left edge)
            int[] xEdges = getEdges(image, mx, reversex, true);
            int edgex = getEdge(xEdges, rangex);
            for(int x = 0; x < xEdges.length; x++){
                System.out.println("EDGE = " + xEdges[x]);
            }
            System.out.println("THE EDGE = " + edgex);
                //the "false" parameter indicates you are doing your cut starting at the end (image.getHeight)
                //and ending at 0
                //if the parameter was true, it would mean it would start the cuts at y = 0
            int[] yEdges = getEdges(image, my, reversey, false);
            int edgey = getEdge(yEdges, rangey);
            for(int y = 0; y < yEdges.length; y++){
                System.out.println("EDGE = " + yEdges[y]);
            }
            System.out.println("THE EDGE = " + edgey);
        }
    
        //This function takes an array of coordinates...detects outliers, 
        //and computes the average of non-outlier points.
    
        public int getEdge(int[] edges, int range){
            ArrayList result = new ArrayList();
            boolean[] passes = new boolean[edges.length];
            int[][] differences = new int[edges.length][edges.length-1];
            //THIS CODE SEGMENT SAVES THE DIFFERENCES BETWEEN THE POINTS INTO AN ARRAY
            for(int n = 0; n n){
                        differences[n][m-1] = edges[n] - edges[m];
                    }
                }
            }
             //This array determines which points are outliers or nots (fall within range of other points)
            for(int n = 0; n= .5){
                System.out.println("MEAN " + mean);
                return (int)mean+1;
            }else{
                System.out.println("MEAN " + mean);
                return (int)mean;
            }       
        }
    
    
         //this function computes "dark" points, which include light gray, to detect edges.
         //reverse - when true, starts counting from x = 0 or y = 0, and ends at image.getWidth or image.getHeight()
         //verticalEdge - determines whether you want to detect a vertical edge, or a horizontal edge
         //arr[] - determines the coordinates of the vertical or horizontal cuts you will do
         //set the arr[] array according to the graphical layout of your scanned image
         //image - this is the image you want to detect black/white edges of
        public int[] getEdges(BufferedImage image, int[] arr, boolean reverse, boolean verticalEdge){
            int red = 255;
            int green = 255;
            int blue = 255;
            int[] result = new int[arr.length];
            for(int n = 0; n=0:m<(verticalEdge ? image.getWidth():image.getHeight());){
                    Color c = new Color(image.getRGB(verticalEdge ? m:arr[n], verticalEdge ? arr[n]:m));
                    red = c.getRed();
                    green = c.getGreen();
                    blue = c.getBlue();
                            //determine if the point is considered "dark" or not.
                            //modify the range if you want to only include really dark spots.
                            //occasionally, though, the edge might be blurred out, and light gray helps
                    if(red<239 && green<239 && blue<239){
                        result[n] = m;
                        break;
                    }
                            //count forwards or backwards depending on reverse variable
                    if(reverse){
                        m--;
                    }else{
                        m++;
                    }
                }
            }
        return result;
        }
    
    }
    

提交回复
热议问题