Skip to content

Commit 5181acb

Browse files
committed
Updated encoder
1 parent 8b30ed0 commit 5181acb

File tree

5 files changed

+99
-45
lines changed

5 files changed

+99
-45
lines changed

encoder.go

Lines changed: 24 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import (
44

55
// Packages
66
"fmt"
7+
"io"
78

89
ff "github.com/mutablelogic/go-media/sys/ffmpeg61"
910

@@ -15,10 +16,11 @@ import (
1516
// TYPES
1617

1718
type encoder struct {
18-
t MediaType
19-
ctx *ff.AVCodecContext
20-
stream *ff.AVStream
21-
packet *ff.AVPacket
19+
t MediaType
20+
ctx *ff.AVCodecContext
21+
stream *ff.AVStream
22+
packet *ff.AVPacket
23+
next_pts int64
2224
}
2325

2426
////////////////////////////////////////////////////////////////////////////////
@@ -78,19 +80,22 @@ func newEncoder(ctx *ff.AVFormatContext, stream_id int, param Parameters) (*enco
7880
codecctx.SetSampleFormat(sampleformat)
7981
}
8082

81-
// Choose sample rate
82-
if samplerate, err := ff.AVCodec_supported_samplerate(codec, par.audiopar.Samplerate); err != nil {
83-
ff.AVCodec_free_context(codecctx)
84-
return nil, err
85-
} else {
86-
codecctx.SetSampleRate(samplerate)
87-
}
83+
// TODO Choose sample rate
84+
codecctx.SetSampleRate(par.audiopar.Samplerate)
8885

89-
// Choose channel layout
90-
if channellayout, err := ff.AVCodec_supported_channellayout(codec, par.audiopar.Ch); err != nil {
91-
ff.AVCodec_free_context(codecctx)
92-
return nil, err
93-
} else if err := codecctx.SetChannelLayout(channellayout); err != nil {
86+
// TODO
87+
//if samplerate, err := ff.AVCodec_supported_samplerate(codec, par.audiopar.Samplerate); err != nil {
88+
// ff.AVCodec_free_context(codecctx)
89+
// return nil, err
90+
//}
91+
92+
// TODO Choose channel layout
93+
//if channellayout, err := ff.AVCodec_supported_channellayout(codec, par.audiopar.Ch); err != nil {
94+
// ff.AVCodec_free_context(codecctx)
95+
// return nil, err
96+
//}
97+
98+
if err := codecctx.SetChannelLayout(par.audiopar.Ch); err != nil {
9499
ff.AVCodec_free_context(codecctx)
95100
return nil, err
96101
}
@@ -174,8 +179,7 @@ func (encoder *encoder) Close() error {
174179
// PRIVATE METHODS
175180

176181
func (encoder *encoder) encode(fn MuxFunc) (*ff.AVPacket, error) {
177-
packet, err := fn(encoder.stream.Id())
178-
if packet != nil {
179-
}
180-
182+
// TODO
183+
fmt.Println("TODO: encode - get packet")
184+
return nil, io.EOF
181185
}

packet.go

Lines changed: 31 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,13 @@ import (
1111
// TYPES
1212

1313
type packetmeta struct {
14-
StreamIndex int `json:"stream_index" writer:",width:10,right"`
15-
MediaType ff.AVMediaType `json:"media_type" writer:",width:20"`
16-
Size int `json:"size,omitempty" writer:",width:7,right"`
17-
Pts ff.AVTimestamp `json:"pts,omitempty" writer:",width:9,right"`
18-
TimeBase ff.AVRational `json:"time_base,omitempty" writer:",width:10,right"`
19-
Duration ff.AVTimestamp `json:"duration,omitempty" writer:",width:10,right"`
20-
Pos *int64 `json:"pos,omitempty" writer:",width:10,right"`
14+
Stream int `json:"stream" writer:",width:10,right"`
15+
MediaType ff.AVMediaType `json:"media_type" writer:",width:20"`
16+
Size int `json:"size,omitempty" writer:",width:7,right"`
17+
Pts int64 `json:"pts,omitempty" writer:",width:9,right"`
18+
TimeBase ff.AVRational `json:"time_base,omitempty" writer:",width:10,right"`
19+
Duration int64 `json:"duration,omitempty" writer:",width:10,right"`
20+
Pos *int64 `json:"pos,omitempty" writer:",width:10,right"`
2121
}
2222

2323
type packet struct {
@@ -34,15 +34,15 @@ func newPacket(ctx *ff.AVPacket, stream int, t ff.AVMediaType, timeBase ff.AVRat
3434
pkt := &packet{
3535
ctx: ctx,
3636
packetmeta: packetmeta{
37-
StreamIndex: stream,
38-
MediaType: t,
37+
Stream: stream,
38+
MediaType: t,
3939
},
4040
}
4141
if ctx != nil {
4242
pkt.packetmeta.Size = ctx.Size()
43-
pkt.packetmeta.Pts = ff.AVTimestamp(ctx.Pts())
43+
pkt.packetmeta.Pts = ctx.Pts()
4444
pkt.packetmeta.TimeBase = timeBase
45-
pkt.packetmeta.Duration = ff.AVTimestamp(ctx.Duration())
45+
pkt.packetmeta.Duration = ctx.Duration()
4646
if ctx.Pos() != -1 {
4747
pos := ctx.Pos()
4848
pkt.packetmeta.Pos = &pos
@@ -62,3 +62,23 @@ func (packet *packet) String() string {
6262
data, _ := json.MarshalIndent(packet, "", " ")
6363
return string(data)
6464
}
65+
66+
////////////////////////////////////////////////////////////////////////////////
67+
// PROPERTIES
68+
69+
func (packet *packet) Id() int {
70+
return packet.packetmeta.Stream
71+
}
72+
73+
func (packet *packet) Type() MediaType {
74+
switch packet.packetmeta.MediaType {
75+
case ff.AVMEDIA_TYPE_AUDIO:
76+
return AUDIO
77+
case ff.AVMEDIA_TYPE_VIDEO:
78+
return VIDEO
79+
case ff.AVMEDIA_TYPE_SUBTITLE:
80+
return SUBTITLE
81+
default:
82+
return DATA
83+
}
84+
}

sys/ffmpeg61/avcodec_core.go

Lines changed: 24 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -105,14 +105,35 @@ func AVCodec_is_decoder(codec *AVCodec) bool {
105105

106106
// Return a supported sample format that is closest to the given sample format.
107107
func AVCodec_supported_sampleformat(codec *AVCodec, samplefmt AVSampleFormat) (AVSampleFormat, error) {
108-
for _, fmt := range codec.SampleFormats() {
108+
first := AV_SAMPLE_FMT_NONE
109+
for i, fmt := range codec.SampleFormats() {
109110
if fmt == samplefmt {
110111
return samplefmt, nil
111112
}
113+
if i == 0 {
114+
first = fmt
115+
}
116+
}
117+
// Return an error and the first supported sample format
118+
return first, fmt.Errorf("sample format %v is not supported by codec %q", samplefmt, codec.Name())
119+
}
120+
121+
// Return a supported pixel format that is closest to the given pixel format.
122+
func AVCodec_supported_pixelformat(codec *AVCodec, pixelfmt AVPixelFormat) (AVPixelFormat, error) {
123+
first := AV_PIX_FMT_NONE
124+
for i, fmt := range codec.PixelFormats() {
125+
if fmt == pixelfmt {
126+
return pixelfmt, nil
127+
}
128+
if i == 0 {
129+
first = fmt
130+
}
112131
}
113-
return AVSampleFormat(AV_SAMPLE_FMT_NONE), fmt.Errorf("sample format %v is not supported by codec %q", samplefmt, codec.Name())
132+
// Return an error and the first supported sample format
133+
return first, fmt.Errorf("pixel format %v is not supported by codec %q", pixelfmt, codec.Name())
114134
}
115135

136+
/*
116137
// Return a supported sample rate that is closest to the given sample rate.
117138
func AVCodec_supported_samplerate(codec *AVCodec, samplerate int) (int, error) {
118139
max := 0
@@ -139,8 +160,4 @@ func AVCodec_supported_channellayout(codec *AVCodec, channellayout AVChannelLayo
139160
}
140161
}
141162
}
142-
143-
// Return a supported pixel format that is closest to the given pixel format.
144-
func AVCodec_supported_pixelformat(AVCodec *codec, AVPixelFormat pixelformat) (AVPixelFormat, error) {
145-
146-
}
163+
*/

sys/ffmpeg61/avcodec_encoding.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,9 @@ import (
99
// CGO
1010

1111
/*
12-
#cgo pkg-config: libavcodec
12+
#cgo pkg-config: libavcodec libavformat
1313
#include <libavcodec/avcodec.h>
14+
#include <libavformat/avformat.h>
1415
#include <stdlib.h>
1516
*/
1617
import "C"

writer.go

Lines changed: 18 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -217,17 +217,24 @@ FOR_LOOP:
217217
}
218218

219219
// Find the first encoder which should return a packet
220-
next_time := 0
221-
next_stream := 0
222-
for stream := range encoders {
223-
if next_time == 0 || encoder.nextTime() < next_time {
224-
next_time = encoder.nextTime()
220+
var next_encoder *encoder
221+
var next_stream int
222+
for stream, encoder := range encoders {
223+
// Initialise the next encoder
224+
if next_encoder == nil {
225+
next_encoder = encoder
226+
next_stream = stream
227+
continue
228+
}
229+
// Compare
230+
if !compareNextPts(next_encoder, encoder) {
231+
next_encoder = encoder
225232
next_stream = stream
226233
}
227234
}
228235

229236
// Get a packet from the encoder
230-
packet, err := encoders[next_stream].encode(fn)
237+
packet, err := next_encoder.encode(fn)
231238
if errors.Is(err, io.EOF) {
232239
break FOR_LOOP
233240
} else if err != nil {
@@ -261,6 +268,11 @@ FOR_LOOP:
261268
return ctx.Err()
262269
}
263270

271+
// Returns true if a.next_pts is greater than b.next_pts
272+
func compareNextPts(a, b *encoder) bool {
273+
return ff.AVUtil_compare_ts(a.next_pts, a.stream.TimeBase(), b.next_pts, b.stream.TimeBase()) > 0
274+
}
275+
264276
/*
265277
while (1) {
266278
AVStream *in_stream, *out_stream;

0 commit comments

Comments
 (0)