图像处理之图像梯度效果(转载)

转载自:http://blog.csdn.net/jia20003/article/details/7664777

图像处理之图像梯度效果

基本思想:

利用X方向与Y方向分别实现一阶微分,求取振幅,实现图像梯度效果。关于如何计算图像

一阶微分参见这里:http://blog.csdn.net/jia20003/article/details/7562092

使用的两种微分算子分别为Prewitt与Sobel,其中Soble在X, Y两个方向算子分别为:

Prewitt在X, Y方向上梯度算子分别为:

二:程序思路及实现

梯度滤镜提供了两个参数:

– 方向,用来要决定图像完成X方向梯度计算, Y方向梯度计算,或者是振幅计算

– 算子类型,用来决定是使用sobel算子或者是prewitt算子。

计算振幅的公式可以参见以前《图像处理之一阶微分应用》的文章

 三:运行效果

原图像如下:

基于Prewitt与sobel算子的XY方向振幅效果如下:

该滤镜的源代码如下:

[java] view plain copy
  1. package com.process.blur.study;  
  2.   
  3. import java.awt.image.BufferedImage;  
  4. /** 
  5.  *  
  6.  * @author gloomy-fish 
  7.  * @date 2012-06-11 
  8.  *  
  9.  * prewitt operator  
  10.  * X-direction 
  11.  * -1, 0, 1 
  12.  * -1, 0, 1 
  13.  * -1, 0, 1 
  14.  *  
  15.  * Y-direction 
  16.  * -1, -1, -1 
  17.  *  0,  0,  0 
  18.  *  1,  1,  1 
  19.  *   
  20.  * sobel operator 
  21.  * X-direction 
  22.  * -1, 0, 1 
  23.  * -2, 0, 2 
  24.  * -1, 0, 1 
  25.  *  
  26.  * Y-direction 
  27.  * -1, -2, -1 
  28.  *  0,  0,  0 
  29.  *  1,  2,  1 
  30.  * 
  31.  */  
  32. public class GradientFilter extends AbstractBufferedImageOp {  
  33.   
  34.     // prewitt operator  
  35.     public final static int[][] PREWITT_X = new int[][]{{-1, 0, 1}, {-1, 0, 1}, {-1, 0, 1}};  
  36.     public final static int[][] PREWITT_Y = new int[][]{{-1, -1, -1}, {0,  0,  0}, {1,  1,  1}};  
  37.       
  38.     // sobel operator  
  39.     public final static int[][] SOBEL_X = new int[][]{{-1, 0, 1}, {-2, 0, 2}, {-1, 0, 1}};  
  40.     public final static int[][] SOBEL_Y = new int[][]{{-1, -2, -1}, {0,  0,  0}, {1,  2,  1}};  
  41.       
  42.     // direction parameter  
  43.     public final static int X_DIRECTION = 0;  
  44.     public final static int Y_DIRECTION = 2;  
  45.     public final static int XY_DIRECTION = 4;  
  46.     private int direction;  
  47.     private boolean isSobel;  
  48.       
  49.     public GradientFilter() {  
  50.         direction = XY_DIRECTION;  
  51.         isSobel = true;  
  52.     }  
  53.       
  54.     public void setSoble(boolean sobel) {  
  55.         this.isSobel = sobel;  
  56.     }  
  57.   
  58.     public int getDirection() {  
  59.         return direction;  
  60.     }  
  61.   
  62.     public void setDirection(int direction) {  
  63.         this.direction = direction;  
  64.     }  
  65.       
  66.     @Override  
  67.     public BufferedImage filter(BufferedImage src, BufferedImage dest) {  
  68.         int width = src.getWidth();  
  69.         int height = src.getHeight();  
  70.   
  71.         if (dest == null )  
  72.             dest = createCompatibleDestImage( src, null );  
  73.   
  74.         int[] inPixels = new int[width*height];  
  75.         int[] outPixels = new int[width*height];  
  76.         getRGB( src, 0, 0, width, height, inPixels );  
  77.         int index = 0, index2 = 0;  
  78.         double xred = 0, xgreen = 0, xblue = 0;  
  79.         double yred = 0, ygreen = 0, yblue = 0;  
  80.         int newRow, newCol;  
  81.         for(int row=0; row<height; row++) {  
  82.             int ta = 255, tr = 0, tg = 0, tb = 0;  
  83.             for(int col=0; col<width; col++) {  
  84.                 index = row * width + col;  
  85.                 for(int subrow = -1; subrow <= 1; subrow++) {  
  86.                     for(int subcol = -1; subcol <= 1; subcol++) {  
  87.                         newRow = row + subrow;  
  88.                         newCol = col + subcol;  
  89.                         if(newRow < 0 || newRow >= height) {  
  90.                             newRow = row;  
  91.                         }  
  92.                         if(newCol < 0 || newCol >= width) {  
  93.                             newCol = col;  
  94.                         }  
  95.                         index2 = newRow * width + newCol;  
  96.                         tr = (inPixels[index2] >> 16) & 0xff;  
  97.                         tg = (inPixels[index2] >> 8) & 0xff;  
  98.                         tb = inPixels[index2] & 0xff;  
  99.                           
  100.                         if(isSobel) {  
  101.                             xred += (SOBEL_X[subrow + 1][subcol + 1] * tr);  
  102.                             xgreen +=(SOBEL_X[subrow + 1][subcol + 1] * tg);  
  103.                             xblue +=(SOBEL_X[subrow + 1][subcol + 1] * tb);  
  104.                               
  105.                             yred += (SOBEL_Y[subrow + 1][subcol + 1] * tr);  
  106.                             ygreen +=(SOBEL_Y[subrow + 1][subcol + 1] * tg);  
  107.                             yblue +=(SOBEL_Y[subrow + 1][subcol + 1] * tb);  
  108.                         } else {  
  109.                             xred += (PREWITT_X[subrow + 1][subcol + 1] * tr);  
  110.                             xgreen +=(PREWITT_X[subrow + 1][subcol + 1] * tg);  
  111.                             xblue +=(PREWITT_X[subrow + 1][subcol + 1] * tb);  
  112.                               
  113.                             yred += (PREWITT_Y[subrow + 1][subcol + 1] * tr);  
  114.                             ygreen +=(PREWITT_Y[subrow + 1][subcol + 1] * tg);  
  115.                             yblue +=(PREWITT_Y[subrow + 1][subcol + 1] * tb);  
  116.                         }  
  117.                     }  
  118.                 }  
  119.                   
  120.                 double mred = Math.sqrt(xred * xred + yred * yred);  
  121.                 double mgreen = Math.sqrt(xgreen * xgreen + ygreen * ygreen);  
  122.                 double mblue = Math.sqrt(xblue * xblue + yblue * yblue);  
  123.                 if(XY_DIRECTION == direction)   
  124.                 {  
  125.                     outPixels[index] = (ta << 24) | (clamp((int)mred) << 16) | (clamp((int)mgreen) << 8) | clamp((int)mblue);  
  126.                 }   
  127.                 else if(X_DIRECTION == direction)  
  128.                 {  
  129.                     outPixels[index] = (ta << 24) | (clamp((int)yred) << 16) | (clamp((int)ygreen) << 8) | clamp((int)yblue);  
  130.                 }   
  131.                 else if(Y_DIRECTION == direction)   
  132.                 {  
  133.                     outPixels[index] = (ta << 24) | (clamp((int)xred) << 16) | (clamp((int)xgreen) << 8) | clamp((int)xblue);  
  134.                 }   
  135.                 else   
  136.                 {  
  137.                     // as default, always XY gradient  
  138.                     outPixels[index] = (ta << 24) | (clamp((int)mred) << 16) | (clamp((int)mgreen) << 8) | clamp((int)mblue);  
  139.                 }  
  140.                   
  141.                 // cleanup for next loop  
  142.                 newRow = newCol = 0;  
  143.                 xred = xgreen = xblue = 0;  
  144.                 yred = ygreen = yblue = 0;  
  145.                   
  146.             }  
  147.         }  
  148.         setRGB(dest, 0, 0, width, height, outPixels );  
  149.         return dest;  
  150.     }  
  151.       
  152.     public static int clamp(int value) {  
  153.         return value < 0 ? 0 : (value > 255 ? 255 : value);  
  154.     }  
  155.   
  156. }  
 
原文地址:https://www.cnblogs.com/jason-wyf/p/6188240.html