From 05ece5560e3251e0fc988d7a796a378365e98ceb Mon Sep 17 00:00:00 2001 From: Mathieu Duponchelle Date: Tue, 10 May 2022 18:50:33 +0200 Subject: [PATCH] tttocea608: expose roll-up timeout property In roll-up mode, when no more timed text comes in, the closed captions may remain displayed on screen indefinitely (unless the decoder implements a timeout, but that is not mandatory). Expose a property to erase the display memory after a configurable amount of time has elapsed instead. Part-of: --- video/closedcaption/src/tttocea608/imp.rs | 35 +++++++++++++++++++++++ 1 file changed, 35 insertions(+) diff --git a/video/closedcaption/src/tttocea608/imp.rs b/video/closedcaption/src/tttocea608/imp.rs index 77dc782d..76c0ef4d 100644 --- a/video/closedcaption/src/tttocea608/imp.rs +++ b/video/closedcaption/src/tttocea608/imp.rs @@ -94,6 +94,7 @@ struct Settings { mode: Cea608Mode, origin_row: i32, origin_column: u32, + roll_up_timeout: Option, } impl Default for Settings { @@ -102,6 +103,7 @@ impl Default for Settings { mode: DEFAULT_MODE, origin_row: DEFAULT_ORIGIN_ROW, origin_column: DEFAULT_ORIGIN_COLUMN, + roll_up_timeout: gst::ClockTime::NONE, } } } @@ -187,6 +189,8 @@ impl State { if let Some(erase_display_frame_no) = self.erase_display_frame_no { if self.last_frame_no == erase_display_frame_no - 1 { self.erase_display_frame_no = None; + self.column = 0; + self.send_roll_up_preamble = true; self.erase_display_memory(element, bufferlist); return true; } @@ -791,6 +795,9 @@ impl TtToCea608 { if state.mode == Cea608Mode::PopOn { state.erase_display_frame_no = Some(state.last_frame_no + duration.mul_div_round(fps_n, fps_d).unwrap().seconds()); + } else if let Some(timeout) = settings.roll_up_timeout { + state.erase_display_frame_no = + Some(state.last_frame_no + timeout.mul_div_round(fps_n, fps_d).unwrap().seconds()); } state.pad(element, mut_list, state.max_frame_no); @@ -1080,6 +1087,15 @@ impl ObjectImpl for TtToCea608 { DEFAULT_ORIGIN_COLUMN, glib::ParamFlags::READWRITE | gst::PARAM_FLAG_MUTABLE_PLAYING, ), + glib::ParamSpecUInt64::new( + "roll-up-timeout", + "Roll-Up Timeout", + "Duration after which to erase display memory in roll-up mode", + 0, + u64::MAX, + u64::MAX, + glib::ParamFlags::READWRITE | gst::PARAM_FLAG_MUTABLE_PLAYING, + ), ] }); @@ -1120,6 +1136,16 @@ impl ObjectImpl for TtToCea608 { state.force_clear = true; state.column = settings.origin_column; } + "roll-up-timeout" => { + let mut settings = self.settings.lock().unwrap(); + + let timeout = value.get().expect("type checked upstream"); + + settings.roll_up_timeout = match timeout { + u64::MAX => gst::ClockTime::NONE, + _ => Some(gst::ClockTime::from_nseconds(timeout)), + }; + } _ => unimplemented!(), } } @@ -1138,6 +1164,15 @@ impl ObjectImpl for TtToCea608 { let settings = self.settings.lock().unwrap(); settings.origin_column.to_value() } + "roll-up-timeout" => { + let settings = self.settings.lock().unwrap(); + + if let Some(timeout) = settings.roll_up_timeout { + timeout.nseconds().to_value() + } else { + u64::MAX.to_value() + } + } _ => unimplemented!(), } }