package test;
import java.awt.Dimension;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Rectangle;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.TreeSet;
import javax.imageio.ImageIO;
import org.bytedeco.javacv.FFmpegFrameGrabber;
import org.bytedeco.javacv.Frame;
import org.bytedeco.javacv.Java2DFrameConverter;
public class VideoTest {
public static String image_type="jpg";
public static String file_type="mp4";
public static void main(String[] args) {
String videofile="C:/xmqtest/test视频.mp4";//或网络视频地址
String framefileDir="C:/xmqtest/";
String targetFilePath=fetchFrame(videofile,framefileDir);
}
/**
* 获取指定视频的帧并保存为图片至指定目录
* @param videofile 源视频文件路径
* @param framefile 截取帧的图片存放路径
* @throws Exception
*/
public static String fetchFrame(String videofile, String framefileDir){
try{
int startIndex=videofile.lastIndexOf('/');
String fileName;
if(startIndex==-1){
fileName=videofile.substring(videofile.lastIndexOf('\\')+1, videofile.lastIndexOf('.'));
}else{
fileName=videofile.substring(startIndex+1, videofile.lastIndexOf('.')+1);
}
String targetFileName=framefileDir+fileName+image_type;
File targetFile=createFile(targetFileName);
FFmpegFrameGrabber ff = new FFmpegFrameGrabber(videofile);
ff.start();
String rotate_old=ff.getVideoMetadata("rotate");//视频旋转角度,可能是null
int length = ff.getLengthInFrames();
int i = 0;
Frame f = null;
while (i < length) {
// 过滤前5帧,避免出现全黑的图片,依自己情况而定
f = ff.grabFrame();
if ((i > 5) && (f.image != null)) {
break;
}
i++;
}
// IplImage img = f.image;
int owidth = f.imageWidth;
int oheight = f.imageHeight;
// 对截取的帧进行等比例缩放
int width = 300;//生成图片宽度为300px
int height = (int) (((double) width / owidth) * oheight);
Java2DFrameConverter converter = new Java2DFrameConverter();
BufferedImage fecthedImage = converter.getBufferedImage(f);
BufferedImage bi = new BufferedImage(width, height, BufferedImage.TYPE_3BYTE_BGR);
bi.getGraphics().drawImage(fecthedImage.getScaledInstance(width, height, Image.SCALE_SMOOTH),
0, 0, null);
ImageIO.write(bi, image_type, targetFile);
ff.stop();
//有需要旋转
if(rotate_old!=null && !rotate_old.isEmpty()){
int rotate=Integer.parseInt(rotate_old);
rotatePhonePhoto(targetFileName,rotate);
}
return targetFileName;
}catch(Exception e){
e.printStackTrace();
}
return null;
}/***
* 创建文件,目录不存在则先创建目录在创建文件
* @param destFileName
* @return
*/
public static File createFile(String destFileName) {
try {
File file = new File(destFileName);
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
file.createNewFile();
return file;
} catch (IOException e) {
e.printStackTrace();
return null;
}
}
/**
* 删除单个文件
*/
public static void deleteFile(String sPath) {
File file = new File(sPath);
if (file.isFile() && file.exists()) {
file.delete();
}
}
/**
* 旋转照片
*
* @return
*/
public static String rotatePhonePhoto(String fullPath, int angel) {
BufferedImage src;
try {
src = ImageIO.read(new File(fullPath));
int src_width = src.getWidth(null);
int src_height = src.getHeight(null);
int swidth = src_width;
int sheight = src_height;
if (angel == 90 || angel == 270) {
swidth = src_height;
sheight = src_width;
}
Rectangle rect_des = new Rectangle(new Dimension(swidth, sheight));
BufferedImage res = new BufferedImage(rect_des.width, rect_des.height, BufferedImage.TYPE_INT_RGB);
Graphics2D g2 = res.createGraphics();
g2.translate((rect_des.width - src_width) / 2, (rect_des.height - src_height) / 2);
g2.rotate(Math.toRadians(angel), src_width / 2, src_height / 2);
g2.drawImage(src, null, null);
ImageIO.write(res,image_type, new File(fullPath));
} catch (Exception e) {
e.printStackTrace();
}
return fullPath;
}
}
说明点:
1、加入依赖,经测试两个依赖在windows环境,linux环境下正常使用。如果本地windows环境正常但是在linux下失败,请使用以下依赖。
org.bytedeco
javacv
1.4.3
org.bytedeco.javacpp-presets
ffmpeg-platform
4.0.2-1.4.3
2、针对iphone手机视频等需要进行首帧图片旋转,否则出现首帧图片横着的情况。如代码部分:
String rotate_old=ff.getVideoMetadata("rotate");//视频旋转角度,可能是null
vue 截取视频第一帧
最近自己写项目,在项目中涉及功能点又截取视频帧的点:需求澄清:移动端封面展示,平台上传图片(多张上传)取第一张上传图片为封面图:如上传视频则截取视频第一帧作为封面图: 实现思路:h5 video标签 ...
php ffmpeg截取视频第一帧保存为图片的方法
php ffmpeg截取视频第一帧保存为图片的方法
$xiangmupath = $this->getxiangmupath(); $filename = 'chengs ...
使用javacv 截取视频指定帧节
个人博客 地址:https://www.wenhaofan.com/article/20190407105818 引入依赖 org. ...
Java截取视频文件缩略图
/** * 截取视频第0帧的图片 */public static void videoImage(String filePath, String fileName,int widthdist, int ...
java获取视频的第一帧
//------------maven配置文件--------------- org.bytedeco
【Java SE】使用Javacv截取视频图片
[Java Web开发学习]使用Javacv截取视频图片 转载:https://www.cnblogs.com/yangchongxing/p/9482935.html github地址:https: ...
用java实现给图片增加图片水印或者文字水印(也支持视频图像帧添加水印)
javaCV图像处理系列: javaCV图像处理之1:实时视频添加文字水印并截取视频图像保存成图片,实现文字水印的字体.位置.大小.粗度.翻转.平滑等操作 javaCV图像处理之2:实时视频添加图片水 ...
java获取视频播第一帧
FFMPEG 功能很强大,做视频必备的软件.大家可通过 http://ffmpeg.org/ 了解.Windows版本的软件,可通过 http://ffmpeg.zeranoe.com/builds/ ...
python opencv 按一定间隔截取视频帧
前言关于opencvOpenCV 是 Intel 开源计算机视觉库 (Computer Version) .它由一系列 C 函数和少量 C++ 类构成,实现了图像处理和计算机视觉方面的很多通用算法. ...
随机推荐
GCD定时器
// // ViewController.m // GCD 定时器 // // #import "ViewController.h" NSInteger count = ; @in ...
【转~】初识贝塞尔曲线(B&#233;zier curve)
本文图文大多转自http://www.html-js.com/article/1628 QAQ我居然去扒维基,,,看不懂啊,,,我要去补数学,,, 在做变形小鸡的时候用到CSS3 transition ...
一次有趣的XSS漏洞挖掘分析(3)最终篇
这真是最后一次了.真的再不逗这个程序员了.和预期一样,勤奋的程序员今天又更新程序了.因为前面写的payload都有一个致命的弱点,就是document.write()会完全破坏DOM结构.而且再“完事 ...
修改Delphi工具控件的默认字体
修改Delphi工具控件的默认字体: 注册表: Delphi 6: HKEY_CURRENT_USER\Software\Borland\Delphi\6.0Delphi 7: HKEY_ ...
Coreseek:部门查询和增量索引代替实时索引
1.行业调查 索引系统需要通过主查询来获取所有的文档信息,一个简单的实现是整个表的数据到内存,但是这可能会导致整个表被锁定,并且使其它操作被阻止(例如:在MyISAM格款式上INSERT操作).同时, ...
[Find the last digit when factorial of A divides factorial of B]
Given two numbers A and B. The task is to compute the last digit of the resulting F, where F= B! / A ...
Divisibility by 25 CodeForces - 988E (技巧的暴力)
You are given an integer nn from 11 to 10181018 without leading zeroes. In one move you can swap any ...
2. Java内存区域
Java 虚拟机的内存模型分为两部分:一部分是线程共享的,包括 Java 堆和方法区:另一部分是线程私有的,包括虚拟机栈和本地方法栈,以及程序计数器这一小部分内存 2.1 程序计数器 程序计数器(Pr ...
(推荐)Skyline调用WMTS服务接口
文章地址 http://blog.csdn.net/chaiqi/article/details/9302373 供大家学习参考.
【kmp算法】uva11475 Extend to Palindrome
就把每个串倒过来,和原串匹配,看最后能匹配多少就行. #include #include #include ...