11use crate :: wayland:: {
22 CapturedDmaBuffer , CapturedDmaBufferSync , CapturedFrame , CapturedFrameBuffer ,
3- CapturedFrameFormat , PipewireOptions , RgbaSwizzle ,
3+ CapturedFrameFormat , PipewireOptions , PixelFormat , RgbaSwizzle ,
44} ;
55use pipewire:: {
66 context:: ContextRc ,
@@ -52,6 +52,13 @@ struct UserStreamState {
5252impl UserStreamState {
5353 fn handle_state_changed ( & mut self , _stream : & Stream , old : StreamState , new : StreamState ) {
5454 log:: debug!( "stream changed: {old:?} -> {new:?}" ) ;
55+
56+ if old == StreamState :: Streaming
57+ && matches ! ( new, StreamState :: Unconnected | StreamState :: Error ( ..) )
58+ && let Some ( main_loop) = self . main_loop . upgrade ( )
59+ {
60+ main_loop. quit ( ) ;
61+ }
5562 }
5663
5764 fn handle_param_changed ( & mut self , stream : & Stream , id : u32 , param : Option < & Pod > ) {
@@ -543,15 +550,18 @@ fn build_stream(
543550
544551 // Add the format params with the video drm modifier property first if dma buffers are to be used
545552 if let Some ( dma_usage) = options. dma_usage {
546- let mut format_params = format_params ( options. max_framerate ) ;
553+ let mut format_params = format_params ( & options . pixel_formats , options. max_framerate ) ;
547554 format_params
548555 . properties
549556 . push ( drm_modifier_property ( & dma_usage. supported_modifier ) ) ;
550557 connect_params. push ( serialize_object ( format_params) ) ;
551558 }
552559
553560 // Add format without video drm modifier property
554- connect_params. push ( serialize_object ( format_params ( options. max_framerate ) ) ) ;
561+ connect_params. push ( serialize_object ( format_params (
562+ & options. pixel_formats ,
563+ options. max_framerate ,
564+ ) ) ) ;
555565
556566 let mut connect_params: SmallVec < [ & Pod ; 2 ] > = connect_params
557567 . iter ( )
@@ -569,31 +579,44 @@ fn build_stream(
569579}
570580
571581/// Build the video format capabilities which will be used to negotiate a video stream with pipewire
572- fn format_params ( max_framerate : u32 ) -> Object {
582+ fn format_params ( pixel_formats : & [ PixelFormat ] , max_framerate : u32 ) -> Object {
583+ fn map ( p : PixelFormat ) -> & ' static [ VideoFormat ] {
584+ match p {
585+ PixelFormat :: NV12 => & [ VideoFormat :: NV12 ] ,
586+ PixelFormat :: I420 => & [ VideoFormat :: I420 ] ,
587+ PixelFormat :: RGBA ( rgba_swizzle) => match rgba_swizzle {
588+ RgbaSwizzle :: RGBA => & [ VideoFormat :: RGBA , VideoFormat :: RGBx ] ,
589+ RgbaSwizzle :: BGRA => & [ VideoFormat :: BGRA , VideoFormat :: BGRx ] ,
590+ RgbaSwizzle :: ARGB => & [ VideoFormat :: ARGB , VideoFormat :: xRGB] ,
591+ RgbaSwizzle :: ABGR => & [ VideoFormat :: ABGR , VideoFormat :: xBGR] ,
592+ } ,
593+ }
594+ }
595+
596+ let video_formats = Value :: Choice ( ChoiceValue :: Id ( Choice (
597+ ChoiceFlags :: empty ( ) ,
598+ ChoiceEnum :: Enum {
599+ default : Id ( map ( pixel_formats[ 0 ] ) [ 0 ] . 0 ) ,
600+ alternatives : pixel_formats
601+ . iter ( )
602+ . flat_map ( |p| map ( * p) . iter ( ) . copied ( ) )
603+ . map ( |video_format| Id ( video_format. as_raw ( ) ) )
604+ . collect ( ) ,
605+ } ,
606+ ) ) ) ;
607+
608+ let video_formats_property = Property {
609+ key : FormatProperties :: VideoFormat . as_raw ( ) ,
610+ flags : PropertyFlags :: empty ( ) ,
611+ value : video_formats,
612+ } ;
613+
573614 object ! (
574615 SpaTypes :: ObjectParamFormat ,
575616 ParamType :: EnumFormat ,
576617 property!( FormatProperties :: MediaType , Id , MediaType :: Video ) ,
577618 property!( FormatProperties :: MediaSubtype , Id , MediaSubtype :: Raw ) ,
578- property!(
579- FormatProperties :: VideoFormat ,
580- Choice ,
581- Enum ,
582- Id ,
583- // Default
584- VideoFormat :: NV12 ,
585- // Alternatives
586- VideoFormat :: NV12 ,
587- VideoFormat :: I420 ,
588- VideoFormat :: RGBA ,
589- VideoFormat :: BGRA ,
590- VideoFormat :: ARGB ,
591- VideoFormat :: ABGR ,
592- VideoFormat :: RGBx ,
593- VideoFormat :: BGRx ,
594- VideoFormat :: xRGB,
595- VideoFormat :: xBGR,
596- ) ,
619+ video_formats_property,
597620 property!(
598621 FormatProperties :: VideoSize ,
599622 Choice ,
0 commit comments