基于ffmpeg使用java实现视频转图片

什么是ffmpeg?

ffmpeg下载安装教程及介绍-CSDN博客

安装后具体实现代码:

java 复制代码
package com.example.playing;

/**
 * @author : 冯子达
 * @version 1.0
 * @description :视频转换为图片 输入视频文件名和文件唯一标识 输出的是图片数量,在本方法里面完成文件夹的创建
 * @createDate : 2024/12/6 07:50
 */

import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;

public class VideoToImages {


    /**
     * 每秒生成多少张图片
     */
    private static Integer fps = 24;
    /**
     * 存放视频和图片的文件夹资源根目录
     */
    private static String Path = "D:\\devopment_project\\java_project\\playing\\src\\main\\resources\\";

    /**
     * 将视频转换为图片
     * <p>
     * 视频存放在 video\\videoName.mp4
     * <p>
     * 分割后存储在 images\\videoId 文件夹中
     * 图片的生成名为:output%d.jpg
     *
     * @param videoId   视频的ID
     * @param videoName 视频文件的名 例如 videoName.mp4
     * @return 生成的图片数用于后面判断,如果是0,则代表失败
     */
    public static int videoToCreateImages(String videoId, String videoName) {

//        创建完成目录
        File completedir = new File( Path+"images\\" + videoId);

        // 检查是否创建目录
        boolean completeSuccess = completedir.mkdir();
        if (completeSuccess) {
            System.out.println("目录创建成功!");
        } else {
            System.out.println("目录创建失败");
            return 0;
        }
        String videoPath = Path+"video\\" + videoName;
        // 输出图片的路径前缀(每张图片将使用前缀+序号.jpg的格式)
        String outputPrefix = completedir +"\\output%d.jpg";

        // 构建FFmpeg命令
        ProcessBuilder builder = new ProcessBuilder(
                "ffmpeg",
                "-i", videoPath, // 输入文件
                "-vf", "fps="+fps, // 每秒fps帧
                outputPrefix // 输出文件(使用%d表示帧编号)
        );
        builder.redirectErrorStream(true); // 将错误输出合并到标准输出

        try {
            Process process = builder.start();
            // 读取命令的输出(可选,用于调试或捕获FFmpeg的输出)
            BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream()));
            String line;
            while ((line = reader.readLine()) != null) {
                System.out.println(line);
            }
            // 等待进程结束
            int exitCode = process.waitFor();
            System.out.println("FFmpeg process exited with code " + exitCode);
            return countTopLevelFiles(completedir);
        } catch (InterruptedException | IOException e) {
            e.printStackTrace();
            return 0;
        }
    }

    /**
     * 统计指定目录下的一级文件数量
     *
     * @param dir 目录名
     * @return
     */
    public static int countTopLevelFiles(File dir) {
        int count = 0;
        // 检查目录是否存在
        if (dir.exists() && dir.isDirectory()) {
            // 获取目录下的所有文件和子目录
            File[] files = dir.listFiles();

            if (files != null) {
                for (File file : files) {
                    // 如果是文件,则增加计数器
                    if (file.isFile()) {
                        count++;
                    }
                }
            }
        }
        return count;
    }
}
相关推荐
好学且牛逼的马13 分钟前
从“Oak”到“虚拟线程”:JDK 1.0到25演进全记录与核心知识点详解a
java·开发语言·python
追随者永远是胜利者16 分钟前
(LeetCode-Hot100)62. 不同路径
java·算法·leetcode·职场和发展·go
好学且牛逼的马18 分钟前
从“XML汪洋”到“智能原生”:Spring Framework 1.x 到 7.x 演进全记录与核心知识点详解(超详细版)
java
追随者永远是胜利者18 分钟前
(LeetCode-Hot100)56. 合并区间
java·算法·leetcode·职场和发展·go
追随者永远是胜利者27 分钟前
(LeetCode-Hot100)55. 跳跃游戏
java·算法·leetcode·游戏·go
知识即是力量ol1 小时前
Java 虚拟机:JVM篇
java·jvm·八股
快乐zbc1 小时前
苍穹外卖 - 菜品起售/停售复习笔记
java·笔记
Cosmoshhhyyy1 小时前
《Effective Java》解读第41条:用标记接口定义类型
java·开发语言
Anastasiozzzz2 小时前
深入浅出:理解控制反转 (IoC) 与 Spring 的核心实现
java·后端·spring
前路不黑暗@2 小时前
Java项目:Java脚手架项目的 B 端用户服务(十四)
android·java·开发语言·spring boot·笔记·学习·spring cloud