抓取在线视频流存到本地,同时截视频图

抓取在线视频流存到本地,同时截视频图

package ;
import org.bytedeco.javacpp.avcodec;
import org.bytedeco.javacv.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.annotation.Resource;
import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.atomic.AtomicBoolean;


/**
 * @ClassName testUrl1
 * @Author dell-pc
 * @create 2023/3/9 17:20
 */
public class videoFile {
    public static Logger logger = LoggerFactory.getLogger(videoFile.class);
    @Resource
    videoFile videoFile;
    //调用原子线程判断
    public static AtomicBoolean running = new AtomicBoolean(true);
    public String streamURL;// 流地址
    public String filePath;// 视频文件路径
    public String imagePath;// 图片路径,存放截取视频某一帧的图片
    public void setStreamURL(String streamURL) {
        this.streamURL = streamURL;
    }
    public void setFilePath(String filePath) {
        this.filePath = filePath;
    }
    public void setImagePath(String imagePath) {
        this.imagePath = imagePath;
    }


    public static void main(String[] args) throws InterruptedException {
        //getVideoStream();

        String dir= "videoAddress/"; //相对路径地址
        Boolean result = getStreamScreenshot(dir,dir,
                "视频流地址");
        System.out.println(result);

        videoFile videoUtil = new videoFile();
        Thread.sleep(500000);
        System.out.println("结束录制");
        videoUtil.running.set(false);

    }

    /**
     * 获取视频流快照
     * @param filePath
     * @param streamURL
     */
    public static Boolean getStreamScreenshot(String filePath,String imagePath,String streamURL){
        return getStream(filePath,imagePath,streamURL,true);
    }

    /**
     * 开始执行下拉流截视频流
     */
    public static Boolean getStream(String filePath,String imagePath,String streamURL,boolean screenshot){
        Boolean b = false ;
        videoFile videoUtil = new videoFile();
        videoUtil.setFilePath(filePath);
        videoUtil.setImagePath(imagePath);
        videoUtil.setStreamURL(streamURL);

        try {
            Thread t0 = new Thread(() -> {
               logger.info("开始录制");
                videoUtil.run(screenshot);
            });
            t0.start();
            b = true;
        } catch (Throwable t) {
            logger.error(t.getMessage());
            b = false;
            t.printStackTrace();
        }
        return b;
    }


    /**
     * 执行视频流抓取
     */
    public Boolean run(boolean screenshot) {
        Boolean b = false;
        Map<String,Object> map = new LinkedHashMap<>();
        // 获取视频源
        System.out.println(streamURL);
        FFmpegFrameGrabber grabber = new FFmpegFrameGrabber(streamURL);
        FFmpegFrameRecorder recorder = null;
        DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd-HH-mm-ss-SS");
        System.out.println("录制中..1");
        try {
            grabber.start();
            System.out.println("录制中..2");
            Frame frame = grabber.grabFrame();
            if (frame != null) {
                File outFile = new File(filePath);
                System.out.println("录制中..3");
                if (!outFile.isFile()) {
                    try {
                        outFile.createNewFile();
                    } catch (IOException e) {
                        System.out.println(e.toString());
                        logger.error(e.getMessage());
                        e.printStackTrace();
                        return  false;
                    }
                }
                Date date = Calendar.getInstance().getTime();
                String strDate = dateFormat.format(date);
                // 流媒体输出地址,分辨率(长,高),是否录制音频(0:不录制/1:录制)
                recorder = new FFmpegFrameRecorder(filePath+strDate+".mp4", 1920, 1440, 1);
                System.out.println("录制中..4");
                recorder.setVideoCodec(avcodec.AV_CODEC_ID_H264);// 直播流格式
                recorder.setFormat("MP4");// 录制的视频格式
                recorder.setFrameRate(30);// 帧数
                //百度翻译的比特率,默认400000,但是我400000贼模糊,调成800000比较合适
                recorder.setVideoBitrate(800000);
                System.out.println("录制中..5");
                recorder.start();
                int flag = 0;
                int i=0;
                while (frame != null && videoFile.running.get()) {
                    //视频快照
                    if(screenshot) {
                        if (flag%30==0&&i<20) {
                            date = Calendar.getInstance().getTime();
                            strDate = dateFormat.format(date);
                            frame = grabber.grabImage();
                            //文件储存对象
                            String fileName = imagePath + strDate +".jpg";
                            File outPut = new File(fileName);
                            ImageIO.write(FrameToBufferedImage(frame), "jpg", outPut);
                            map.put(fileName, outPut);
                            if (i == 20){
                                //结束视频快照
                                screenshot = false;
                            }
                            i++;
                        }
                    }

                    recorder.record(frame);// 录制
                    frame = grabber.grabFrame();// 获取下一帧
                    flag++;
                    System.out.println("录制中...");
                }
                recorder.record(frame);
                System.out.println("录制中..6");
                // 停止录制
                recorder.stop();
                grabber.stop();
                //视频文件地址
                b = true;

            }
        } catch (Exception e) {
            System.out.println(e.toString());
            logger.error(e.getMessage());
           return  false;
        }  finally {
            if (null != grabber) {
                try {
                    grabber.stop();
                } catch (FrameGrabber.Exception e) {
                    System.out.println(e.toString());
                    logger.error(e.getMessage());
                    return  false;
                }
            }
            if (recorder != null) {
                try {
                    recorder.stop();
                } catch (FrameRecorder.Exception e) {
                    System.out.println(e.toString());
                    e.printStackTrace();
                    logger.error(e.getMessage());
                    return  false;
                }
            }
        }
        videoFile.running.set(true);
        return  b ;
    }

    /**
     * frame 转图片流
     * @param frame
     * @return
     */
    public static BufferedImage FrameToBufferedImage(Frame frame) {
        //创建BufferedImage对象
        Java2DFrameConverter converter = new Java2DFrameConverter();
        BufferedImage bufferedImage = converter.getBufferedImage(frame);
        return bufferedImage;
    }


    /**
     * 获取视频流
     * @param filePath
     * @param streamURL
     */
    public static Boolean getVideoStream(String filePath,String imagePath,String streamURL){
        return getStream(filePath,imagePath,streamURL,false);
    }

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值