ffmpeg实现视频播放 ----------- Javacv

news2024/11/27 14:53:03

什么是Javacv和FFmpeg?
Javacv是一个专门为Java开发人员提供的计算机视觉库,它基于FFmpeg和Opencv库,提供了许多用于处理图
像、视频和音频的功能。FFmpeg是一个开源的音视频处理工具集,它提供了用于编码、解码、转换和播放音视频
文件的库和工具。

实现视频播放的步骤
要实现音视频同步播放,我们需要完成以下几个步骤
 1.加载音视频文件
 2.解码音视频流
 3.同步音视频播放
 4.染音视频数据

运行项目需要先导入pom依赖:

<properties>
        <javacpp.version>1.5.5</javacpp.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>

        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>

<!--        javaCV依赖-->
        <dependency>
            <groupId>org.bytedeco</groupId>
            <artifactId>javacv</artifactId>
            <version>${javacpp.version}</version>
        </dependency>
        <dependency>
            <groupId>org.bytedeco</groupId>
            <artifactId>javacv-platform</artifactId>
            <version>${javacpp.version}</version>
        </dependency>


    </dependencies>

1.加载音视频文件
首先,我们需要加载音视频文件。使用Javacv的FFmpegFrameGrabber类可以轻松地加载音视频文件。

​
String filePath = "path/to/video.mp4";
FFmpegFrameGrabber grabber = new FFmpegFrameGrabber(filePath);
grabber.start();

​

 2.解码音视频流
加载音视频文件后,我们需要解码音视频流。使用Javacv的Frame类可以轻松地解码音视频流。

​
Frame frame = nu11;
while ((frame = grabber.grabFrame()) != nul1) {
      //处理解码后的音视频数据
}

​

 3.同步音视频播放
在解码音视频流之后,我们需要确保音频和视频能够同步播放。通常情况下,音频和视频的时间截是不一致的,我们可以通过比较音频和视频的时间戳来判断两者之间的差异,并进行相应的调整。

​
        long audioPts = frame.timestamp;
        long videoPts = //从视频中获取时间
        long ptsDiff = audioPts - videoPts;
        if (ptsDiff > 0) {
            //音频时间较大,视频播放较慢,需要进行快进处理
        } else if (ptsDiff < 0) {
            //视频时间戳较大,音频播放较慢,需要进行快进处理
        } else {
            //音频和视频时间戳一致,正常播放
        }

​

 4.染音视频数据
最后,我们需要将解码后的音视频数据染到屏幕上。使用Javacv的CanvasFrame类可以创建一个窗口,并将音频和视频数据染到窗口上。

​
        CanvasFrame canvasFrame = new CanvasFrame("Video Player");
        canvasFrame.setcanvasSize(grabber.getImageWidth,grabber.getImageHeight());
        while((frame = grabber.grabFrame()) != nul1) {
            canvasFrame.showImage(frame);
        }

​

  完整示例代码
下面是一个完整的示例代码,演示如何使用Javacv和FFmpeg实现音视频同步播放:

import org.bytedeco.javacv.CanvasFrame;
import org.bytedeco.javacv.FFmpegFrameGrabber;
import org.bytedeco.javacv.Frame;
import org.bytedeco.javacv.FrameGrabber;


public class VideoPlayer {

    public static void main(String[] args) {
        String filePath = "d:/test/yq.mp4";
        FFmpegFrameGrabber grabber = new FFmpegFrameGrabber(filePath);
        try {
            grabber.start();
            CanvasFrame canvasFrame = new CanvasFrame("video Player");
            canvasFrame.setCanvasSize(grabber.getImageWidth(), grabber.getImageHeight());
            Frame frame = null;
            while ((frame = grabber.grabFrame()) != null) {
                canvasFrame.showImage(frame);
            }
            canvasFrame.dispose();
            grabber.stop();
        } catch (FrameGrabber.Exception e) {
            e.printStackTrace();
        }
    }

}

运行效果:

                              感谢大家的阅读,觉得有所帮助的朋友点点关注点点赞! 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1816285.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

