依赖 github.com/deepch/vdk 开源库
视频流生成图片部分 开源库使用cgo调用ffmpeg 需要安装对应的依赖软件
mac
brew install ffmpeg
ubuntu
apt install libavcodec-dev libavcodec-ffmpeg56 libavformat-dev libavformat-ffmpeg56
package main
import (
"fmt"
"github.com/deepch/vdk/av"
"github.com/deepch/vdk/cgo/ffmpeg"
"github.com/deepch/vdk/format/rtspv2"
"image/jpeg"
"log"
"os"
"time"
)
func main() {
client, err := rtspv2.Dial(rtspv2.RTSPClientOptions{
URL: "rtsp://root:123456@127.0.0.1",
Debug: false,
DisableAudio: false,
DialTimeout: 3 * time.Second,
ReadWriteTimeout: 3 * time.Second,
})
if err != nil {
fmt.Println(err)
return
}
defer client.Close()
if client.CodecData == nil {
return
}
AudioOnly := true
var videoIDX int
for i, codec := range client.CodecData {
if codec.Type().IsVideo() {
AudioOnly = false
videoIDX = i
break
}
}
var FrameDecoderSingle *ffmpeg.VideoDecoder
if !AudioOnly {
FrameDecoderSingle, err = ffmpeg.NewVideoDecoder(client.CodecData[videoIDX].(av.VideoCodecData))
if err != nil {
log.Fatalln("FrameDecoderSingle Error", err)
}
}
for {
select {
case signals := <-client.Signals:
switch signals {
case rtspv2.SignalStreamRTPStop:
return
default:
fmt.Println("111", signals)
}
case packetAV := <-client.OutgoingPacketQueue:
if packetAV.IsKeyFrame {
if pic, err := FrameDecoderSingle.DecodeSingle(packetAV.Data); err == nil && pic != nil {
if out, err := os.Create("./test.jpg"); err == nil {
if err = jpeg.Encode(out, &pic.Image, nil); err == nil {
log.Println("Poster Saved On Disk Ready ./output.jpg")
}
}
}
}
}
}
}