【JAVA】 后端 图片裁剪、压缩 及 视频压缩

本人使用java封装的后端媒体处理工具包

基于ImageMagick和FFmpeg客户端,使用java调用命令行实现
https://gitee.com/gnliscream/multimedia-utils

介绍

java后端的图片、视频处理工具jar包

1.获取视频信息

2.生成视频封面图

3.异步压缩视频(生成输出文件名后,调用异步压缩视频方法,且同一时间只会处理一个视频,多个请求的视频会进行排队处理)

4.异步压缩视频完成时回调通知

5.图片裁切

6.图片压缩

客户端安装

运行环境需安装FFmpeg和ImageMagick,官网地址如下:

FFmpeg:https://ffmpeg.org/

ImageMagick:http://www.imagemagick.com.cn/

FFmpeg解压后需设置/bin目录的环境变量,ImageMagick安装版安装后会自动设置环境变量。

引入依赖

<dependency>
      <groupId>com.whty.zdxt</groupId>
      <artifactId>multimedia-utils</artifactId>
      <version>0.0.1-SNAPSHOT</version>
</dependency>

配置

yml 配置上传文件的临时路径

spring:
  servlet:
    multipart:
      # 是否支持 multipart 上传文件
      enabled: true
      # 最大支持文件大小
      max-file-size: 10MB
      # 最大支持请求大小
      max-request-size: 10MB
      # 上传文件的临时目录
      location: E:/tomcat-temp

注入 视频处理类FFmpegUtils 以及 图片处理类 ImageMagickUtils

import com.whty.zdxt.multimedia.util.FFmpegUtils;
import com.whty.zdxt.multimedia.util.ImageMagickUtils;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;

@Component
public class MultimediaUtilsConfig {
    
    /**
     * 视频处理工具,因为所有压缩任务需要排队进行,所以FFmpegUtils需要是单例的,FFmpegUtils实例交由spring管理就为单例的
     */
    @Bean
    public FFmpegUtils fFmpegUtilsImpl() {
        return new FFmpegUtils();
    }

    /**
     * 图片处理工具
     */
    @Bean
    public ImageMagickUtils imageMagickUtils() {
        return new ImageMagickUtils();
    }

}

使用

FileController

import com.example.demo.util.FileUtil;
import com.whty.zdxt.multimedia.attribute.CompressionAttributes;
import com.whty.zdxt.multimedia.attribute.CropAttributes;
import com.whty.zdxt.multimedia.attribute.ResizeAttributes;
import com.whty.zdxt.multimedia.attribute.VideoAttributes;
import com.whty.zdxt.multimedia.enumeration.Suffix;
import com.whty.zdxt.multimedia.enumeration.VideoSize;
import com.whty.zdxt.multimedia.pojo.FFmpegInfo;
import com.whty.zdxt.multimedia.util.FFmpegUtils;
import com.whty.zdxt.multimedia.util.ImageMagickUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.web.servlet.MultipartProperties;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;

@RestController
@RequestMapping("/file")
public class FileController {

    @Autowired
    private FFmpegUtils fFmpegUtils;

    @Autowired
    private MultipartProperties multipartProperties;

    @Autowired
    private ImageMagickUtils imageMagickUtils;

    /**
     * 获取视频信息
     */
    @PostMapping("/getVideoInfo")
    public Object getFileInfo(@RequestParam MultipartFile file) {
        String location = multipartProperties.getLocation();

        // 生成上传视频的临时文件
        File inputFile = FileUtil.multipartFile2File(file, location);

        // 调用视频处理工具类
        String inputFileName = inputFile.getName();
        FFmpegInfo info = fFmpegUtils.getInfo(location, inputFileName);

        // 删除上传视频的临时文件
        inputFile.delete();
        return info;
    }

    /**
     * 生成视频封面图
     */
    @PostMapping("/createVideoCover")
    public Object createVideoCover(@RequestParam MultipartFile file) {
        String location = multipartProperties.getLocation();
        // 生成上传视频的临时文件
        File inputFile = FileUtil.multipartFile2File(file, location);

        // 调用视频处理工具类
        String outputFileName = fFmpegUtils.createCover(location, inputFile.getName());

        // 删除上传视频的临时文件
        inputFile.delete();
        return outputFileName;
    }

    /**
     * 压缩视频
     */
    @PostMapping("/compressionVideo")
    public Object compressionVideo(@RequestParam MultipartFile file) {

        String location = multipartProperties.getLocation();

        // 生成上传视频的临时文件
        File inputFile = FileUtil.multipartFile2File(file, location);

        // 调用视频处理工具类


        CompressionAttributes compressionAttributes = new CompressionAttributes();
        // 设置视频压缩完成时的回调URL
        compressionAttributes.setProgressUrl("http://localhost:8999/file/callback?fileId=111111&a=456");

        // 设置视频压缩参数
        VideoAttributes videoAttributes = new VideoAttributes();
        videoAttributes.setMaxDuration(15);
        videoAttributes.setMaxFps(20);
        videoAttributes.setVideoSize(VideoSize.HD480);

        compressionAttributes.setVideoAttributes(videoAttributes);

        String outputFileName = fFmpegUtils.putCompressionTask(location, inputFile.getName(), compressionAttributes);

        return outputFileName;
    }

