java圖片裁剪填充工具類

import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.net.URL;

/**
 * @author gyp
 * @version 1.0
 * @date 2019/9/20 10:39
 */
public final class ImageUtil {

    private ImageUtil() {

    }

    /**
     * 裁剪圖片並返回圖片的字節數組
     *
     * @param url        圖片的url
     * @param formatName 圖片格式名 jpg\png\jpeg...
     * @param x          起始點x
     * @param y          起始點y
     * @param w          裁剪寬度
     * @param h          裁剪高度
     * @return
     * @throws IOException
     */
    public static byte[] subToByteArray(URL url, String formatName, int x, int y, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(url);
        buffer = buffer.getSubimage(x, y, w, h);
        return toByteArray(buffer, formatName);
    }

    /**
     * 裁剪圖片並返回圖片的字節數組
     *
     * @param input      圖片的輸入流
     * @param formatName 圖片格式名 jpg\png\jpeg...
     * @param x          起始點x
     * @param y          起始點y
     * @param w          裁剪寬度
     * @param h          裁剪高度
     * @return
     * @throws IOException
     */
    public static byte[] subToByteArray(InputStream input, String formatName, int x, int y, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(input);
        buffer = buffer.getSubimage(x, y, w, h);
        return toByteArray(buffer, formatName);
    }

    /**
     * 裁剪圖片並返回圖片的字節數組
     *
     * @param file       圖片文件
     * @param formatName 圖片格式名 jpg\png\jpeg...
     * @param x          起始點x
     * @param y          起始點y
     * @param w          裁剪寬度
     * @param h          裁剪高度
     * @return
     * @throws IOException
     */
    public static byte[] subToByteArray(File file, String formatName, int x, int y, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(file);
        buffer = buffer.getSubimage(x, y, w, h);
        return toByteArray(buffer, formatName);
    }


    /**
     * 根據比率裁剪圖片例如 3:2
     *
     * @param w 寬的比率因素 例如 3
     * @param h 高的比率因素 例如 2
     * @return
     */
    public static BufferedImage subByRate(URL url, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(url);
        return baseSubByRate(buffer, w, h);
    }

    /**
     * 根據比率裁剪圖片例如 3:2
     *
     * @param formatName 圖片格式名 jpg\png\jpeg...
     * @param w          寬的比率因素 例如 3
     * @param h          高的比率因素 例如 2
     * @return
     */
    public static BufferedImage subByRate(InputStream input, String formatName, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(input);
        return baseSubByRate(buffer, w, h);
    }

    /**
     * 根據比率裁剪圖片例如 3:2
     *
     * @param w 寬的比率因素 例如 3
     * @param h 高的比率因素 例如 2
     * @return
     */
    public static BufferedImage subByRate(File file, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(file);
        return baseSubByRate(buffer, w, h);
    }

    private static BufferedImage baseSubByRate(BufferedImage buffer, int w, int h) throws IOException {
        int imgWidth = buffer.getWidth();
        int imgHeight = buffer.getHeight();
        // 圖片的寬高比
        BigDecimal imgRate = BigDecimal.valueOf(imgWidth).divide(BigDecimal.valueOf(imgHeight), 8, BigDecimal.ROUND_HALF_UP);
        // 裁剪後寬高比
        BigDecimal rate = BigDecimal.valueOf(w).divide(BigDecimal.valueOf(h), 8, BigDecimal.ROUND_HALF_UP);
        int compare = imgRate.compareTo(rate);
        if (compare > 0) {
            // 如果圖片比例比裁剪比例大,則裁剪左右
            int width = BigDecimal.valueOf(imgHeight).multiply(rate).intValue();
            int x = (imgWidth - width) / 2;
            return buffer.getSubimage(x, 0, width, imgHeight);
        }
        if (compare < 0) {
            // 如果圖片比例比裁剪比例小,則裁剪上下
            int height = BigDecimal.valueOf(imgWidth).divide(rate, 0, BigDecimal.ROUND_HALF_DOWN).intValue();
            int y = (imgHeight - height) / 2;
            return buffer.getSubimage(0, y, imgWidth, height);
        }
        return buffer;
    }

