hls source: support proxying H265 and Opus tracks
This commit is contained in:
parent
3f7009f72a
commit
f837ba6a83
|
@ -13,7 +13,7 @@ Live streams can be published to the server with:
|
|||
|RTSP servers and cameras|UDP, UDP-Multicast, TCP, RTSPS|H264, H265, VP8, VP9, AV1, MPEG2, M-JPEG, MP3, MPEG4 Audio (AAC), Opus, G711, G722, LPCM and any RTP-compatible codec|
|
||||
|RTMP clients (OBS Studio)|RTMP, RTMPS|H264, H265, MPEG4 Audio (AAC)|
|
||||
|RTMP servers and cameras|RTMP, RTMPS|H264, MPEG4 Audio (AAC)|
|
||||
|HLS servers and cameras|Low-Latency HLS, MP4-based HLS, legacy HLS|H264, MPEG4 Audio (AAC)|
|
||||
|HLS servers and cameras|Low-Latency HLS, MP4-based HLS, legacy HLS|H264, H265, MPEG4 Audio (AAC), Opus|
|
||||
|Raspberry Pi Cameras||H264|
|
||||
|
||||
And can be read from the server with:
|
||||
|
|
|
@ -83,6 +83,18 @@ func (s *hlsSource) run(ctx context.Context) error {
|
|||
}
|
||||
})
|
||||
|
||||
case *format.H265:
|
||||
c.OnData(track, func(pts time.Duration, dat interface{}) {
|
||||
err := stream.writeData(medi, ctrack, &formatprocessor.DataH265{
|
||||
PTS: pts,
|
||||
AU: dat.([][]byte),
|
||||
NTP: time.Now(),
|
||||
})
|
||||
if err != nil {
|
||||
s.Log(logger.Warn, "%v", err)
|
||||
}
|
||||
})
|
||||
|
||||
case *format.MPEG4Audio:
|
||||
c.OnData(track, func(pts time.Duration, dat interface{}) {
|
||||
err := stream.writeData(medi, ctrack, &formatprocessor.DataMPEG4Audio{
|
||||
|
@ -94,6 +106,18 @@ func (s *hlsSource) run(ctx context.Context) error {
|
|||
s.Log(logger.Warn, "%v", err)
|
||||
}
|
||||
})
|
||||
|
||||
case *format.Opus:
|
||||
c.OnData(track, func(pts time.Duration, dat interface{}) {
|
||||
err := stream.writeData(medi, ctrack, &formatprocessor.DataOpus{
|
||||
PTS: pts,
|
||||
Frame: dat.([]byte),
|
||||
NTP: time.Now(),
|
||||
})
|
||||
if err != nil {
|
||||
s.Log(logger.Warn, "%v", err)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -39,7 +39,9 @@ func codecParametersGenerate(track format.Format) string {
|
|||
func codecParametersAreSupported(codecs string) bool {
|
||||
for _, codec := range strings.Split(codecs, ",") {
|
||||
if !strings.HasPrefix(codec, "avc1.") &&
|
||||
!strings.HasPrefix(codec, "mp4a.") {
|
||||
!strings.HasPrefix(codec, "hvc1.") &&
|
||||
!strings.HasPrefix(codec, "mp4a.") &&
|
||||
codec != "opus" {
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,12 @@
|
|||
//nolint:gochecknoinits,revive,gocritic
|
||||
package fmp4
|
||||
|
||||
import (
|
||||
gomp4 "github.com/abema/go-mp4"
|
||||
)
|
||||
|
||||
func BoxTypeHvc1() gomp4.BoxType { return gomp4.StrToBoxType("hvc1") }
|
||||
|
||||
func init() {
|
||||
gomp4.AddAnyTypeBoxDef(&gomp4.VisualSampleEntry{}, BoxTypeHvc1())
|
||||
}
|
|
@ -76,7 +76,6 @@ func (i *Init) Unmarshal(byts []byte) error {
|
|||
if state != waitingCodec {
|
||||
return nil, fmt.Errorf("unexpected box 'avc1'")
|
||||
}
|
||||
|
||||
state = waitingAvcC
|
||||
|
||||
case "avcC":
|
||||
|
@ -116,7 +115,7 @@ func (i *Init) Unmarshal(byts []byte) error {
|
|||
}
|
||||
state = waitingTrak
|
||||
|
||||
case "hev1":
|
||||
case "hev1", "hvc1":
|
||||
if state != waitingCodec {
|
||||
return nil, fmt.Errorf("unexpected box 'hev1'")
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue