From 78ea8010afc1d711e99b1f403f2d9679dfc4bed2 Mon Sep 17 00:00:00 2001 From: "Steinar H. Gunderson" Date: Sat, 11 May 2019 16:47:33 +0200 Subject: [PATCH] Refactor out a function for adding the end of EffectChains. --- nageru/theme.cpp | 100 ++++++++++++++++++++++++----------------------- 1 file changed, 52 insertions(+), 48 deletions(-) diff --git a/nageru/theme.cpp b/nageru/theme.cpp index ed99e5f..aa2d59a 100644 --- a/nageru/theme.cpp +++ b/nageru/theme.cpp @@ -193,6 +193,57 @@ string checkstdstring(lua_State *L, int index) return string(cstr, len); } +void add_outputs_and_finalize(EffectChain *chain, bool is_main_chain) +{ + // Add outputs as needed. + // NOTE: If you change any details about the output format, you will need to + // also update what's given to the muxer (HTTPD::Mux constructor) and + // what's put in the H.264 stream (sps_rbsp()). + ImageFormat inout_format; + inout_format.color_space = COLORSPACE_REC_709; + + // Output gamma is tricky. We should output Rec. 709 for TV, except that + // we expect to run with web players and others that don't really care and + // just output with no conversion. So that means we'll need to output sRGB, + // even though H.264 has no setting for that (we use “unspecified”). + inout_format.gamma_curve = GAMMA_sRGB; + + if (is_main_chain) { + YCbCrFormat output_ycbcr_format; + // We actually output 4:2:0 and/or 4:2:2 in the end, but chroma subsampling + // happens in a pass not run by Movit (see ChromaSubsampler::subsample_chroma()). + output_ycbcr_format.chroma_subsampling_x = 1; + output_ycbcr_format.chroma_subsampling_y = 1; + + // This will be overridden if HDMI/SDI output is in force. + if (global_flags.ycbcr_rec709_coefficients) { + output_ycbcr_format.luma_coefficients = YCBCR_REC_709; + } else { + output_ycbcr_format.luma_coefficients = YCBCR_REC_601; + } + + output_ycbcr_format.full_range = false; + output_ycbcr_format.num_levels = 1 << global_flags.x264_bit_depth; + + GLenum type = global_flags.x264_bit_depth > 8 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_BYTE; + + chain->add_ycbcr_output(inout_format, OUTPUT_ALPHA_FORMAT_POSTMULTIPLIED, output_ycbcr_format, YCBCR_OUTPUT_SPLIT_Y_AND_CBCR, type); + + // If we're using zerocopy video encoding (so the destination + // Y texture is owned by VA-API and will be unavailable for + // display), add a copy, where we'll only be using the Y component. + if (global_flags.use_zerocopy) { + chain->add_ycbcr_output(inout_format, OUTPUT_ALPHA_FORMAT_POSTMULTIPLIED, output_ycbcr_format, YCBCR_OUTPUT_INTERLEAVED, type); // Add a copy where we'll only be using the Y component. + } + chain->set_dither_bits(global_flags.x264_bit_depth > 8 ? 16 : 8); + chain->set_output_origin(OUTPUT_ORIGIN_TOP_LEFT); + } else { + chain->add_output(inout_format, OUTPUT_ALPHA_FORMAT_POSTMULTIPLIED); + } + + chain->finalize(); +} + int EffectChain_new(lua_State* L) { assert(lua_gettop(L) == 2); @@ -311,54 +362,7 @@ int EffectChain_finalize(lua_State* L) assert(lua_gettop(L) == 2); EffectChain *chain = (EffectChain *)luaL_checkudata(L, 1, "EffectChain"); bool is_main_chain = checkbool(L, 2); - - // Add outputs as needed. - // NOTE: If you change any details about the output format, you will need to - // also update what's given to the muxer (HTTPD::Mux constructor) and - // what's put in the H.264 stream (sps_rbsp()). - ImageFormat inout_format; - inout_format.color_space = COLORSPACE_REC_709; - - // Output gamma is tricky. We should output Rec. 709 for TV, except that - // we expect to run with web players and others that don't really care and - // just output with no conversion. So that means we'll need to output sRGB, - // even though H.264 has no setting for that (we use “unspecified”). - inout_format.gamma_curve = GAMMA_sRGB; - - if (is_main_chain) { - YCbCrFormat output_ycbcr_format; - // We actually output 4:2:0 and/or 4:2:2 in the end, but chroma subsampling - // happens in a pass not run by Movit (see ChromaSubsampler::subsample_chroma()). - output_ycbcr_format.chroma_subsampling_x = 1; - output_ycbcr_format.chroma_subsampling_y = 1; - - // This will be overridden if HDMI/SDI output is in force. - if (global_flags.ycbcr_rec709_coefficients) { - output_ycbcr_format.luma_coefficients = YCBCR_REC_709; - } else { - output_ycbcr_format.luma_coefficients = YCBCR_REC_601; - } - - output_ycbcr_format.full_range = false; - output_ycbcr_format.num_levels = 1 << global_flags.x264_bit_depth; - - GLenum type = global_flags.x264_bit_depth > 8 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_BYTE; - - chain->add_ycbcr_output(inout_format, OUTPUT_ALPHA_FORMAT_POSTMULTIPLIED, output_ycbcr_format, YCBCR_OUTPUT_SPLIT_Y_AND_CBCR, type); - - // If we're using zerocopy video encoding (so the destination - // Y texture is owned by VA-API and will be unavailable for - // display), add a copy, where we'll only be using the Y component. - if (global_flags.use_zerocopy) { - chain->add_ycbcr_output(inout_format, OUTPUT_ALPHA_FORMAT_POSTMULTIPLIED, output_ycbcr_format, YCBCR_OUTPUT_INTERLEAVED, type); // Add a copy where we'll only be using the Y component. - } - chain->set_dither_bits(global_flags.x264_bit_depth > 8 ? 16 : 8); - chain->set_output_origin(OUTPUT_ORIGIN_TOP_LEFT); - } else { - chain->add_output(inout_format, OUTPUT_ALPHA_FORMAT_POSTMULTIPLIED); - } - - chain->finalize(); + add_outputs_and_finalize(chain, is_main_chain); return 0; } -- 2.39.2