Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Smaller frames #3607

Merged
merged 21 commits into from
Jan 5, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 2 additions & 4 deletions src/core/builtins/builtins_ffmpeg_bitstream_filters.ml
Original file line number Diff line number Diff line change
Expand Up @@ -83,9 +83,7 @@ let process (type a) ~put_data ~(mk_params : a mk_params)
} ))
packets
in
let data =
{ Ffmpeg_content_base.params = Some (mk_params params); data; length }
in
let data = { Content.Video.params = Some (mk_params params); data; length } in
let data = Ffmpeg_copy_content.lift_data data in
put_data generator data

Expand Down Expand Up @@ -121,7 +119,7 @@ let on_data (type a)
a handler) ~put_data ~(get_params : a get_params)
~(get_packet : a get_packet) ~(mk_params : a mk_params)
~(mk_packet : a mk_packet) ~generator
({ Ffmpeg_content_base.params; data } : Ffmpeg_copy_content.data) =
({ Content.Video.params; data } : Ffmpeg_copy_content.data) =
List.iter
(fun (_, { Ffmpeg_copy_content.stream_idx; time_base; packet }) ->
let handler =
Expand Down
19 changes: 9 additions & 10 deletions src/core/builtins/builtins_ffmpeg_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@ let decode_audio_frame ~field ~mode generator =
| `Frame frame ->
let data, params =
match Ffmpeg_copy_content.get_data frame with
| { Ffmpeg_content_base.data; params = Some (`Audio params) } ->
| { Content.Video.data; params = Some (`Audio params) } ->
(data, params)
| _ -> assert false
in
Expand Down Expand Up @@ -165,7 +165,7 @@ let decode_audio_frame ~field ~mode generator =

function
| `Frame frame ->
let { Ffmpeg_content_base.data; params } =
let { Content.Video.data; params } =
Ffmpeg_raw_content.Audio.get_data frame
in
let data =
Expand All @@ -181,14 +181,14 @@ let decode_audio_frame ~field ~mode generator =

let convert
: 'a 'b.
get_data:(Content.data -> ('a, 'b) Ffmpeg_content_base.content) ->
get_data:(Content.data -> ('a, 'b) Content_video.Base.content) ->
decoder:([ `Frame of Content.data | `Flush ] -> unit) ->
[ `Frame of Frame.t | `Flush ] ->
unit =
fun ~get_data ~decoder -> function
| `Frame frame ->
let frame = Frame.get frame field in
let { Ffmpeg_content_base.data; _ } = get_data frame in
let { Content.Video.data; _ } = get_data frame in
if data = [] then () else decoder (`Frame frame)
| `Flush -> decoder `Flush
in
Expand Down Expand Up @@ -253,8 +253,7 @@ let decode_video_frame ~field ~mode generator =
Ffmpeg_utils.unpack_image ~width:internal_width ~height:internal_height
(InternalScaler.convert scaler data)
in
let data = Video.Canvas.single_image img in
let data = Content.Video.lift_data data in
let data = Content.Video.lift_image (Video.Canvas.Image.make img) in
Generator.put generator field data
in

Expand Down Expand Up @@ -318,7 +317,7 @@ let decode_video_frame ~field ~mode generator =
| `Frame frame ->
let data, params =
match Ffmpeg_copy_content.get_data frame with
| { Ffmpeg_content_base.data; params = Some (`Video params) } ->
| { Content.Video.data; params = Some (`Video params) } ->
(data, params)
| _ -> assert false
in
Expand Down Expand Up @@ -364,7 +363,7 @@ let decode_video_frame ~field ~mode generator =
let last_params = ref None in
function
| `Frame frame ->
let { Ffmpeg_content_base.data; _ } =
let { Content.Video.data; _ } =
Ffmpeg_raw_content.Video.get_data frame
in
let data =
Expand All @@ -385,14 +384,14 @@ let decode_video_frame ~field ~mode generator =

let convert
: 'a 'b.
get_data:(Content.data -> ('a, 'b) Ffmpeg_content_base.content) ->
get_data:(Content.data -> ('a, 'b) Content_video.Base.content) ->
decoder:([ `Frame of Content.data | `Flush ] -> unit) ->
[ `Frame of Frame.t | `Flush ] ->
unit =
fun ~get_data ~decoder -> function
| `Frame frame ->
let frame = Frame.get frame field in
let { Ffmpeg_content_base.data; _ } = get_data frame in
let { Content.Video.data; _ } = get_data frame in
if data = [] then () else decoder (`Frame frame)
| `Flush -> decoder `Flush
in
Expand Down
27 changes: 13 additions & 14 deletions src/core/builtins/builtins_ffmpeg_encoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ let encode_audio_frame ~source_idx ~type_t ~mode ~opts ?codec ~format
} ))
packets
in
let data = { Ffmpeg_content_base.params; data; length } in
let data = { Content.Video.params; data; length } in
let data = Ffmpeg_copy_content.lift_data data in
Generator.put generator field data
| None -> ()
Expand Down Expand Up @@ -160,7 +160,7 @@ let encode_audio_frame ~source_idx ~type_t ~mode ~opts ?codec ~format
} ))
frames
in
let data = { Ffmpeg_content_base.params; data; length } in
let data = { Content.Video.params; data; length } in
let data = Ffmpeg_raw_content.Audio.lift_data data in
Generator.put generator field data
| None -> ())
Expand Down Expand Up @@ -294,7 +294,7 @@ let encode_video_frame ~source_idx ~type_t ~mode ~opts ?codec ~format ~field
} ))
packets
in
let data = { Ffmpeg_content_base.params; data; length } in
let data = { Content.Video.params; data; length } in
let data = Ffmpeg_copy_content.lift_data data in
Generator.put generator field data
| None -> ()
Expand Down Expand Up @@ -350,7 +350,7 @@ let encode_video_frame ~source_idx ~type_t ~mode ~opts ?codec ~format ~field
} ))
frames
in
let data = { Ffmpeg_content_base.params; data; length } in
let data = { Content.Video.params; data; length } in
let data = Ffmpeg_raw_content.Video.lift_data data in
Generator.put generator field data
| None -> ())
Expand All @@ -368,17 +368,16 @@ let encode_video_frame ~source_idx ~type_t ~mode ~opts ?codec ~format ~field

