mirror of
https://github.com/pion/mediadevices.git
synced 2025-09-26 20:41:46 +08:00
WIP
This commit is contained in:
101
rtp.go
Normal file
101
rtp.go
Normal file
@@ -0,0 +1,101 @@
|
||||
package mediadevices
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/pion/mediadevices/pkg/codec"
|
||||
"github.com/pion/mediadevices/pkg/prop"
|
||||
"github.com/pion/mediadevices/pkg/io/video"
|
||||
"github.com/pion/rtcp"
|
||||
"github.com/pion/rtp"
|
||||
"github.com/pion/webrtc/v2"
|
||||
)
|
||||
|
||||
type RTPTracker struct {
|
||||
videoEncoders []codec.VideoEncoderBuilder
|
||||
audioEncoders []codec.AudioEncoderBuilder
|
||||
}
|
||||
|
||||
type RTPTrackerOption func(*RTPTracker)
|
||||
|
||||
func WithVideoEncoders(codecs ...codec.VideoEncoderBuilder) func(*RTPTracker) {
|
||||
return func(tracker *RTPTracker) {
|
||||
tracker.videoEncoders = codecs
|
||||
}
|
||||
}
|
||||
|
||||
func WithAudioEncoders(codecs ...codec.AudioEncoderBuilder) func(*RTPTracker) {
|
||||
return func(tracker *RTPTracker) {
|
||||
tracker.audioEncoders = codecs
|
||||
}
|
||||
}
|
||||
|
||||
func NewRTPTracker(opts ...RTPTrackerOption) *RTPTracker {
|
||||
var tracker RTPTracker
|
||||
|
||||
for _, opt := range opts {
|
||||
opt(&tracker)
|
||||
}
|
||||
|
||||
return &tracker
|
||||
}
|
||||
|
||||
func (tracker *RTPTracker) Track(track Track) *RTPTrack {
|
||||
rtpTrack := RTPTrack{
|
||||
Track: track,
|
||||
}
|
||||
|
||||
return &rtpTrack
|
||||
}
|
||||
|
||||
type RTPTrack struct {
|
||||
Track
|
||||
tracker *RTPTracker
|
||||
currentEncoder codec.ReadCloser
|
||||
currentParams RTPParameters
|
||||
lastProp prop.Media
|
||||
}
|
||||
|
||||
func (track *RTPTrack) SetParameters(params RTPParameters) error {
|
||||
var err error
|
||||
|
||||
switch t := track.Track.(type) {
|
||||
case *VideoTrack:
|
||||
err = track.setParametersVideo(t, ¶ms)
|
||||
case *AudioTrack:
|
||||
err = track.setParametersAudio(t, ¶ms)
|
||||
default:
|
||||
err = fmt.Errorf("unsupported track type")
|
||||
}
|
||||
|
||||
if err == nil {
|
||||
track.currentParams = params
|
||||
}
|
||||
|
||||
return err
|
||||
}
|
||||
|
||||
func (track *RTPTrack) setParametersVideo(videoTrack *VideoTrack, params *RTPParameters) error {
|
||||
if params.SelectedCodec.Type != webrtc.RTPCodecTypeVideo {
|
||||
return fmt.Errorf("invalid selected RTP codec type. Expected video but got audio")
|
||||
}
|
||||
|
||||
video.DetectChanges(interval time.Duration, onChange func(prop.Media))
|
||||
return nil
|
||||
}
|
||||
|
||||
func (track *RTPTrack) setParametersAudio(audioTrack *AudioTrack, params *RTPParameters) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (track *RTPTrack) ReadRTP() (*rtp.Packet, error) {
|
||||
if track.currentEncoder == nil {
|
||||
return nil, fmt.Errorf("Encoder has not been specified. Please call SetParameters to specify.")
|
||||
}
|
||||
|
||||
return nil, nil
|
||||
}
|
||||
|
||||
func (track *RTPTrack) WriteRTCP(packet rtcp.Packet) error {
|
||||
return nil
|
||||
}
|
9
track.go
9
track.go
@@ -3,7 +3,6 @@ package mediadevices
|
||||
import (
|
||||
"fmt"
|
||||
"image"
|
||||
"math/rand"
|
||||
"sync"
|
||||
|
||||
"github.com/pion/mediadevices/pkg/driver"
|
||||
@@ -24,7 +23,6 @@ const (
|
||||
// Reference: https://w3c.github.io/mediacapture-main/#mediastreamtrack
|
||||
type Track interface {
|
||||
ID() string
|
||||
SSRC() uint32
|
||||
Kind() TrackKind
|
||||
Stop()
|
||||
// OnEnded registers a handler to receive an error from the media stream track.
|
||||
@@ -197,7 +195,6 @@ func (track *AudioTrack) Transform(fns ...audio.TransformFunc) {
|
||||
type baseTrack struct {
|
||||
d driver.Driver
|
||||
constraints MediaTrackConstraints
|
||||
ssrc uint32
|
||||
|
||||
onErrorHandler func(error)
|
||||
err error
|
||||
@@ -206,17 +203,13 @@ type baseTrack struct {
|
||||
}
|
||||
|
||||
func newBaseTrack(d driver.Driver, constraints MediaTrackConstraints) baseTrack {
|
||||
return baseTrack{d: d, constraints: constraints, ssrc: rand.Uint32()}
|
||||
return baseTrack{d: d, constraints: constraints}
|
||||
}
|
||||
|
||||
func (t *baseTrack) ID() string {
|
||||
return t.d.ID()
|
||||
}
|
||||
|
||||
func (t *baseTrack) SSRC() uint32 {
|
||||
return t.ssrc
|
||||
}
|
||||
|
||||
// OnEnded sets an error handler. When a track has been created and started, if an
|
||||
// error occurs, handler will get called with the error given to the parameter.
|
||||
func (t *baseTrack) OnEnded(handler func(error)) {
|
||||
|
62
webrtc.go
62
webrtc.go
@@ -1,43 +1,45 @@
|
||||
package mediadevices
|
||||
|
||||
import (
|
||||
"github.com/pion/mediadevices/pkg/codec"
|
||||
"github.com/pion/rtcp"
|
||||
"github.com/pion/rtp"
|
||||
"github.com/pion/webrtc/v2"
|
||||
)
|
||||
|
||||
// PeerConnection is an extension of webrtc.PeerConnection which allows to operate with raw video/audio
|
||||
type PeerConnection struct {
|
||||
*webrtc.PeerConnection
|
||||
audioEncoders []codec.AudioEncoderBuilder
|
||||
videoEncoders []codec.VideoEncoderBuilder
|
||||
// == WebRTC v3 design ==
|
||||
|
||||
// Reader is an interface to handle incoming RTP stream.
|
||||
type Reader interface {
|
||||
ReadRTP() (*rtp.Packet, error)
|
||||
WriteRTCP(rtcp.Packet) error
|
||||
}
|
||||
|
||||
// PeerConnectionOption is a function that configures the underlying PeerConnection
|
||||
type PeerConnectionOption func(*PeerConnection)
|
||||
|
||||
func WithVideoEncoders(encoders ...codec.VideoEncoderBuilder) PeerConnectionOption {
|
||||
return PeerConnectionOption(func(pc *PeerConnection) {
|
||||
pc.videoEncoders = encoders
|
||||
})
|
||||
// TrackBase represents common MediaStreamTrack functionality of LocalTrack and RemoteTrack.
|
||||
type TrackBase interface {
|
||||
ID() string
|
||||
}
|
||||
|
||||
func WithAudioEncoders(encoders ...codec.AudioEncoderBuilder) PeerConnectionOption {
|
||||
return PeerConnectionOption(func(pc *PeerConnection) {
|
||||
pc.audioEncoders = encoders
|
||||
})
|
||||
type LocalRTPTrack interface {
|
||||
TrackBase
|
||||
Reader
|
||||
|
||||
// SetParameters sets information about how the data is to be encoded.
|
||||
// This will be called by PeerConnection according to the result of
|
||||
// SDP based negotiation.
|
||||
// It will be called via RTPSender.Parameters() by PeerConnection to
|
||||
// tell the negotiated media codec information.
|
||||
//
|
||||
// This is pion's extension to process data without having encoder/decoder
|
||||
// in webrtc package.
|
||||
SetParameters(RTPParameters) error
|
||||
}
|
||||
|
||||
func ExtendPeerConnection(pc *webrtc.PeerConnection, opts ...PeerConnectionOption) (*PeerConnection, error) {
|
||||
extPC := PeerConnection{
|
||||
PeerConnection: pc,
|
||||
}
|
||||
|
||||
for _, opt := range opts {
|
||||
opt(&extPC)
|
||||
}
|
||||
|
||||
return &extPC, nil
|
||||
}
|
||||
|
||||
func (pc *PeerConnection) ExtAddTransceiverFromTrack(track Track, init ...webrtc.RtpTransceiverInit) (*webrtc.RTPTransceiver, error) {
|
||||
// RTPParameters represents RTCRtpParameters which contains information about
|
||||
// how the RTC data is to be encoded/decoded.
|
||||
//
|
||||
// ref: https://developer.mozilla.org/en-US/docs/Web/API/RTCRtpSendParameters
|
||||
type RTPParameters struct {
|
||||
SSRC uint32
|
||||
SelectedCodec *webrtc.RTPCodec
|
||||
Codecs []*webrtc.RTPCodec
|
||||
}
|
||||
|
Reference in New Issue
Block a user