    /**
     * 压缩视频完成时的回调
     */
    @PostMapping("/callback")
    public Object callback(@RequestBody String info, @RequestParam("fileId") String fileId, @RequestParam("a") String a) {
        // 回调信息
        String[] split = info.split("/");

        // 回调参数 fileId,根据fileId查询数据库的上传临时文件名和下载临时文件名,进行文件上传和文件删除
        System.out.println(String.format("fileId为%s的文件已压缩完成", fileId));

        return null;
    }

    /**
     * 图片裁切
     */
    @PostMapping("/crop")
    public Object crop(@RequestParam MultipartFile file) {

        String location = multipartProperties.getLocation();

        // 生成上传图片的临时文件
        File inputFile = FileUtil.multipartFile2File(file, location);

        // 调用图片处理工具类
        // 裁切成3000x1200的图后,修改分辨率为宽800的图(高度按比例缩小)
        CropAttributes cropAttributes = new CropAttributes(3000, 1200, 1000, 500);
        ResizeAttributes resizeAttributes = new ResizeAttributes(800, null);
        String outputFileName = imageMagickUtils.cropAndResize(location, inputFile.getName(), cropAttributes, resizeAttributes);

        // 删除上传图片的临时文件
        inputFile.delete();
        return outputFileName;
    }

    /**
     * 图片分辨率修改
     */
    @PostMapping("/resize")
    public Object resize(@RequestParam MultipartFile file) {

        String location = multipartProperties.getLocation();

        // 生成上传图片的临时文件
        File inputFile = FileUtil.multipartFile2File(file, location);

        // 调用图片处理工具类
        ResizeAttributes resizeAttributes = new ResizeAttributes(800, null);
        String outputFileName = imageMagickUtils.resize(location, inputFile.getName(), resizeAttributes, Suffix.JPG);

        // 删除上传图片的临时文件
        inputFile.delete();
        return outputFileName;
    }

}

FileUtil

import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.util.UUID;

public class FileUtil {

    /**
     * 将上传的MultipartFile转化为File
     */
    public static File multipartFile2File(MultipartFile multipartFile, String directory) {
        String suffix = getSuffix(multipartFile.getOriginalFilename());
        File tempFile = null;
        try {
            tempFile = new File(directory + "/" + UUID.randomUUID().toString() + suffix);
            multipartFile.transferTo(tempFile);
        } catch (IOException e) {
            throw new RuntimeException("multipartFile转File失败", e);
        }
        return tempFile;
    }

    /**
     * 获取文件拓展名
     */
    public static String getSuffix(String fileName) {
        if (fileName == null) {
            throw new RuntimeException("获取文件拓展名失败");
        }
        int index = fileName.lastIndexOf(".");
        if (-1 == index) {
            throw new RuntimeException("获取文件拓展名失败");
        }
        return fileName.substring(index);
    }

}

文档

图片工具ImageMagickUtils

方法

1.图片裁切后修改分辨率并指定输出文件格式

cropAndResize(tempDirectory,inputFileName,cropAttributes,resizeAttributes,outputFileSuffix)

2.图片裁切后修改分辨率

cropAndResize(tempDirectory,inputFileName,cropAttributes,resizeAttributes)

3.图片裁切并指定输出文件格式

crop(tempDirectory,inputFileName,cropAttributes,outputFileSuffix)

4.图片裁切

crop(tempDirectory,inputFileName,cropAttributes)

5.图片修改分辨率并指定输出文件格式

resize(tempDirectory,inputFileName,resizeAttributes,outputFileSuffix)

6.图片修改分辨率

resize(tempDirectory,inputFileName,resizeAttributes)

参数介绍

输入参数
参数 类型 必需 注释
tempDirectory String 是 临时文件目录
inputFileName String 是 输入文件名
cropAttributes CropAttributes 否 裁切参数
resizeAttributes ResizeAttributes 否 修改分辨率参数
outputFileSuffix Suffix 否 输出文件格式,未设置则同输入文件格式

其中:

CropAttributes

参数 类型 必需 注释
width Integer 是 裁切图片的宽
height Integer 是 裁切图片的高
leftOffset Integer 是 距左边偏移量
topOffset Integer 是 距顶部偏移量

ResizeAttributes

参数 类型 必需 注释
width Integer 否 输出图片的宽,只填写宽则高自适应
height Integer 否 输出图片的高,只填写高则宽自适应
quality Integer 否 输出图片的质量,范围0~100,默认100
输出参数
参数 类型 必需 注释
outputFileName String 是 输出文件名