MyBatis 参数上的处理的细节内容

1. MyBatis 参数上的处理的细节内容 文章目录 1. MyBatis 参数上的处理的细节内容2. MyBatis 参数上的处理3. 准备工作4. 单个(一个)参数4.1 单个(一个)简单类型作为参数4.2 单个(一个) Map集合 作为参数4.3 单个(一个) 实体类POJO作为参数 5. 多个参数5.1 Param注解(命名参数)…

免费学习通刷课(免费高分)Pro版

文章目录 概要整体架构流程小结 概要 关于上一版的免费高分的学习通刷课&#xff0c;有很多人觉得还得登录太复杂了&#xff0c;然后我又发现了个神脚本&#xff0c;操作简单&#xff0c;可以后台挂着&#xff0c;但是还是建议调整速度到2倍速&#xff0c;然后找到你该刷的课&…

论文图片颜色提取

论文绘图的时候有些颜色不知道怎么选取&#xff0c;参考其他论文&#xff0c;将其他论文中的颜色提取下来&#xff0c;用取色器识别出来&#xff0c;记录如下&#xff1a; 颜色代码&#xff1a;#BEAED4 190,174,212 颜色代码&#xff1a;#C4CBCB 196,203,203 颜色代码&am…

【JVM】之常见面试题

文章目录 1.JVM中的内存区域划分2.JVM的类加载机制2.1 加载2.2 验证2.3 准备2.4 解析2.5 初始化2.6 类加载的时机 3 类加载器4.双亲委派模型5.JVM中的垃圾回收策略5.1 找谁是垃圾5.1.1 引用计数法5.1.2 可达性分析法 5.2 释放垃圾5.2.1 标记清除算法5.2.2 复制算法5.2.3 标记整…

GoogleDeepMind联合发布医学领域大语言模型论文技术讲解

Towards Expert-Level Medical Question Answering with Large Language Mod 这是一篇由Google Research和DeepMind合作发表的论文,题为"Towards Expert-Level Medical Question Answering with Large Language Models"。 我先整体介绍下这篇论文的主要内容&#x…

[CAN] 创建解析CAN报文DBC文件教程

&#x1f449;本教程需要先安装CANdb软件&#xff0c;[CAN] DBC数据库编辑器的下载与安装 &#x1f64b;前言 DBC(全称为Database CAN)&#xff0c;是用于描述单个CAN网络中各逻辑节点的信息。 DBC是汽车ECU&#xff08;Electronic Control Unit&#xff0c;电子控制单元&…

批量文件重命名软件

因为日常用电脑的时候,经常都会遇到需要对当前目录下的文件,进行重命名。最好是按照自己的规则上来进行批量重命名。我试了几款软件,都感觉不是很好,不是要收费,就是各种乱七八糟的流氓广告。本想着干脆自己写算了,在绝望之际,找到了这款软件,亲测,确实还用,特别是满…

python 10个高频率的自动化脚本(干货,速度收藏)

1. 文件操作&#xff1a;自动备份文件 场景&#xff1a;每日自动备份重要文件到指定目录。 import shutilimport datetimedef backup_file(src, dst_folder): now datetime.datetime.now().strftime(%Y%m%d%H%M%S) dst_path f"{dst_folder}/backup_{now}_{src.s…

bugku---misc---ping

1、下载附件&#xff0c;解压后是一个流量包 2、用wireshark分析&#xff0c;发现都是清一色的icmp报文&#xff0c;只能看看内容。 3、点了几条流量&#xff0c;发现有个地方连起来是flag 4、最终将所有的拼起来&#xff0c;得到flag flag{dc76a1eee6e3822877ed627e0a04ab4a}…

CleanMyMac X软件最新版下载【安装详细图文教程】

​CleanMyMac X是一款专业的Mac清理软件&#xff0c;可智能清理mac磁盘垃圾和多余语言安装包&#xff0c;快速释放电脑内存&#xff0c;轻松管理和升级Mac上的应用&#xff0c;同时CleanMyMac X可以强力卸载恶意软件&#xff0c;修复系统漏洞&#xff0c;一键扫描和优化Mac系统…