function
| `Frame frame ->
let vstart = 0 in
let vstop = VFrame.position frame in
let vbuf = VFrame.data frame in
for i = vstart to vstop - 1 do
let f = Video.Canvas.render vbuf i in
let vdata = Ffmpeg_utils.pack_image f in
let frame = InternalScaler.convert (Option.get !scaler) vdata in
Avutil.Frame.set_pts frame (Some !nb_frames);
nb_frames := Int64.succ !nb_frames;
encode_ffmpeg_frame frame
done
List.iter
(fun (_, img) ->
let f = Video.Canvas.Image.render img in
let vdata = Ffmpeg_utils.pack_image f in
let frame = InternalScaler.convert (Option.get !scaler) vdata in
Avutil.Frame.set_pts frame (Some !nb_frames);
nb_frames := Int64.succ !nb_frames;
encode_ffmpeg_frame frame)
vbuf.Content.Video.data
| `Flush -> encode_frame `Flush

let mk_encoder mode =
Expand Down
40 changes: 26 additions & 14 deletions src/core/decoder/decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ type fps = Decoder_utils.fps = { num : int; den : int }
type buffer = {
generator : Generator.t;
put_pcm : ?field:Frame.field -> samplerate:int -> Content.Audio.data -> unit;
put_yuva420p : ?field:Frame.field -> fps:fps -> Content.Video.data -> unit;
put_yuva420p : ?field:Frame.field -> fps:fps -> Video.Canvas.image -> unit;
}

type decoder = {
Expand Down Expand Up @@ -240,7 +240,7 @@ let test_file ?(log = log) ?mimes ?extensions fname =
ext_ok || mime_ok)

let channel_layout audio =
Lazy.force Content.(Audio.(get_params audio).Content.channel_layout)
Lazy.force Content.(Audio.(get_params audio).Content.Audio.channel_layout)

let can_decode_type decoded_type target_type =
let map_convertible cur (field, target_field) =
Expand Down Expand Up @@ -451,16 +451,28 @@ let mk_buffer ~ctype generator =
let out_freq =
Decoder_utils.{ num = Lazy.force Frame.video_rate; den = 1 }
in
fun ~fps (data : Content.Video.data) ->
let data = Array.map video_scale data in
let data = video_resample ~in_freq:fps ~out_freq data in
let len = Video.Canvas.length data in
let data =
Content.Video.lift_data
~length:(Frame_settings.main_of_video len)
data
in
Generator.put generator field data)
let params =
{
Content.Video.width = Some Frame.video_width;
height = Some Frame.video_height;
}
in
let interval = Frame.main_of_video 1 in
fun ~fps img ->
match video_resample ~in_freq:fps ~out_freq img with
| [] -> ()
| data ->
let data =
List.mapi
(fun i img -> (i * interval, video_scale img))
data
in
let length = List.length data * interval in
let buf =
Content.Video.lift_data
{ Content.Video.params; length; data }
in
Generator.put generator field buf)
else fun ~fps:_ _ -> ()
in
Hashtbl.add video_handlers field handler;
Expand All @@ -471,8 +483,8 @@ let mk_buffer ~ctype generator =
get_audio_handler ~field ~samplerate data
in

let put_yuva420p ?(field = Frame.Fields.video) ~fps data =
get_video_handler ~field ~fps data
let put_yuva420p ?(field = Frame.Fields.video) ~fps img =
get_video_handler ~field ~fps img
in

{ generator; put_pcm; put_yuva420p }
Expand Down
4 changes: 2 additions & 2 deletions src/core/decoder/decoder.mli
Original file line number Diff line number Diff line change
Expand Up @@ -49,8 +49,8 @@ type fps = { num : int; den : int }
- Implicit content drop *)
type buffer = {
generator : Generator.t;
put_pcm : ?field:Frame.field -> samplerate:int -> Content.Audio.data -> unit;
put_yuva420p : ?field:Frame.field -> fps:fps -> Content.Video.data -> unit;
put_pcm : ?field:Frame.field -> samplerate:int -> Audio.t -> unit;
put_yuva420p : ?field:Frame.field -> fps:fps -> Video.Canvas.image -> unit;
}

type decoder = {
Expand Down
17 changes: 8 additions & 9 deletions src/core/decoder/decoder_utils.ml
Original file line number Diff line number Diff line change
Expand Up @@ -108,30 +108,29 @@ let video_resample ~in_freq ~out_freq =
* which o: nearest neighbour in the currently available buffer.
* This is not as good as nearest neighbour in the real stream.
*
* Turns out the same code codes for when out_freq>in_freq too. *)
* Turns out the same code codes for when out_freq>in_freq works too. *)
let in_pos = ref 0 in
let in_freq = in_freq.num * out_freq.den
and out_freq = out_freq.num * in_freq.num in
let ratio = out_freq / in_freq in
fun input off len ->
let new_in_pos = !in_pos + len in
fun img ->
let new_in_pos = !in_pos + 1 in
let already_out_len = !in_pos * ratio in
let needed_out_len = new_in_pos * ratio in
let out_len = needed_out_len - already_out_len in
in_pos := new_in_pos mod in_freq;
Array.init out_len (fun i -> input.(off + (i * ratio)))
List.init out_len (fun _ -> img)

let video_resample () =
let state = ref None in
let exec resampler data = resampler data 0 (Video.Canvas.length data) in
fun ~in_freq ~out_freq (data : Content.Video.data) : Content.Video.data ->
if in_freq = out_freq then data
fun ~in_freq ~out_freq img ->
if in_freq = out_freq then [img]
else (
match !state with
| Some (resampler, _in_freq, _out_freq)
when in_freq = _in_freq && out_freq = _out_freq ->
exec resampler data
resampler img
| _ ->
let resampler = video_resample ~in_freq ~out_freq in
state := Some (resampler, in_freq, out_freq);
exec resampler data)
resampler img)
4 changes: 2 additions & 2 deletions src/core/decoder/decoder_utils.mli
Original file line number Diff line number Diff line change
Expand Up @@ -59,5 +59,5 @@ val video_resample :
unit ->
in_freq:fps ->
out_freq:fps ->
Content.Video.data ->
Content.Video.data
Video.Canvas.image ->
Video.Canvas.image list
2 changes: 1 addition & 1 deletion src/core/decoder/ffmpeg_copy_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ let mk_decoder ~stream_idx ~stream_time_base ~mk_packet ~put_data params =
} ))
packets
in
let data = { Ffmpeg_content_base.params = Some params; data; length } in
let data = { Content.Video.params = Some params; data; length } in
let data = Ffmpeg_copy_content.lift_data data in
put_data buffer.Decoder.generator data
with Empty | Corrupt (* Might want to change that later. *) -> ()
Expand Down
3 changes: 1 addition & 2 deletions src/core/decoder/ffmpeg_internal_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -159,10 +159,9 @@ let mk_video_decoder ~width ~height ~stream ~field codec =
let pixel_aspect = Av.get_pixel_aspect stream in
let cb ~buffer frame =
let img = scale frame in
let content = Video.Canvas.single img in
buffer.Decoder.put_yuva420p ~field
~fps:{ Decoder.num = target_fps; den = 1 }
content;
img;
let metadata = Avutil.Frame.metadata frame in
if metadata <> [] then
Generator.add_metadata buffer.Decoder.generator
Expand Down
2 changes: 1 addition & 1 deletion src/core/decoder/ffmpeg_raw_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ let mk_decoder ~stream_idx ~stream_time_base ~mk_params ~lift_data ~put_data
frames
in
let data =
{ Ffmpeg_content_base.params = mk_params params; data; length }
{ Content.Video.params = mk_params params; data; length }
in
let data = lift_data data in
put_data buffer.Decoder.generator data
Expand Down
3 changes: 1 addition & 2 deletions src/core/decoder/gstreamer_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -138,9 +138,8 @@ let create_decoder ?(merge_tracks = false) _ ~width ~height ~channels ~mode
let y_stride = round4 width in
let uv_stride = round4 (width / 2) in
let img = Image.YUV420.make_data width height buf y_stride uv_stride in
let stream = Video.Canvas.single_image img in
let fps = { Decoder.num = Lazy.force Frame.video_rate; den = 1 } in
buffer.Decoder.put_yuva420p ~fps stream);
buffer.Decoder.put_yuva420p ~fps (Video.Canvas.Image.make img));
GU.flush ~log gst.bin
in
let seek off =
Expand Down
24 changes: 16 additions & 8 deletions src/core/decoder/image_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -119,16 +119,24 @@ let create_decoder ~ctype ~width ~height ~metadata img =
let remaining () =
if !duration = -1 then -1 else Frame.main_of_video !duration
in
let generator =
Content.Video.make_generator
(Content.Video.get_params (Frame.Fields.find Frame.Fields.video ctype))
in
let fread length =
let frame = Frame.create ~length ctype in
let video = Content.Video.get_data (Frame.get frame Frame.Fields.video) in
for i = 0 to Frame.video_of_main length - 1 do
Video.Canvas.set video i img
done;
match Frame.Fields.find_opt Frame.Fields.audio frame with
let frame = Frame.create ~length Frame.Fields.empty in
let video =
Content.Video.generate
~create:(fun ~pos:_ ~width:_ ~height:_ () -> img)
generator length
in
let frame =
Frame.set_data frame Frame.Fields.video Content.Video.lift_data video
in
match Frame.Fields.find_opt Frame.Fields.audio ctype with
| None -> frame
| Some data ->
let pcm = Content.Audio.get_data data in
| Some format ->
let pcm = Content.Audio.get_data (Content.make ~length format) in
Audio.clear pcm 0 (Frame.audio_of_main length);
Frame.set_data frame Frame.Fields.audio Content.Audio.lift_data pcm
in
Expand Down
4 changes: 2 additions & 2 deletions src/core/decoder/liq_ogg_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -170,14 +170,14 @@ let create_decoder ?(merge_tracks = false) source input =
in
let video_feed track buf =
let info, _ = Ogg_decoder.video_info decoder track in
let rgb = video_convert video_scale buf in
let img = video_convert video_scale buf in
let fps =
{
Decoder.num = info.Ogg_decoder.fps_numerator;
den = info.Ogg_decoder.fps_denominator;
}
in
buffer.Decoder.put_yuva420p ~fps (Video.Canvas.single_image rgb)
buffer.Decoder.put_yuva420p ~fps (Video.Canvas.Image.make img)
in
let decode_audio, decode_video =
if decode_audio && decode_video then
Expand Down
2 changes: 1 addition & 1 deletion src/core/decoder/midi_decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ let () =
(fun ~metadata:_ ~ctype:_ _ ->
Some
(Frame.Fields.make
~midi:Content.(Midi.lift_params { Content.channels = 16 })
~midi:Content.(Midi.lift_params { Content.Midi.channels = 16 })
()));
file_decoder =
Some (fun ~metadata:_ ~ctype filename -> decoder ~ctype filename);
Expand Down
2 changes: 1 addition & 1 deletion src/core/encoder/encoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ let type_of_format f =
assert (channels > 0);
let params =
{
Content.channel_layout =
Content.Audio.channel_layout =
lazy
(Audio_converter.Channel_layout.layout_of_channels
channels);
Expand Down
Loading
Loading