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

Handle keyframe request it in the encoder and use x264 defaults #111

Merged
merged 10 commits into from
Jul 10, 2024
Merged
5 changes: 4 additions & 1 deletion c_src/membrane_h264_ffmpeg_plugin/encoder.c
Original file line number Diff line number Diff line change
Expand Up @@ -153,7 +153,7 @@ static int get_frames(UnifexEnv *env, AVFrame *frame,
}

UNIFEX_TERM encode(UnifexEnv *env, UnifexPayload *payload, int64_t pts,
int use_shm, State *state) {
int use_shm, int keyframe_requested, State *state) {
UNIFEX_TERM res_term;
int res = 0;
int max_frames = 16, frame_cnt = 0;
Expand All @@ -165,6 +165,9 @@ UNIFEX_TERM encode(UnifexEnv *env, UnifexPayload *payload, int64_t pts,
frame->format = state->codec_ctx->pix_fmt;
frame->width = state->codec_ctx->width;
frame->height = state->codec_ctx->height;
if(keyframe_requested) {
frame->pict_type = AV_PICTURE_TYPE_I;
}
av_image_fill_arrays(frame->data, frame->linesize, payload->data,
frame->format, frame->width, frame->height, 1);

Expand Down
2 changes: 1 addition & 1 deletion c_src/membrane_h264_ffmpeg_plugin/encoder.spec.exs
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ spec create(

spec get_frame_size(state) :: {:ok :: label, frame_size :: int} | {:error :: label}

spec encode(payload, pts :: int64, use_shm :: bool, state) ::
spec encode(payload, pts :: int64, use_shm :: bool, keyframe_requested :: bool, state) ::
{:ok :: label, dts_list :: [int64], pts_list :: [int64], [payload]}
| {:error :: label, reason :: atom}

Expand Down
19 changes: 18 additions & 1 deletion lib/membrane_h264_ffmpeg/encoder.ex
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,7 @@ defmodule Membrane.H264.FFmpeg.Encoder do
state =
opts
|> Map.put(:encoder_ref, nil)
|> Map.put(:keyframe_requested?, false)

{[], state}
end
Expand All @@ -141,12 +142,13 @@ defmodule Membrane.H264.FFmpeg.Encoder do
buffer.payload,
pts,
use_shm?,
state.keyframe_requested?,
encoder_ref
) do
{:ok, dts_list, pts_list, frames} ->
bufs = wrap_frames(dts_list, pts_list, frames)

{bufs, state}
{bufs, %{state | keyframe_requested?: false}}

{:error, reason} ->
raise "Native encoder failed to encode the payload: #{inspect(reason)}"
Expand Down Expand Up @@ -194,6 +196,21 @@ defmodule Membrane.H264.FFmpeg.Encoder do
{actions, state}
end

@impl true
def handle_event(:input, event, _ctx, state) do
{[event: {:output, event}], state}
end

@impl true
def handle_event(:output, %Membrane.H264.FFmpeg.KeyframeRequestEvent{}, _ctx, state) do
{[], %{state | keyframe_requested?: true}}
end

@impl true
def handle_event(:output, event, _ctx, state) do
{[event: {:input, event}], state}
end

defp flush_encoder_if_exists(%{encoder_ref: nil}), do: []

defp flush_encoder_if_exists(%{encoder_ref: encoder_ref, use_shm?: use_shm?}) do
Expand Down
5 changes: 5 additions & 0 deletions lib/membrane_h264_ffmpeg/keyframe_request_event.ex
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
defmodule Membrane.H264.FFmpeg.KeyframeRequestEvent do
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done

@moduledoc false
@derive Membrane.EventProtocol
defstruct []
end
3 changes: 2 additions & 1 deletion test/encoder/encoder_native_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,8 @@ defmodule Encoder.NativeTest do
Enc.encode(
frame,
Common.to_h264_time_base_truncated(seconds(timestamp)),
false,
_use_shm? = false,
_keyframe_requested? = false,
ref
)
end
Expand Down