nginx rewrite地址重写

常用的nginx正则表达式 ^匹配以...开头的字符串$匹配以...结尾的字符串^$^$表示空行*匹配前面的字符0次或者多次&#xff08;通配符*表示任意数量的任意字符&#xff09;匹配前面的字符1次或多次?匹配前面的字符0次或1次.匹配除了“\n”之外的任意单个字符&#xff0c;[.\n]表…

第十五届蓝桥杯大赛 国赛 pb组F题【括号与字母】(15分) 栈的应用

博客主页&#xff1a;誓则盟约系列专栏&#xff1a;IT竞赛 专栏关注博主&#xff0c;后期持续更新系列文章如果有错误感谢请大家批评指出&#xff0c;及时修改感谢大家点赞&#x1f44d;收藏⭐评论✍ 试题F:括号与字母 【问题描述】 给定一个仅包含小写字母和括号的字符串 S …

少有人走的低风险创业之路:一人公司

大家好&#xff0c;我是弗雷&#xff01;在前面的文章中&#xff0c;深入讨论了老板和员工思维的本质不同&#xff0c;非常值得普通人一看。接下来&#xff0c;我们将继续分享一人公司的话题。 一提到创业就认为风险很大&#xff1f; 只懂埋头苦干&#xff0c;不懂创新营销怎…

rocketmq-5.1.2的dleger高可用集群部署

1、背景 原先为5.0.0版本&#xff0c;因检查出有漏洞&#xff0c;升级到5.1.2版本。 【Rocketmq是阿里巴巴在2012年开发的分布式消息中间件&#xff0c;专为万亿级超大规模的消息处理而设计&#xff0c;具有高吞吐量、低延迟、海量堆积、顺序收发等特点。在一定条件下&#xf…

如何手动实现multiSetIfAbsent、multiExpire

👽System.out.println(“👋🏼嗨,大家好,我是代码不会敲的小符,目前工作于上海某电商服务公司…”); 📚System.out.println(“🎈如果文章中有错误的地方,恳请大家指正!共同进步,共同成长✊”); 🌟System.out.println(“💡如果文章对您有所帮助,希望您可以三…

C#操作MySQL从入门到精通(22)——创建表与操纵表

前言 我们新建数据库以后,最需要做的就是创建表,对数据库的操作绝大多数情况下都是都对表的操作,本文就是讲解如何创建表以及修改表中的列,修改表名等操作。由于创建表的方法基本上有两种,一种是使用带有界面的工具比如Navicate来创建表,另一种是使用sql语句来创建表,实…

rv1126-rv1109-串口显示路径不变化

串口只有#, 后来看了教程改成如下 但是没有变化,那个路径都只显示rootLonbon# 于是最后改成了这样 因为:

CSS函数: 实现数据限阈的数字函数

CSS函数中提供了几个比较实用的数字函数&#xff0c;它可以帮助我们实现一定的数学计算功能。常见的数字函数目前提供了五个&#xff1a;calc()、max()、min()和clamp()函数。其基本实现功能如下&#xff1a; calc()&#xff1a;允许在声明 CSS 属性值时执行一些计算。max()&a…

数据结构 —— 堆

1.堆的概念及结构 堆是一种特殊的树形数据结构&#xff0c;称为“二叉堆”&#xff08;binary heap&#xff09; 看它的名字也可以看出堆与二叉树有关系&#xff1a;其实堆就是一种特殊的二叉树 堆的性质&#xff1a; 堆中某个结点的值总是不大于或不小于其父结点的值&…

ColorEasyDuino上手指南

介绍 ColorEasyDuino是嘉立创推出的一块Aduino开发板&#xff08;类似物&#xff09;&#xff0c;具有丰富的外设接口&#xff1a;uart、i2c、spi、adc、pwm等&#xff1b;开发板设计参考原型是Arduino Uno&#xff0c;采用的芯片是ATMEGA328P&#xff0c;它的外观设计比较紧凑…