    /**
     * 圖片轉byte數組
     *
     * @param buffer     圖片
     * @param formatName 圖片格式名 jpg\png\jpeg...
     * @return
     * @throws IOException
     */
    public static byte[] toByteArray(BufferedImage buffer, String formatName) throws IOException {
        ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
        ImageIO.write(buffer, formatName, outputStream);
        return outputStream.toByteArray();
    }

    /**
     * 填充顏色
     *
     * @param buffer 圖片
     * @param color  顏色
     * @param x      起始點x
     * @param y      起始點y
     * @param w      填充寬度
     * @param h      填充高度
     */
    public static void fillColor(BufferedImage buffer, Color color, int x, int y, int w, int h) {
        Graphics2D graphics = buffer.createGraphics();
        graphics.setPaint(color);
        graphics.fillRect(x, y, w, h);
    }

    /**
     * 填充圖片到指定比率
     *
     * @param url   圖片url
     * @param color 填充顏色
     * @param w     寬的比率因素 例如3
     * @param h     高的比率因素 例如2
     * @return
     * @throws IOException
     */
    public static BufferedImage fillByRate(URL url, Color color, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(url);
        return baseFillByRate(buffer, color, w, h);
    }

    /**
     * 填充圖片到指定比率
     *
     * @param input 圖片輸入流
     * @param color 填充顏色
     * @param w     寬的比率因素 例如3
     * @param h     高的比率因素 例如2
     * @return
     * @throws IOException
     */
    public static BufferedImage fillByRate(InputStream input, Color color, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(input);
        return baseFillByRate(buffer, color, w, h);
    }

    /**
     * 填充圖片到指定比率
     *
     * @param file  圖片文件
     * @param color 填充顏色
     * @param w     寬的比率因素 例如3
     * @param h     高的比率因素 例如2
     * @return
     * @throws IOException
     */
    public static BufferedImage fillByRate(File file, Color color, int w, int h) throws IOException {
        BufferedImage buffer = ImageIO.read(file);
        return baseFillByRate(buffer, color, w, h);
    }

    private static BufferedImage baseFillByRate(BufferedImage buffer, Color color, int w, int h) {
        int imgWidth = buffer.getWidth();
        int imgHeight = buffer.getHeight();
        // 圖片的寬高比
        BigDecimal imgRate = BigDecimal.valueOf(imgWidth).divide(BigDecimal.valueOf(imgHeight), 8, BigDecimal.ROUND_HALF_UP);
        // 裁剪後寬高比
        BigDecimal rate = BigDecimal.valueOf(w).divide(BigDecimal.valueOf(h), 8, BigDecimal.ROUND_HALF_UP);
        int compare = imgRate.compareTo(rate);
        if (compare > 0) {
            // 如果圖片比例比填充比例大,則填充上下
            int height = BigDecimal.valueOf(imgWidth).divide(rate, 0, BigDecimal.ROUND_HALF_UP).intValue();
            BufferedImage bufferedImage = new BufferedImage(imgWidth, height, buffer.getType());
            Graphics2D graphics = bufferedImage.createGraphics();
            int topH = (height - imgHeight) / 2;
            graphics.setPaint(color);
            graphics.fillRect(0, 0, imgWidth, topH);
            AffineTransform xform = new AffineTransform();
            xform.translate(0, topH);
            graphics.drawRenderedImage(buffer, xform);
            graphics.fillRect(0, topH + imgHeight, imgWidth, height - topH - imgHeight);
            return bufferedImage;
        }
        if (compare < 0) {
            // 如果圖片比例比填充比例小,則填充左右
            int width = BigDecimal.valueOf(imgHeight).multiply(rate).intValue();
            BufferedImage bufferedImage = new BufferedImage(width, imgHeight, buffer.getType());
            Graphics2D graphics = bufferedImage.createGraphics();
            int leftW = (width - imgWidth) / 2;
            graphics.fillRect(0, 0, leftW, imgHeight);
            AffineTransform xform = new AffineTransform();
            xform.translate(leftW, 0);
            graphics.drawRenderedImage(buffer, xform);
            graphics.fillRect(leftW + imgWidth, 0, width - leftW - imgWidth, imgHeight);
            return bufferedImage;
        }
        return buffer;
    }
}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章