俊星的BLOG

          JAVA圖像縮放處理

          今天在網上看到了一篇關于JAVA圖像處理的文章,博主貼出了一個處理類:特點是高品質縮小,具體代碼如下:
          import java.awt.image.BufferedImage;
          import java.io.File;
          import java.io.FileOutputStream;
          import java.io.IOException;

          import javax.imageio.ImageIO;

          public class ImageScale {

              
          private int width;
              
          private int height;
              
          private int scaleWidth;
              
          double support = (double3.0;
              
          double[] contrib;
              
          double[] normContrib;
              
          double[] tmpContrib;
              
          int startContrib, stopContrib;
              
          int nDots;
              
          int nHalfDots;

              
          public BufferedImage imageZoomOut(BufferedImage srcBufferImage, int w, int h, boolean lockScale) {
                  width 
          = srcBufferImage.getWidth();
                  height 
          = srcBufferImage.getHeight();
                  scaleWidth 
          = w;
                  
          if (lockScale) {
                      h 
          = w * height / width;
                  }


                  
          if (DetermineResultSize(w, h) == 1{
                      
          return srcBufferImage;
                  }

                  CalContrib();
                  BufferedImage pbOut 
          = HorizontalFiltering(srcBufferImage, w);
                  BufferedImage pbFinalOut 
          = VerticalFiltering(pbOut, h);
                  
          return pbFinalOut;
              }


              
          /**
               * 決定圖像尺寸
               
          */

              
          private int DetermineResultSize(int w, int h) {
                  
          double scaleH, scaleV;
                  scaleH 
          = (double) w / (double) width;
                  scaleV 
          = (double) h / (double) height;
                  
          // 需要判斷一下scaleH,scaleV,不做放大操作
                  if (scaleH >= 1.0 && scaleV >= 1.0{
                      
          return 1;
                  }

                  
          return 0;

              }
           // end of DetermineResultSize()

              
          private double Lanczos(int i, int inWidth, int outWidth, double Support) {
                  
          double x;

                  x 
          = (double) i * (double) outWidth / (double) inWidth;

                  
          return Math.sin(x * Math.PI) / (x * Math.PI) * Math.sin(x * Math.PI / Support) / (x * Math.PI / Support);

              }
           // end of Lanczos()

              
          //
              
          // Assumption: same horizontal and vertical scaling factor
              
          //
              private void CalContrib() {
                  nHalfDots 
          = (int) ((double) width * support / (double) scaleWidth);
                  nDots 
          = nHalfDots * 2 + 1;
                  
          try {
                      contrib 
          = new double[nDots];
                      normContrib 
          = new double[nDots];
                      tmpContrib 
          = new double[nDots];
                  }
           catch (Exception e) {
                      System.out.println(
          "init contrib,normContrib,tmpContrib" + e);
                  }


                  
          int center = nHalfDots;
                  contrib[center] 
          = 1.0;

                  
          double weight = 0.0;
                  
          int i = 0;
                  
          for (i = 1; i <= center; i++{
                      contrib[center 
          + i] = Lanczos(i, width, scaleWidth, support);
                      weight 
          += contrib[center + i];
                  }


                  
          for (i = center - 1; i >= 0; i--{
                      contrib[i] 
          = contrib[center * 2 - i];
                  }


                  weight 
          = weight * 2 + 1.0;

                  
          for (i = 0; i <= center; i++{
                      normContrib[i] 
          = contrib[i] / weight;
                  }


                  
          for (i = center + 1; i < nDots; i++{
                      normContrib[i] 
          = normContrib[center * 2 - i];
                  }

              }
           // end of CalContrib()

              
          // 處理邊緣
              private void CalTempContrib(int start, int stop) {
                  
          double weight = 0;

                  
          int i = 0;
                  
          for (i = start; i <= stop; i++{
                      weight 
          += contrib[i];
                  }


                  
          for (i = start; i <= stop; i++{
                      tmpContrib[i] 
          = contrib[i] / weight;
                  }


              }
           // end of CalTempContrib()

              
          private int GetRedValue(int rgbValue) {
                  
          int temp = rgbValue & 0x00ff0000;
                  
          return temp >> 16;
              }


              
          private int GetGreenValue(int rgbValue) {
                  
          int temp = rgbValue & 0x0000ff00;
                  
          return temp >> 8;
              }


              
          private int GetBlueValue(int rgbValue) {
                  
          return rgbValue & 0x000000ff;
              }


              
          private int ComRGB(int redValue, int greenValue, int blueValue) {

                  
          return (redValue << 16+ (greenValue << 8+ blueValue;
              }


              
          // 行水平濾波
              private int HorizontalFilter(BufferedImage bufImg, int startX, int stopX, int start, int stop, int y,
                      
          double[] pContrib) {
                  
          double valueRed = 0.0;
                  
          double valueGreen = 0.0;
                  
          double valueBlue = 0.0;
                  
          int valueRGB = 0;
                  
          int i, j;

                  
          for (i = startX, j = start; i <= stopX; i++, j++{
                      valueRGB 
          = bufImg.getRGB(i, y);

                      valueRed 
          += GetRedValue(valueRGB) * pContrib[j];
                      valueGreen 
          += GetGreenValue(valueRGB) * pContrib[j];
                      valueBlue 
          += GetBlueValue(valueRGB) * pContrib[j];
                  }


                  valueRGB 
          = ComRGB(Clip((int) valueRed), Clip((int) valueGreen), Clip((int) valueBlue));
                  
          return valueRGB;

              }
           // end of HorizontalFilter()

              
          // 圖片水平濾波
              private BufferedImage HorizontalFiltering(BufferedImage bufImage, int iOutW) {
                  
          int dwInW = bufImage.getWidth();
                  
          int dwInH = bufImage.getHeight();
                  
          int value = 0;
                  BufferedImage pbOut 
          = new BufferedImage(iOutW, dwInH, BufferedImage.TYPE_INT_RGB);

                  
          for (int x = 0; x < iOutW; x++{

                      
          int startX;
                      
          int start;
                      
          int X = (int) (((double) x) * ((double) dwInW) / ((double) iOutW) + 0.5);
                      
          int y = 0;

                      startX 
          = X - nHalfDots;
                      
          if (startX < 0{
                          startX 
          = 0;
                          start 
          = nHalfDots - X;
                      }
           else {
                          start 
          = 0;
                      }


                      
          int stop;
                      
          int stopX = X + nHalfDots;
                      
          if (stopX > (dwInW - 1)) {
                          stopX 
          = dwInW - 1;
                          stop 
          = nHalfDots + (dwInW - 1 - X);
                      }
           else {
                          stop 
          = nHalfDots * 2;
                      }


                      
          if (start > 0 || stop < nDots - 1{
                          CalTempContrib(start, stop);
                          
          for (y = 0; y < dwInH; y++{
                              value 
          = HorizontalFilter(bufImage, startX, stopX, start, stop, y, tmpContrib);
                              pbOut.setRGB(x, y, value);
                          }

                      }
           else {
                          
          for (y = 0; y < dwInH; y++{
                              value 
          = HorizontalFilter(bufImage, startX, stopX, start, stop, y, normContrib);
                              pbOut.setRGB(x, y, value);
                          }

                      }

                  }


                  
          return pbOut;

              }
           // end of HorizontalFiltering()

              
          private int VerticalFilter(BufferedImage pbInImage, int startY, int stopY, int start, int stop, int x,
                      
          double[] pContrib) {
                  
          double valueRed = 0.0;
                  
          double valueGreen = 0.0;
                  
          double valueBlue = 0.0;
                  
          int valueRGB = 0;
                  
          int i, j;

                  
          for (i = startY, j = start; i <= stopY; i++, j++{
                      valueRGB 
          = pbInImage.getRGB(x, i);

                      valueRed 
          += GetRedValue(valueRGB) * pContrib[j];
                      valueGreen 
          += GetGreenValue(valueRGB) * pContrib[j];
                      valueBlue 
          += GetBlueValue(valueRGB) * pContrib[j];
                  }


                  valueRGB 
          = ComRGB(Clip((int) valueRed), Clip((int) valueGreen), Clip((int) valueBlue));
                  
          // System.out.println(valueRGB);
                  return valueRGB;

              }
           // end of VerticalFilter()

              
          private BufferedImage VerticalFiltering(BufferedImage pbImage, int iOutH) {
                  
          int iW = pbImage.getWidth();
                  
          int iH = pbImage.getHeight();
                  
          int value = 0;
                  BufferedImage pbOut 
          = new BufferedImage(iW, iOutH, BufferedImage.TYPE_INT_RGB);

                  
          for (int y = 0; y < iOutH; y++{

                      
          int startY;
                      
          int start;
                      
          int Y = (int) (((double) y) * ((double) iH) / ((double) iOutH) + 0.5);

                      startY 
          = Y - nHalfDots;
                      
          if (startY < 0{
                          startY 
          = 0;
                          start 
          = nHalfDots - Y;
                      }
           else {
                          start 
          = 0;
                      }


                      
          int stop;
                      
          int stopY = Y + nHalfDots;
                      
          if (stopY > (int) (iH - 1)) {
                          stopY 
          = iH - 1;
                          stop 
          = nHalfDots + (iH - 1 - Y);
                      }
           else {
                          stop 
          = nHalfDots * 2;
                      }


                      
          if (start > 0 || stop < nDots - 1{
                          CalTempContrib(start, stop);
                          
          for (int x = 0; x < iW; x++{
                              value 
          = VerticalFilter(pbImage, startY, stopY, start, stop, x, tmpContrib);
                              pbOut.setRGB(x, y, value);
                          }

                      }
           else {
                          
          for (int x = 0; x < iW; x++{
                              value 
          = VerticalFilter(pbImage, startY, stopY, start, stop, x, normContrib);
                              pbOut.setRGB(x, y, value);
                          }

                      }


                  }


                  
          return pbOut;

              }
           // end of VerticalFiltering()

              
          int Clip(int x) {
                  
          if (x < 0)
                      
          return 0;
                  
          if (x > 255)
                      
          return 255;
                  
          return x;
              }


              
          public static void main(String[] args) throws IOException {
                  ImageScale is 
          = new ImageScale();
                  String path 
          = "D:\\My Documents\\My Pictures\\pictrue\\";
                  BufferedImage image1 
          = ImageIO.read(new File(path + "test.jpg"));
                  
          int w = 200, h = 400;
                  BufferedImage image2 
          = is.imageZoomOut(image1, w, h, true);
                  FileOutputStream out 
          = new FileOutputStream(path + "test_2.jpg");
                  ImageIO.write(image2, 
          "jpeg", out);
              }

          }

          上面的代碼中,本人做了一點小改進:imageZoomOut方法中,添加了一個lockScale參數,如果為true則表明保持縱橫比。
          程序運行的效果如下:
          test.jpg(原圖):


          test_2.jpg(程序生成的圖片):


          posted on 2009-05-23 13:37 俊星 閱讀(4181) 評論(1)  編輯  收藏

          評論

          # re: JAVA圖像縮放處理[未登錄] 2014-11-24 15:13 test

          不錯的方法  回復  更多評論   


          只有注冊用戶登錄后才能發表評論。


          網站導航:
           
          主站蜘蛛池模板: 芮城县| 崇信县| 咸阳市| 屏东市| 桂阳县| 游戏| 四会市| 山西省| 越西县| 胶州市| 大城县| 淮北市| 龙游县| 清河县| 柯坪县| 喜德县| 竹溪县| 彭水| 浦北县| 上栗县| 芮城县| 郯城县| 盱眙县| 乐业县| 屯门区| 宁都县| 合山市| 波密县| 余江县| 铜鼓县| 舟曲县| 伊金霍洛旗| 山丹县| 德令哈市| 双江| 新野县| 平湖市| 衡东县| 舞钢市| 宁阳县| 墨竹工卡县|