gstreamer/
pad_template.rs
1use std::ffi::CStr;
4
5use glib::{prelude::*, translate::*};
6
7use crate::{ffi, Caps, PadDirection, PadPresence, PadTemplate, StaticPadTemplate};
8
9impl PadTemplate {
10 #[doc(alias = "gst_pad_template_new_from_static_pad_template_with_gtype")]
20 pub fn from_static_pad_template_with_gtype(
21 pad_template: &StaticPadTemplate,
22 pad_type: glib::types::Type,
23 ) -> Result<PadTemplate, glib::BoolError> {
24 skip_assert_initialized!();
25 unsafe {
26 Option::<_>::from_glib_none(
27 ffi::gst_pad_template_new_from_static_pad_template_with_gtype(
28 mut_override(pad_template.to_glib_none().0),
29 pad_type.into_glib(),
30 ),
31 )
32 .ok_or_else(|| glib::bool_error!("Failed to create PadTemplate"))
33 }
34 }
35
36 #[doc(alias = "gst_pad_template_get_caps")]
43 #[doc(alias = "get_caps")]
44 pub fn caps(&self) -> &Caps {
45 unsafe {
46 let templ = &*(self.as_ptr() as *const ffi::GstPadTemplate);
47 &*(&templ.caps as *const *mut ffi::GstCaps as *const Caps)
48 }
49 }
50
51 #[cfg(feature = "v1_18")]
58 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
59 #[doc(alias = "gst_pad_template_get_documentation_caps")]
60 #[doc(alias = "get_documentation_caps")]
61 pub fn documentation_caps(&self) -> &Caps {
62 unsafe {
63 let templ = &*(self.as_ptr() as *const ffi::GstPadTemplate);
64 if !templ.ABI.abi.documentation_caps.is_null() {
65 &*(&templ.ABI.abi.documentation_caps as *const *mut ffi::GstCaps as *const Caps)
66 } else {
67 &*(&templ.caps as *const *mut ffi::GstCaps as *const Caps)
68 }
69 }
70 }
71
72 pub fn direction(&self) -> PadDirection {
73 unsafe {
74 let templ = &*(self.as_ptr() as *const ffi::GstPadTemplate);
75 from_glib(templ.direction)
76 }
77 }
78
79 pub fn gtype(&self) -> glib::types::Type {
80 unsafe {
81 let templ = &*(self.as_ptr() as *const ffi::GstPadTemplate);
82 from_glib(templ.ABI.abi.gtype)
83 }
84 }
85
86 #[doc(alias = "name-template")]
87 pub fn name_template(&self) -> &str {
88 unsafe {
89 let templ = &*(self.as_ptr() as *const ffi::GstPadTemplate);
90 CStr::from_ptr(templ.name_template).to_str().unwrap()
91 }
92 }
93
94 pub fn presence(&self) -> PadPresence {
95 unsafe {
96 let templ = &*(self.as_ptr() as *const ffi::GstPadTemplate);
97 from_glib(templ.presence)
98 }
99 }
100
101 pub fn builder<'a>(
102 name_template: &'a str,
103 direction: PadDirection,
104 presence: PadPresence,
105 caps: &'a Caps,
106 ) -> PadTemplateBuilder<'a> {
107 skip_assert_initialized!();
108
109 PadTemplateBuilder {
110 name_template,
111 direction,
112 presence,
113 caps,
114 gtype: None,
115 #[cfg(feature = "v1_18")]
116 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
117 documentation_caps: None,
118 }
119 }
120}
121
122#[must_use = "The builder must be built to be used"]
123#[derive(Debug)]
124pub struct PadTemplateBuilder<'a> {
125 name_template: &'a str,
126 direction: PadDirection,
127 presence: PadPresence,
128 caps: &'a Caps,
129 gtype: Option<glib::Type>,
130 #[cfg(feature = "v1_18")]
131 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
132 documentation_caps: Option<&'a Caps>,
133}
134
135#[allow(clippy::needless_lifetimes)]
136impl<'a> PadTemplateBuilder<'a> {
137 pub fn gtype(self, gtype: glib::Type) -> Self {
138 PadTemplateBuilder {
139 gtype: Some(gtype),
140 ..self
141 }
142 }
143
144 pub fn gtype_if(self, gtype: glib::Type, predicate: bool) -> Self {
145 if predicate {
146 PadTemplateBuilder {
147 gtype: Some(gtype),
148 ..self
149 }
150 } else {
151 self
152 }
153 }
154
155 pub fn gtype_if_some(self, gtype: Option<glib::Type>) -> Self {
156 if let Some(gtype) = gtype {
157 self.gtype(gtype)
158 } else {
159 self
160 }
161 }
162
163 #[cfg(feature = "v1_18")]
164 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
165 pub fn documentation_caps(self, documentation_caps: &'a Caps) -> Self {
166 PadTemplateBuilder {
167 documentation_caps: Some(documentation_caps),
168 ..self
169 }
170 }
171
172 #[cfg(feature = "v1_18")]
173 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
174 pub fn documentation_caps_if(self, documentation_caps: &'a Caps, predicate: bool) -> Self {
175 if predicate {
176 PadTemplateBuilder {
177 documentation_caps: Some(documentation_caps),
178 ..self
179 }
180 } else {
181 self
182 }
183 }
184
185 #[cfg(feature = "v1_18")]
186 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
187 pub fn documentation_caps_if_some(self, documentation_caps: Option<&'a Caps>) -> Self {
188 if let Some(documentation_caps) = documentation_caps {
189 self.documentation_caps(documentation_caps)
190 } else {
191 self
192 }
193 }
194
195 pub fn build(self) -> Result<PadTemplate, glib::BoolError> {
196 let templ = if let Some(gtype) = self.gtype {
197 PadTemplate::with_gtype(
198 self.name_template,
199 self.direction,
200 self.presence,
201 self.caps,
202 gtype,
203 )?
204 } else {
205 PadTemplate::new(self.name_template, self.direction, self.presence, self.caps)?
206 };
207
208 #[cfg(feature = "v1_18")]
209 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
210 if let Some(documentation_caps) = self.documentation_caps {
211 unsafe {
212 ffi::gst_pad_template_set_documentation_caps(
213 templ.to_glib_none().0,
214 documentation_caps.to_glib_none().0,
215 );
216 }
217 }
218
219 Ok(templ)
220 }
221}