@@ -349,14 +349,35 @@ impl<T: Pixel> ContextInner<T> {
349
349
}
350
350
self . frame_q . insert ( input_frameno, frame) ;
351
351
352
+ #[ cfg( feature = "unstable" ) ]
353
+ // Update T.35 metadata from encoder config
354
+ let maybe_updated_t35_metadata = self . get_maybe_updated_t35_metadata (
355
+ input_frameno,
356
+ params. as_ref ( ) . map ( |params| params. t35_metadata . as_ref ( ) ) ,
357
+ ) ;
358
+
352
359
if let Some ( params) = params {
353
360
if params. frame_type_override == FrameTypeOverride :: Key {
354
361
self . keyframes_forced . insert ( input_frameno) ;
355
362
}
356
363
if let Some ( op) = params. opaque {
357
364
self . opaque_q . insert ( input_frameno, op) ;
358
365
}
366
+
367
+ #[ cfg( not( feature = "unstable" ) ) ]
359
368
self . t35_q . insert ( input_frameno, params. t35_metadata ) ;
369
+
370
+ #[ cfg( feature = "unstable" ) ]
371
+ if let Some ( new_t35_metadata) = maybe_updated_t35_metadata {
372
+ self . t35_q . insert ( input_frameno, new_t35_metadata. into_boxed_slice ( ) ) ;
373
+ } else {
374
+ self . t35_q . insert ( input_frameno, params. t35_metadata ) ;
375
+ }
376
+ } else {
377
+ #[ cfg( feature = "unstable" ) ]
378
+ if let Some ( new_t35_metadata) = maybe_updated_t35_metadata {
379
+ self . t35_q . insert ( input_frameno, new_t35_metadata. into_boxed_slice ( ) ) ;
380
+ }
360
381
}
361
382
362
383
if !self . needs_more_frame_q_lookahead ( self . next_lookahead_frame ) {
@@ -1688,4 +1709,59 @@ impl<T: Pixel> ContextInner<T> {
1688
1709
( prev_keyframe_nframes, prev_keyframe_ntus)
1689
1710
}
1690
1711
}
1712
+
1713
+ #[ cfg( feature = "unstable" ) ]
1714
+ /// Updates the T.35 metadata to be added to the frame.
1715
+ /// The existing T.35 array may come from `FrameParameters`.
1716
+ /// New metadata is added from the encoder config:
1717
+ /// - HDR10+, ST2094-40 in `EncoderConfig.hdr10plus_payloads`
1718
+ ///
1719
+ /// Returns an `Option`, where `None` means the T.35 metadata is unchanged.
1720
+ /// Otherwise, the updated T.35 metadata array is returned.
1721
+ fn get_maybe_updated_t35_metadata (
1722
+ & self , input_frameno : u64 , maybe_existing_t35_metadata : Option < & [ T35 ] > ,
1723
+ ) -> Option < Vec < T35 > > {
1724
+ let hdr10plus_payload = self
1725
+ . config
1726
+ . hdr10plus_payloads
1727
+ . as_ref ( )
1728
+ . and_then ( |list| list. get ( & input_frameno) ) ;
1729
+
1730
+ let update_t35_metadata = hdr10plus_payload. is_some ( ) ;
1731
+
1732
+ let mut new_t35_metadata = if update_t35_metadata {
1733
+ Some (
1734
+ maybe_existing_t35_metadata. map_or_else ( Vec :: new, |t35| t35. to_vec ( ) ) ,
1735
+ )
1736
+ } else {
1737
+ None
1738
+ } ;
1739
+
1740
+ if let Some ( list) = new_t35_metadata. as_mut ( ) {
1741
+ // HDR10+, ST2094-40
1742
+ if let Some ( payload) = hdr10plus_payload {
1743
+ // FIXME: Make const
1744
+ let st2094_40_needle = & [
1745
+ 0x00 , 0x03C , // Samsung Electronics America
1746
+ 0x00 , 0x01 , // ST-2094-40
1747
+ 0x04 , // application_identifier = 4
1748
+ 0x01 , // application_mode =1
1749
+ ] ;
1750
+
1751
+ let has_existing_hdr10plus_meta = list. iter ( ) . any ( |t35| {
1752
+ t35. country_code == 0xB5 && t35. data . starts_with ( st2094_40_needle)
1753
+ } ) ;
1754
+
1755
+ if !has_existing_hdr10plus_meta {
1756
+ list. push ( T35 {
1757
+ country_code : 0xB5 ,
1758
+ country_code_extension_byte : 0x00 ,
1759
+ data : payload. clone ( ) . into_boxed_slice ( ) ,
1760
+ } ) ;
1761
+ }
1762
+ }
1763
+ }
1764
+
1765
+ new_t35_metadata
1766
+ }
1691
1767
}
0 commit comments