Start line:  
End line:  

Snippet Preview

Snippet HTML Code

Stack Overflow Questions
  /*
   * Copyright 1999-2101 Alibaba Group.
   *
   * Licensed under the Apache License, Version 2.0 (the "License");
   * you may not use this file except in compliance with the License.
   * You may obtain a copy of the License at
   *
   *      http://www.apache.org/licenses/LICENSE-2.0
   *
  * Unless required by applicable law or agreed to in writing, software
  * distributed under the License is distributed on an "AS IS" BASIS,
  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
 package com.alibaba.simpleimage.util;
 
 
 import  javax.media.jai.BorderExtender;
 import  javax.media.jai.Interpolation;
 import  javax.media.jai.JAI;
 import  javax.media.jai.PlanarImage;
 import  javax.media.jai.RenderedImageAdapter;
 
 
 import  com.sun.media.jai.opimage.SubsampleAverageCRIF;
 
 public class ImageScaleHelper {
 
     private static ImageLog log = ImageLog.getLog(ImageScaleHelper.class);
 
     public static ImageWrapper scaleGIF(ImageWrapper imgWrapperScaleParameter zoomthrows SimpleImageException {
         Node streamMetadata = imgWrapper.getStreamMetadata();
 
         int width = 0, height = 0;
         Node screenDescNode = NodeUtils.getChild(streamMetadata"LogicalScreenDescriptor");
         if (screenDescNode != null) {
             width = NodeUtils.getIntAttr(screenDescNode"logicalScreenWidth");
             height = NodeUtils.getIntAttr(screenDescNode"logicalScreenHeight");
         }
         if (width <= 0 || height <= 0) {
             width = imgWrapper.getAsBufferedImage().getWidth();
             height = imgWrapper.getAsBufferedImage().getHeight();
         }
 
         // do not need scale the image
         if (zoom.getMaxWidth() >= width && zoom.getMaxHeight() >= height) {
             return imgWrapper;
         }
 
         double scale = computeDoubleScale(widthheightzoom);
         int newWidth = (int) (width * scale);
         int newHeight = (int) (height * scale);
         NodeUtils.setAttrValue(screenDescNode"logicalScreenWidth"newWidth);
         NodeUtils.setAttrValue(screenDescNode"logicalScreenHeight"newHeight);
         NodeUtils.removeChild(streamMetadata"GlobalColorTable");
 
         for (int i = 0; i < imgWrapper.getNumOfImages(); i++) {
             PlanarImage img = imgWrapper.getAsPlanarImage(i);
             Node imgMetadata = imgWrapper.getMetadata(i);
 
             if (img.getColorModel() instanceof IndexColorModel) {
                 throw new SimpleImageException(
                                                "Unsupported scale image with IndexColorModel, please convert to RGB color model first");
             }
             // No more need, index color model will triger throws exception first
             // NodeUtils.removeChild(imgMetadata, "LocalColorTable");
             Node imgDescNode = NodeUtils.getChild(imgMetadata"ImageDescriptor");
 
             int x = NodeUtils.getIntAttr(imgDescNode"imageLeftPosition");
             int y = NodeUtils.getIntAttr(imgDescNode"imageTopPosition");
             int newX = (int) (x * scale), newY = (int) (y * scale);
             newX = newX > 0 ? newX : 0;
             newY = newY > 0 ? newY : 0;
             NodeUtils.setAttrValue(imgDescNode"imageLeftPosition"newX);
             NodeUtils.setAttrValue(imgDescNode"imageTopPosition"newY);
 
             int imgWidth = NodeUtils.getIntAttr(imgDescNode"imageWidth");
             int imgHeight = NodeUtils.getIntAttr(imgDescNode"imageHeight");
             int newImgWidth = (int) (imgWidth * scale), newImgHeight = (int) (imgHeight * scale);
             newImgWidth = newImgWidth > 1 ? newImgWidth : 1;
             newImgHeight = newImgHeight > 1 ? newImgHeight : 1;
             NodeUtils.setAttrValue(imgDescNode"imageWidth"newImgWidth);
             NodeUtils.setAttrValue(imgDescNode"imageHeight"newImgHeight);
 
             if (zoom.getAlgorithm() == ..) {
                 img = bicubicScaleImage(img, (floatscale, Interpolation.INTERP_BICUBIC);
             } else if (zoom.getAlgorithm() == ..) {
                img = bicubicScaleImage(img, (floatscale, Interpolation.INTERP_BICUBIC_2);
            } else if (zoom.getAlgorithm() == ..) {
                img = subsampleavgScaleImage(imgscale);
            } else if (zoom.getAlgorithm() == ..) {
                img = lanczosScaleImage(imgscale);
            } else if (zoom.getAlgorithm() == ..) {
                img = autoScaleImage(imgscale);
            } else {
                throw new IllegalArgumentException("Unknow algorithm");
            }
            imgWrapper.setImage(iimg);
        }
        return imgWrapper;
    }
    public static PlanarImage scale(PlanarImage inputScaleParameter zoom) {
        int w = input.getWidth();
        int h = input.getHeight();
        // 如果不超过最大限制则不做任何处理
        if (zoom.getMaxWidth() >= w && zoom.getMaxHeight() >= h) {
            return input;
        }
        if (zoom.getAlgorithm() == ..) {
            float scale = computeFloatScale(whzoom);
            return bicubicScaleImage(inputscale, Interpolation.INTERP_BICUBIC);
        } else if (zoom.getAlgorithm() == ..) {
            float scale = computeFloatScale(whzoom);
            return bicubicScaleImage(inputscale, Interpolation.INTERP_BICUBIC_2);
        } else if (zoom.getAlgorithm() == ..) {
            double scale = computeDoubleScale(whzoom);
            return subsampleavgScaleImage(inputscale);
        } else if (zoom.getAlgorithm() == ..) {
            double scale = computeDoubleScale(whzoom);
            return lanczosScaleImage(inputscale);
        } else if (zoom.getAlgorithm() == ..) {
            double scale = computeDoubleScale(whzoom);
            return autoScaleImage(inputscale);
        } else if (zoom.getAlgorithm() == ..) {
            throw new UnsupportedOperationException("Deprecated method");
        } else {
            throw new IllegalArgumentException("Unknow algorithm");
        }
    }
    public static float computeFloatScale(int wint hScaleParameter zoom) {
        int maxWidth = zoom.getMaxWidth();
        int maxHeight = zoom.getMaxHeight();
        float scale = 0.0f;
        scale = Math.min(((floatmaxWidth) / w, ((floatmaxHeight) / h);
        return scale;
    }
    public static double computeDoubleScale(int wint hScaleParameter zoom) {
        int maxWidth = zoom.getMaxWidth();
        int maxHeight = zoom.getMaxHeight();
        double scale = 0.0;
        scale = Math.min(((doublemaxWidth) / w, ((doublemaxHeight) / h);
        return scale;
    }
    public static PlanarImage bicubicScaleImage(PlanarImage inputfloat scaleint alg) {
        RenderingHints qualityHints = new RenderingHints(.,
                                                         .);
        // 必须使用该hint,否则会出现边框变黑到情况
        qualityHints.put(JAI.KEY_BORDER_EXTENDER, BorderExtender.createInstance(BorderExtender.BORDER_COPY));
        ParameterBlock pb = new ParameterBlock();
        pb.addSource(input);
        pb.add(scale);
        pb.add(scale);
        pb.add(0.0F);
        pb.add(0.0F);
        pb.add(Interpolation.getInstance(alg));
        return JAI.create("scale"pbqualityHints);
    }
    public static PlanarImage subsampleavgScaleImage(PlanarImage inputdouble scale) {
        RenderingHints qualityHints = new RenderingHints(.,
                                                         .);
        ParameterBlock pb = new ParameterBlock();
        pb.addSource(input);
        pb.add(scale);
        pb.add(scale);
        // Because the mlib subsampleaverage has bug, use pure java version
        SubsampleAverageCRIF factory = new SubsampleAverageCRIF();
        PlanarImage zoomOp = (PlanarImage) factory.create(pbqualityHints);
        return zoomOp;
    }
    public static PlanarImage lanczosScaleImage(PlanarImage inputdouble scale) {
        LanczosScaleOp lanczosOp = new LanczosScaleOp(scalescale);
        BufferedImage dest = lanczosOp.compute(input.getAsBufferedImage());
        return PlanarImage.wrapRenderedImage(dest);
    }
    public static PlanarImage autoScaleImage(PlanarImage inputdouble scale) {
        if (input.getWidth() > 3000 || input.getHeight() > 3000) {
            return subsampleavgScaleImage(inputscale);
        }
        try {
            return lanczosScaleImage(inputscale);
        } catch (Exception e) {
            .warn("LanczosScale fail : " + e.getMessage(), input);
            return subsampleavgScaleImage(inputscale);
        }
    }

    
折半渐进压缩图片方法 测试后觉得效果不太理想,不鼓励使用

Parameters:
img
targetWidth
targetHeight
hint
progressiveBilinear
Returns:
    @Deprecated
    public static PlanarImage progressiveScaleImage(PlanarImage inputint targetWidthint targetHeightObject hint,
                                                    boolean progressive) {
        BufferedImage img = input.getAsBufferedImage();
        int type = (img.getTransparency() == .) ? . : .;
        BufferedImage ret = img;
        BufferedImage scratchImage = null;
        Graphics2D g2 = null;
        int wh;
        int prevW = ret.getWidth();
        int prevH = ret.getHeight();
        boolean isTranslucent = img.getTransparency() != .;
        if (progressive) {
            // Use multi-step technique: start with original size, then
            // scale down in multiple passes with drawImage()
            // until the target size is reached
            w = img.getWidth();
            h = img.getHeight();
        } else {
            // Use one-step technique: scale directly from original
            // size to target size with a single drawImage() call
            w = targetWidth;
            h = targetHeight;
        }
        do {
            if (progressive && w > targetWidth) {
                w /= 2;
                if (w < targetWidth) {
                    w = targetWidth;
                }
            }
            if (progressive && h > targetHeight) {
                h /= 2;
                if (h < targetHeight) {
                    h = targetHeight;
                }
            }
            if (scratchImage == null || isTranslucent) {
                // Use a single scratch buffer for all iterations
                // and then copy to the final, correctly-sized image
                // before returning
                scratchImage = new BufferedImage(whtype);
                g2 = scratchImage.createGraphics();
            }
            g2.setRenderingHint(.hint);
            g2.drawImage(ret, 0, 0, wh, 0, 0, prevWprevHnull);
            prevW = w;
            prevH = h;
            ret = scratchImage;
        } while (w != targetWidth || h != targetHeight);
        if (g2 != null) {
            g2.dispose();
        }
        // If we used a scratch buffer that is larger than our target size,
        // create an image of the right size and copy the results into it
        if (targetWidth != ret.getWidth() || targetHeight != ret.getHeight()) {
            scratchImage = new BufferedImage(targetWidthtargetHeighttype);
            g2 = scratchImage.createGraphics();
            g2.drawImage(ret, 0, 0, null);
            g2.dispose();
            ret = scratchImage;
        }
        return new RenderedImageAdapter(ret);
    }
New to GrepCode? Check out our FAQ X