视频工具FFmpegUtils

方法

1.获取视频信息

getInfo(tempDirectory,inputFileName)

输入参数
参数 类型 必需 注释
tempDirectory String 是 临时文件目录
inputFileName String 是 输入文件名
输出参数
参数 类型 必需 注释
format FFFormat 是 文件信息
videoInfo VideoInfo 是 视频信息
audioInfo AudioInfo 是 音频信息

其中:

FFFormat

参数 类型 必需 注释
filename String 是 文件名全路径名
duration String 是 文件时长
size String 是 文件大小
bitRate String 是 文件比特率

VideoInfo

参数 类型 必需 注释
codecName String 是 视频 编码名称
codecType String 是 类型 video
width Integer 是 视频 宽度
height Integer 是 视频 高度
frameRate Integer 是 视频 帧率
duration Integer 是 视频 时长
bitRate Integer 是 视频 比特率
nbFrames Integer 是 视频 总帧数

AudioInfo

参数 类型 必需 注释
codecName String 是 音频 编码名称
codecType String 是 类型 audio
duration Integer 是 音频 时长
bitRate Integer 是 音频 比特率
sampleRate Integer 是 音频 采样率
channels Integer 是 音频 声道数 1:单声道 2:双声道
2.截取视频封面

createCover(tempDirectory, inputFileName, outputFileSuffix)

createCover(tempDirectory, inputFileName)

输入参数
参数 类型 必需 注释
tempDirectory String 是 临时文件目录
inputFileName String 是 输入文件名
outputFileSuffix Suffix 否 输出文件格式,默认jpg
输出参数
参数 类型 必需 注释
outputFileName String 是 输出文件名
3.视频压缩

putCompressionTask(tempDirectory, inputFileName, compressionAttributes)

putCompressionTask(tempDirectory, inputFileName, compressionAttributes, outputFileName)

输入参数
参数 类型 必需 注释
tempDirectory String 是 临时文件目录
inputFileName String 是 输入文件名
compressionAttributes CompressionAttributes 是 压缩参数
outputFileName String 否 输出文件名,默认UUID生成

其中:

CompressionAttributes

参数 类型 必需 注释
videoAttributes VideoAttributes 否 视频压缩参数
audioAttributes AudioAttributes 否 音频压缩参数
progressUrl String 是 压缩完成后的回调地址

VideoAttributes

参数 类型 必需 注释
codec VideoCodec 否 视频编码(默认libx264,libx265)
maxFps Integer 否 最大帧率
videoSize VideoSize 否 视频分辨率(hd480,hd720,hd1080,800x800)
maxDuration Integer 否 最大时长
maxBitRate Integer 否 视频最大比特率

AudioAttributes

参数 类型 必需 注释
maxBitRate Integer 否 音频最大比特率
maxSamplingRate Integer 否 音频最大采样率
输出参数
参数 类型 必需 注释
outputFileName String 是 输出文件名

ImageMagick官网

http://www.imagemagick.com.cn/

命令行

图片裁切

magick 1.jpg -crop 3000x1200+1000+500 2.jpg

1.jpg 为6000x4500的图片

3000x1200 裁切后图片的宽x高

+1000 裁切横坐标偏移量

+500 裁切纵坐标偏移量

2.jpg 为裁切后的3000x1200的图片

image

图片压缩

指定分辨率压缩
magick 1.jpg -resize 3000x2250 2.jpg
给定宽度,高度自动选择以保留宽高比。
magick 1.jpg -resize 3000 2.jpg
给定高度,自动选择宽度以保留宽高比。
magick 1.jpg -resize x2250 2.jpg

FFmpeg官网

https://ffmpeg.org/ffmpeg.html#Advanced-options

命令行

查询视频信息

ffprobe -v quiet -print_format json -show_format -show_streams 1.mp4

设置帧率 -r

ffmpeg –i input.mp4 –r fps output.mp4

设置码率 音频:-b:a 视频: - b:v

ffmpeg -i input.avi -b:v 1500k output.mp4

设置分辨率

ffmpeg -i input.mp4 -s 320x240 output.mp4

设置声道和采样率

-ac 1 设置声道数为1
-ar 48000 设置采样率为48000Hz

截取视频生成图片

从第-ss秒开始,每秒截取-r张图片,持续-t秒,使用-s进行缩放,保存为foo-001.jpeg, foo-002.jpeg...
ffmpeg -i 1.mp4 -ss 5 -r 1 -t 1 -s hd480 -f image2 foo-%03d.jpeg

网上的开源框架

https://github.com/a-schild/jave2

网上的相关资料

https://www.jianshu.com/p/e14bc2551cfd
https://www.jianshu.com/p/3c8c4a892f3c
https://blog.csdn.net/u010629285/article/details/102998555

最后编辑于 :
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

友情链接更多精彩内容