1use std::ptr;
4
5use glib::{prelude::*, translate::*};
6use gst::subclass::prelude::*;
7
8use crate::{Aggregator, AggregatorPad, ffi};
9
10pub trait AggregatorImpl: ElementImpl + ObjectSubclass<Type: IsA<Aggregator>> {
11 fn flush(&self) -> Result<gst::FlowSuccess, gst::FlowError> {
16 self.parent_flush()
17 }
18
19 fn clip(&self, aggregator_pad: &AggregatorPad, buffer: gst::Buffer) -> Option<gst::Buffer> {
35 self.parent_clip(aggregator_pad, buffer)
36 }
37
38 #[cfg(feature = "v1_18")]
44 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
45 fn finish_buffer_list(
46 &self,
47 buffer_list: gst::BufferList,
48 ) -> Result<gst::FlowSuccess, gst::FlowError> {
49 self.parent_finish_buffer_list(buffer_list)
50 }
51
52 fn finish_buffer(&self, buffer: gst::Buffer) -> Result<gst::FlowSuccess, gst::FlowError> {
58 self.parent_finish_buffer(buffer)
59 }
60
61 fn sink_event(&self, aggregator_pad: &AggregatorPad, event: gst::Event) -> bool {
68 self.parent_sink_event(aggregator_pad, event)
69 }
70
71 #[cfg(feature = "v1_18")]
78 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
79 fn sink_event_pre_queue(
80 &self,
81 aggregator_pad: &AggregatorPad,
82 event: gst::Event,
83 ) -> Result<gst::FlowSuccess, gst::FlowError> {
84 self.parent_sink_event_pre_queue(aggregator_pad, event)
85 }
86
87 fn sink_query(&self, aggregator_pad: &AggregatorPad, query: &mut gst::QueryRef) -> bool {
91 self.parent_sink_query(aggregator_pad, query)
92 }
93
94 #[cfg(feature = "v1_18")]
98 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
99 fn sink_query_pre_queue(
100 &self,
101 aggregator_pad: &AggregatorPad,
102 query: &mut gst::QueryRef,
103 ) -> bool {
104 self.parent_sink_query_pre_queue(aggregator_pad, query)
105 }
106
107 fn src_event(&self, event: gst::Event) -> bool {
112 self.parent_src_event(event)
113 }
114
115 fn src_query(&self, query: &mut gst::QueryRef) -> bool {
119 self.parent_src_query(query)
120 }
121
122 fn src_activate(&self, mode: gst::PadMode, active: bool) -> Result<(), gst::LoggableError> {
126 self.parent_src_activate(mode, active)
127 }
128
129 fn aggregate(&self, timeout: bool) -> Result<gst::FlowSuccess, gst::FlowError> {
137 self.parent_aggregate(timeout)
138 }
139
140 fn start(&self) -> Result<(), gst::ErrorMessage> {
145 self.parent_start()
146 }
147
148 fn stop(&self) -> Result<(), gst::ErrorMessage> {
152 self.parent_stop()
153 }
154
155 fn next_time(&self) -> Option<gst::ClockTime> {
162 self.parent_next_time()
163 }
164
165 fn create_new_pad(
179 &self,
180 templ: &gst::PadTemplate,
181 req_name: Option<&str>,
182 caps: Option<&gst::Caps>,
183 ) -> Option<AggregatorPad> {
184 self.parent_create_new_pad(templ, req_name, caps)
185 }
186
187 fn update_src_caps(&self, caps: &gst::Caps) -> Result<gst::Caps, gst::FlowError> {
193 self.parent_update_src_caps(caps)
194 }
195
196 fn fixate_src_caps(&self, caps: gst::Caps) -> gst::Caps {
206 self.parent_fixate_src_caps(caps)
207 }
208
209 fn negotiated_src_caps(&self, caps: &gst::Caps) -> Result<(), gst::LoggableError> {
212 self.parent_negotiated_src_caps(caps)
213 }
214
215 fn propose_allocation(
218 &self,
219 pad: &AggregatorPad,
220 decide_query: Option<&gst::query::Allocation>,
221 query: &mut gst::query::Allocation,
222 ) -> Result<(), gst::LoggableError> {
223 self.parent_propose_allocation(pad, decide_query, query)
224 }
225
226 fn decide_allocation(
232 &self,
233 query: &mut gst::query::Allocation,
234 ) -> Result<(), gst::LoggableError> {
235 self.parent_decide_allocation(query)
236 }
237
238 #[cfg(feature = "v1_18")]
246 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
247 fn negotiate(&self) -> bool {
248 self.parent_negotiate()
249 }
250
251 #[cfg(feature = "v1_18")]
265 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
266 fn peek_next_sample(&self, pad: &AggregatorPad) -> Option<gst::Sample> {
267 self.parent_peek_next_sample(pad)
268 }
269}
270
271pub trait AggregatorImplExt: AggregatorImpl {
272 fn parent_flush(&self) -> Result<gst::FlowSuccess, gst::FlowError> {
273 unsafe {
274 let data = Self::type_data();
275 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
276 (*parent_class)
277 .flush
278 .map(|f| {
279 try_from_glib(f(self
280 .obj()
281 .unsafe_cast_ref::<Aggregator>()
282 .to_glib_none()
283 .0))
284 })
285 .unwrap_or(Ok(gst::FlowSuccess::Ok))
286 }
287 }
288
289 fn parent_clip(
290 &self,
291 aggregator_pad: &AggregatorPad,
292 buffer: gst::Buffer,
293 ) -> Option<gst::Buffer> {
294 unsafe {
295 let data = Self::type_data();
296 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
297 match (*parent_class).clip {
298 None => Some(buffer),
299 Some(ref func) => from_glib_full(func(
300 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
301 aggregator_pad.to_glib_none().0,
302 buffer.into_glib_ptr(),
303 )),
304 }
305 }
306 }
307
308 fn parent_finish_buffer(
309 &self,
310 buffer: gst::Buffer,
311 ) -> Result<gst::FlowSuccess, gst::FlowError> {
312 unsafe {
313 let data = Self::type_data();
314 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
315 let f = (*parent_class)
316 .finish_buffer
317 .expect("Missing parent function `finish_buffer`");
318 try_from_glib(f(
319 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
320 buffer.into_glib_ptr(),
321 ))
322 }
323 }
324
325 #[cfg(feature = "v1_18")]
326 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
327 fn parent_finish_buffer_list(
328 &self,
329 buffer_list: gst::BufferList,
330 ) -> Result<gst::FlowSuccess, gst::FlowError> {
331 unsafe {
332 let data = Self::type_data();
333 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
334 let f = (*parent_class)
335 .finish_buffer_list
336 .expect("Missing parent function `finish_buffer_list`");
337 try_from_glib(f(
338 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
339 buffer_list.into_glib_ptr(),
340 ))
341 }
342 }
343
344 fn parent_sink_event(&self, aggregator_pad: &AggregatorPad, event: gst::Event) -> bool {
345 unsafe {
346 let data = Self::type_data();
347 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
348 let f = (*parent_class)
349 .sink_event
350 .expect("Missing parent function `sink_event`");
351 from_glib(f(
352 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
353 aggregator_pad.to_glib_none().0,
354 event.into_glib_ptr(),
355 ))
356 }
357 }
358
359 #[cfg(feature = "v1_18")]
360 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
361 fn parent_sink_event_pre_queue(
362 &self,
363 aggregator_pad: &AggregatorPad,
364 event: gst::Event,
365 ) -> Result<gst::FlowSuccess, gst::FlowError> {
366 unsafe {
367 let data = Self::type_data();
368 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
369 let f = (*parent_class)
370 .sink_event_pre_queue
371 .expect("Missing parent function `sink_event_pre_queue`");
372 try_from_glib(f(
373 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
374 aggregator_pad.to_glib_none().0,
375 event.into_glib_ptr(),
376 ))
377 }
378 }
379
380 fn parent_sink_query(&self, aggregator_pad: &AggregatorPad, query: &mut gst::QueryRef) -> bool {
381 unsafe {
382 let data = Self::type_data();
383 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
384 let f = (*parent_class)
385 .sink_query
386 .expect("Missing parent function `sink_query`");
387 from_glib(f(
388 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
389 aggregator_pad.to_glib_none().0,
390 query.as_mut_ptr(),
391 ))
392 }
393 }
394
395 #[cfg(feature = "v1_18")]
396 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
397 fn parent_sink_query_pre_queue(
398 &self,
399 aggregator_pad: &AggregatorPad,
400 query: &mut gst::QueryRef,
401 ) -> bool {
402 unsafe {
403 let data = Self::type_data();
404 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
405 let f = (*parent_class)
406 .sink_query_pre_queue
407 .expect("Missing parent function `sink_query`");
408 from_glib(f(
409 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
410 aggregator_pad.to_glib_none().0,
411 query.as_mut_ptr(),
412 ))
413 }
414 }
415
416 fn parent_src_event(&self, event: gst::Event) -> bool {
417 unsafe {
418 let data = Self::type_data();
419 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
420 let f = (*parent_class)
421 .src_event
422 .expect("Missing parent function `src_event`");
423 from_glib(f(
424 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
425 event.into_glib_ptr(),
426 ))
427 }
428 }
429
430 fn parent_src_query(&self, query: &mut gst::QueryRef) -> bool {
431 unsafe {
432 let data = Self::type_data();
433 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
434 let f = (*parent_class)
435 .src_query
436 .expect("Missing parent function `src_query`");
437 from_glib(f(
438 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
439 query.as_mut_ptr(),
440 ))
441 }
442 }
443
444 fn parent_src_activate(
445 &self,
446 mode: gst::PadMode,
447 active: bool,
448 ) -> Result<(), gst::LoggableError> {
449 unsafe {
450 let data = Self::type_data();
451 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
452 match (*parent_class).src_activate {
453 None => Ok(()),
454 Some(f) => gst::result_from_gboolean!(
455 f(
456 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
457 mode.into_glib(),
458 active.into_glib()
459 ),
460 gst::CAT_RUST,
461 "Parent function `src_activate` failed"
462 ),
463 }
464 }
465 }
466
467 fn parent_aggregate(&self, timeout: bool) -> Result<gst::FlowSuccess, gst::FlowError> {
468 unsafe {
469 let data = Self::type_data();
470 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
471 let f = (*parent_class)
472 .aggregate
473 .expect("Missing parent function `aggregate`");
474 try_from_glib(f(
475 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
476 timeout.into_glib(),
477 ))
478 }
479 }
480
481 fn parent_start(&self) -> Result<(), gst::ErrorMessage> {
482 unsafe {
483 let data = Self::type_data();
484 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
485 (*parent_class)
486 .start
487 .map(|f| {
488 if from_glib(f(self
489 .obj()
490 .unsafe_cast_ref::<Aggregator>()
491 .to_glib_none()
492 .0))
493 {
494 Ok(())
495 } else {
496 Err(gst::error_msg!(
497 gst::CoreError::Failed,
498 ["Parent function `start` failed"]
499 ))
500 }
501 })
502 .unwrap_or(Ok(()))
503 }
504 }
505
506 fn parent_stop(&self) -> Result<(), gst::ErrorMessage> {
507 unsafe {
508 let data = Self::type_data();
509 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
510 (*parent_class)
511 .stop
512 .map(|f| {
513 if from_glib(f(self
514 .obj()
515 .unsafe_cast_ref::<Aggregator>()
516 .to_glib_none()
517 .0))
518 {
519 Ok(())
520 } else {
521 Err(gst::error_msg!(
522 gst::CoreError::Failed,
523 ["Parent function `stop` failed"]
524 ))
525 }
526 })
527 .unwrap_or(Ok(()))
528 }
529 }
530
531 fn parent_next_time(&self) -> Option<gst::ClockTime> {
532 unsafe {
533 let data = Self::type_data();
534 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
535 (*parent_class)
536 .get_next_time
537 .map(|f| {
538 from_glib(f(self
539 .obj()
540 .unsafe_cast_ref::<Aggregator>()
541 .to_glib_none()
542 .0))
543 })
544 .unwrap_or(gst::ClockTime::NONE)
545 }
546 }
547
548 fn parent_create_new_pad(
549 &self,
550 templ: &gst::PadTemplate,
551 req_name: Option<&str>,
552 caps: Option<&gst::Caps>,
553 ) -> Option<AggregatorPad> {
554 unsafe {
555 let data = Self::type_data();
556 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
557 let f = (*parent_class)
558 .create_new_pad
559 .expect("Missing parent function `create_new_pad`");
560 from_glib_full(f(
561 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
562 templ.to_glib_none().0,
563 req_name.to_glib_none().0,
564 caps.to_glib_none().0,
565 ))
566 }
567 }
568
569 fn parent_update_src_caps(&self, caps: &gst::Caps) -> Result<gst::Caps, gst::FlowError> {
570 unsafe {
571 let data = Self::type_data();
572 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
573 let f = (*parent_class)
574 .update_src_caps
575 .expect("Missing parent function `update_src_caps`");
576
577 let mut out_caps = ptr::null_mut();
578 gst::FlowSuccess::try_from_glib(f(
579 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
580 caps.as_mut_ptr(),
581 &mut out_caps,
582 ))
583 .map(|_| from_glib_full(out_caps))
584 }
585 }
586
587 fn parent_fixate_src_caps(&self, caps: gst::Caps) -> gst::Caps {
588 unsafe {
589 let data = Self::type_data();
590 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
591
592 let f = (*parent_class)
593 .fixate_src_caps
594 .expect("Missing parent function `fixate_src_caps`");
595 from_glib_full(f(
596 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
597 caps.into_glib_ptr(),
598 ))
599 }
600 }
601
602 fn parent_negotiated_src_caps(&self, caps: &gst::Caps) -> Result<(), gst::LoggableError> {
603 unsafe {
604 let data = Self::type_data();
605 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
606 (*parent_class)
607 .negotiated_src_caps
608 .map(|f| {
609 gst::result_from_gboolean!(
610 f(
611 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
612 caps.to_glib_none().0
613 ),
614 gst::CAT_RUST,
615 "Parent function `negotiated_src_caps` failed"
616 )
617 })
618 .unwrap_or(Ok(()))
619 }
620 }
621
622 fn parent_propose_allocation(
623 &self,
624 pad: &AggregatorPad,
625 decide_query: Option<&gst::query::Allocation>,
626 query: &mut gst::query::Allocation,
627 ) -> Result<(), gst::LoggableError> {
628 unsafe {
629 let data = Self::type_data();
630 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
631 (*parent_class)
632 .propose_allocation
633 .map(|f| {
634 gst::result_from_gboolean!(
635 f(
636 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
637 pad.to_glib_none().0,
638 decide_query
639 .as_ref()
640 .map(|q| q.as_mut_ptr())
641 .unwrap_or(ptr::null_mut()),
642 query.as_mut_ptr()
643 ),
644 gst::CAT_RUST,
645 "Parent function `propose_allocation` failed",
646 )
647 })
648 .unwrap_or(Ok(()))
649 }
650 }
651
652 fn parent_decide_allocation(
653 &self,
654 query: &mut gst::query::Allocation,
655 ) -> Result<(), gst::LoggableError> {
656 unsafe {
657 let data = Self::type_data();
658 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
659 (*parent_class)
660 .decide_allocation
661 .map(|f| {
662 gst::result_from_gboolean!(
663 f(
664 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
665 query.as_mut_ptr(),
666 ),
667 gst::CAT_RUST,
668 "Parent function `decide_allocation` failed",
669 )
670 })
671 .unwrap_or(Ok(()))
672 }
673 }
674
675 #[cfg(feature = "v1_18")]
676 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
677 fn parent_negotiate(&self) -> bool {
678 unsafe {
679 let data = Self::type_data();
680 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
681 (*parent_class)
682 .negotiate
683 .map(|f| {
684 from_glib(f(self
685 .obj()
686 .unsafe_cast_ref::<Aggregator>()
687 .to_glib_none()
688 .0))
689 })
690 .unwrap_or(true)
691 }
692 }
693
694 #[cfg(feature = "v1_18")]
695 #[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
696 fn parent_peek_next_sample(&self, pad: &AggregatorPad) -> Option<gst::Sample> {
697 unsafe {
698 let data = Self::type_data();
699 let parent_class = data.as_ref().parent_class() as *mut ffi::GstAggregatorClass;
700 (*parent_class)
701 .peek_next_sample
702 .map(|f| {
703 from_glib_full(f(
704 self.obj().unsafe_cast_ref::<Aggregator>().to_glib_none().0,
705 pad.to_glib_none().0,
706 ))
707 })
708 .unwrap_or(None)
709 }
710 }
711}
712
713impl<T: AggregatorImpl> AggregatorImplExt for T {}
714
715unsafe impl<T: AggregatorImpl> IsSubclassable<T> for Aggregator {
716 fn class_init(klass: &mut glib::Class<Self>) {
717 Self::parent_class_init::<T>(klass);
718 let klass = klass.as_mut();
719 klass.flush = Some(aggregator_flush::<T>);
720 klass.clip = Some(aggregator_clip::<T>);
721 klass.finish_buffer = Some(aggregator_finish_buffer::<T>);
722 klass.sink_event = Some(aggregator_sink_event::<T>);
723 klass.sink_query = Some(aggregator_sink_query::<T>);
724 klass.src_event = Some(aggregator_src_event::<T>);
725 klass.src_query = Some(aggregator_src_query::<T>);
726 klass.src_activate = Some(aggregator_src_activate::<T>);
727 klass.aggregate = Some(aggregator_aggregate::<T>);
728 klass.start = Some(aggregator_start::<T>);
729 klass.stop = Some(aggregator_stop::<T>);
730 klass.get_next_time = Some(aggregator_get_next_time::<T>);
731 klass.create_new_pad = Some(aggregator_create_new_pad::<T>);
732 klass.update_src_caps = Some(aggregator_update_src_caps::<T>);
733 klass.fixate_src_caps = Some(aggregator_fixate_src_caps::<T>);
734 klass.negotiated_src_caps = Some(aggregator_negotiated_src_caps::<T>);
735 klass.propose_allocation = Some(aggregator_propose_allocation::<T>);
736 klass.decide_allocation = Some(aggregator_decide_allocation::<T>);
737 #[cfg(feature = "v1_18")]
738 {
739 klass.sink_event_pre_queue = Some(aggregator_sink_event_pre_queue::<T>);
740 klass.sink_query_pre_queue = Some(aggregator_sink_query_pre_queue::<T>);
741 klass.negotiate = Some(aggregator_negotiate::<T>);
742 klass.peek_next_sample = Some(aggregator_peek_next_sample::<T>);
743 klass.finish_buffer_list = Some(aggregator_finish_buffer_list::<T>);
744 }
745 }
746}
747
748unsafe extern "C" fn aggregator_flush<T: AggregatorImpl>(
749 ptr: *mut ffi::GstAggregator,
750) -> gst::ffi::GstFlowReturn {
751 unsafe {
752 let instance = &*(ptr as *mut T::Instance);
753 let imp = instance.imp();
754
755 gst::panic_to_error!(imp, gst::FlowReturn::Error, { imp.flush().into() }).into_glib()
756 }
757}
758
759unsafe extern "C" fn aggregator_clip<T: AggregatorImpl>(
760 ptr: *mut ffi::GstAggregator,
761 aggregator_pad: *mut ffi::GstAggregatorPad,
762 buffer: *mut gst::ffi::GstBuffer,
763) -> *mut gst::ffi::GstBuffer {
764 unsafe {
765 let instance = &*(ptr as *mut T::Instance);
766 let imp = instance.imp();
767
768 let ret = gst::panic_to_error!(imp, None, {
769 imp.clip(&from_glib_borrow(aggregator_pad), from_glib_full(buffer))
770 });
771
772 ret.map(|r| r.into_glib_ptr()).unwrap_or(ptr::null_mut())
773 }
774}
775
776unsafe extern "C" fn aggregator_finish_buffer<T: AggregatorImpl>(
777 ptr: *mut ffi::GstAggregator,
778 buffer: *mut gst::ffi::GstBuffer,
779) -> gst::ffi::GstFlowReturn {
780 unsafe {
781 let instance = &*(ptr as *mut T::Instance);
782 let imp = instance.imp();
783
784 gst::panic_to_error!(imp, gst::FlowReturn::Error, {
785 imp.finish_buffer(from_glib_full(buffer)).into()
786 })
787 .into_glib()
788 }
789}
790
791#[cfg(feature = "v1_18")]
792#[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
793unsafe extern "C" fn aggregator_finish_buffer_list<T: AggregatorImpl>(
794 ptr: *mut ffi::GstAggregator,
795 buffer_list: *mut gst::ffi::GstBufferList,
796) -> gst::ffi::GstFlowReturn {
797 unsafe {
798 let instance = &*(ptr as *mut T::Instance);
799 let imp = instance.imp();
800
801 gst::panic_to_error!(imp, gst::FlowReturn::Error, {
802 imp.finish_buffer_list(from_glib_full(buffer_list)).into()
803 })
804 .into_glib()
805 }
806}
807
808unsafe extern "C" fn aggregator_sink_event<T: AggregatorImpl>(
809 ptr: *mut ffi::GstAggregator,
810 aggregator_pad: *mut ffi::GstAggregatorPad,
811 event: *mut gst::ffi::GstEvent,
812) -> glib::ffi::gboolean {
813 unsafe {
814 let instance = &*(ptr as *mut T::Instance);
815 let imp = instance.imp();
816
817 gst::panic_to_error!(imp, false, {
818 imp.sink_event(&from_glib_borrow(aggregator_pad), from_glib_full(event))
819 })
820 .into_glib()
821 }
822}
823
824#[cfg(feature = "v1_18")]
825#[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
826unsafe extern "C" fn aggregator_sink_event_pre_queue<T: AggregatorImpl>(
827 ptr: *mut ffi::GstAggregator,
828 aggregator_pad: *mut ffi::GstAggregatorPad,
829 event: *mut gst::ffi::GstEvent,
830) -> gst::ffi::GstFlowReturn {
831 unsafe {
832 let instance = &*(ptr as *mut T::Instance);
833 let imp = instance.imp();
834
835 gst::panic_to_error!(imp, gst::FlowReturn::Error, {
836 imp.sink_event_pre_queue(&from_glib_borrow(aggregator_pad), from_glib_full(event))
837 .into()
838 })
839 .into_glib()
840 }
841}
842
843unsafe extern "C" fn aggregator_sink_query<T: AggregatorImpl>(
844 ptr: *mut ffi::GstAggregator,
845 aggregator_pad: *mut ffi::GstAggregatorPad,
846 query: *mut gst::ffi::GstQuery,
847) -> glib::ffi::gboolean {
848 unsafe {
849 let instance = &*(ptr as *mut T::Instance);
850 let imp = instance.imp();
851
852 gst::panic_to_error!(imp, false, {
853 imp.sink_query(
854 &from_glib_borrow(aggregator_pad),
855 gst::QueryRef::from_mut_ptr(query),
856 )
857 })
858 .into_glib()
859 }
860}
861
862#[cfg(feature = "v1_18")]
863#[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
864unsafe extern "C" fn aggregator_sink_query_pre_queue<T: AggregatorImpl>(
865 ptr: *mut ffi::GstAggregator,
866 aggregator_pad: *mut ffi::GstAggregatorPad,
867 query: *mut gst::ffi::GstQuery,
868) -> glib::ffi::gboolean {
869 unsafe {
870 let instance = &*(ptr as *mut T::Instance);
871 let imp = instance.imp();
872
873 gst::panic_to_error!(imp, false, {
874 imp.sink_query_pre_queue(
875 &from_glib_borrow(aggregator_pad),
876 gst::QueryRef::from_mut_ptr(query),
877 )
878 })
879 .into_glib()
880 }
881}
882
883unsafe extern "C" fn aggregator_src_event<T: AggregatorImpl>(
884 ptr: *mut ffi::GstAggregator,
885 event: *mut gst::ffi::GstEvent,
886) -> glib::ffi::gboolean {
887 unsafe {
888 let instance = &*(ptr as *mut T::Instance);
889 let imp = instance.imp();
890
891 gst::panic_to_error!(imp, false, { imp.src_event(from_glib_full(event)) }).into_glib()
892 }
893}
894
895unsafe extern "C" fn aggregator_src_query<T: AggregatorImpl>(
896 ptr: *mut ffi::GstAggregator,
897 query: *mut gst::ffi::GstQuery,
898) -> glib::ffi::gboolean {
899 unsafe {
900 let instance = &*(ptr as *mut T::Instance);
901 let imp = instance.imp();
902
903 gst::panic_to_error!(imp, false, {
904 imp.src_query(gst::QueryRef::from_mut_ptr(query))
905 })
906 .into_glib()
907 }
908}
909
910unsafe extern "C" fn aggregator_src_activate<T: AggregatorImpl>(
911 ptr: *mut ffi::GstAggregator,
912 mode: gst::ffi::GstPadMode,
913 active: glib::ffi::gboolean,
914) -> glib::ffi::gboolean {
915 unsafe {
916 let instance = &*(ptr as *mut T::Instance);
917 let imp = instance.imp();
918
919 gst::panic_to_error!(imp, false, {
920 match imp.src_activate(from_glib(mode), from_glib(active)) {
921 Ok(()) => true,
922 Err(err) => {
923 err.log_with_imp(imp);
924 false
925 }
926 }
927 })
928 .into_glib()
929 }
930}
931
932unsafe extern "C" fn aggregator_aggregate<T: AggregatorImpl>(
933 ptr: *mut ffi::GstAggregator,
934 timeout: glib::ffi::gboolean,
935) -> gst::ffi::GstFlowReturn {
936 unsafe {
937 let instance = &*(ptr as *mut T::Instance);
938 let imp = instance.imp();
939
940 gst::panic_to_error!(imp, gst::FlowReturn::Error, {
941 imp.aggregate(from_glib(timeout)).into()
942 })
943 .into_glib()
944 }
945}
946
947unsafe extern "C" fn aggregator_start<T: AggregatorImpl>(
948 ptr: *mut ffi::GstAggregator,
949) -> glib::ffi::gboolean {
950 unsafe {
951 let instance = &*(ptr as *mut T::Instance);
952 let imp = instance.imp();
953
954 gst::panic_to_error!(imp, false, {
955 match imp.start() {
956 Ok(()) => true,
957 Err(err) => {
958 imp.post_error_message(err);
959 false
960 }
961 }
962 })
963 .into_glib()
964 }
965}
966
967unsafe extern "C" fn aggregator_stop<T: AggregatorImpl>(
968 ptr: *mut ffi::GstAggregator,
969) -> glib::ffi::gboolean {
970 unsafe {
971 let instance = &*(ptr as *mut T::Instance);
972 let imp = instance.imp();
973
974 gst::panic_to_error!(imp, false, {
975 match imp.stop() {
976 Ok(()) => true,
977 Err(err) => {
978 imp.post_error_message(err);
979 false
980 }
981 }
982 })
983 .into_glib()
984 }
985}
986
987unsafe extern "C" fn aggregator_get_next_time<T: AggregatorImpl>(
988 ptr: *mut ffi::GstAggregator,
989) -> gst::ffi::GstClockTime {
990 unsafe {
991 let instance = &*(ptr as *mut T::Instance);
992 let imp = instance.imp();
993
994 gst::panic_to_error!(imp, gst::ClockTime::NONE, { imp.next_time() }).into_glib()
995 }
996}
997
998unsafe extern "C" fn aggregator_create_new_pad<T: AggregatorImpl>(
999 ptr: *mut ffi::GstAggregator,
1000 templ: *mut gst::ffi::GstPadTemplate,
1001 req_name: *const libc::c_char,
1002 caps: *const gst::ffi::GstCaps,
1003) -> *mut ffi::GstAggregatorPad {
1004 unsafe {
1005 let instance = &*(ptr as *mut T::Instance);
1006 let imp = instance.imp();
1007
1008 gst::panic_to_error!(imp, None, {
1009 let req_name: Borrowed<Option<glib::GString>> = from_glib_borrow(req_name);
1010
1011 imp.create_new_pad(
1012 &from_glib_borrow(templ),
1013 req_name.as_ref().as_ref().map(|s| s.as_str()),
1014 Option::<gst::Caps>::from_glib_borrow(caps)
1015 .as_ref()
1016 .as_ref(),
1017 )
1018 })
1019 .into_glib_ptr()
1020 }
1021}
1022
1023unsafe extern "C" fn aggregator_update_src_caps<T: AggregatorImpl>(
1024 ptr: *mut ffi::GstAggregator,
1025 caps: *mut gst::ffi::GstCaps,
1026 res: *mut *mut gst::ffi::GstCaps,
1027) -> gst::ffi::GstFlowReturn {
1028 unsafe {
1029 let instance = &*(ptr as *mut T::Instance);
1030 let imp = instance.imp();
1031
1032 *res = ptr::null_mut();
1033
1034 gst::panic_to_error!(imp, gst::FlowReturn::Error, {
1035 match imp.update_src_caps(&from_glib_borrow(caps)) {
1036 Ok(res_caps) => {
1037 *res = res_caps.into_glib_ptr();
1038 gst::FlowReturn::Ok
1039 }
1040 Err(err) => err.into(),
1041 }
1042 })
1043 .into_glib()
1044 }
1045}
1046
1047unsafe extern "C" fn aggregator_fixate_src_caps<T: AggregatorImpl>(
1048 ptr: *mut ffi::GstAggregator,
1049 caps: *mut gst::ffi::GstCaps,
1050) -> *mut gst::ffi::GstCaps {
1051 unsafe {
1052 let instance = &*(ptr as *mut T::Instance);
1053 let imp = instance.imp();
1054
1055 gst::panic_to_error!(imp, gst::Caps::new_empty(), {
1056 imp.fixate_src_caps(from_glib_full(caps))
1057 })
1058 .into_glib_ptr()
1059 }
1060}
1061
1062unsafe extern "C" fn aggregator_negotiated_src_caps<T: AggregatorImpl>(
1063 ptr: *mut ffi::GstAggregator,
1064 caps: *mut gst::ffi::GstCaps,
1065) -> glib::ffi::gboolean {
1066 unsafe {
1067 let instance = &*(ptr as *mut T::Instance);
1068 let imp = instance.imp();
1069
1070 gst::panic_to_error!(imp, false, {
1071 match imp.negotiated_src_caps(&from_glib_borrow(caps)) {
1072 Ok(()) => true,
1073 Err(err) => {
1074 err.log_with_imp(imp);
1075 false
1076 }
1077 }
1078 })
1079 .into_glib()
1080 }
1081}
1082
1083unsafe extern "C" fn aggregator_propose_allocation<T: AggregatorImpl>(
1084 ptr: *mut ffi::GstAggregator,
1085 pad: *mut ffi::GstAggregatorPad,
1086 decide_query: *mut gst::ffi::GstQuery,
1087 query: *mut gst::ffi::GstQuery,
1088) -> glib::ffi::gboolean {
1089 unsafe {
1090 let instance = &*(ptr as *mut T::Instance);
1091 let imp = instance.imp();
1092 let decide_query = if decide_query.is_null() {
1093 None
1094 } else {
1095 match gst::QueryRef::from_ptr(decide_query).view() {
1096 gst::QueryView::Allocation(allocation) => Some(allocation),
1097 _ => unreachable!(),
1098 }
1099 };
1100 let query = match gst::QueryRef::from_mut_ptr(query).view_mut() {
1101 gst::QueryViewMut::Allocation(allocation) => allocation,
1102 _ => unreachable!(),
1103 };
1104
1105 gst::panic_to_error!(imp, false, {
1106 match imp.propose_allocation(&from_glib_borrow(pad), decide_query, query) {
1107 Ok(()) => true,
1108 Err(err) => {
1109 err.log_with_imp(imp);
1110 false
1111 }
1112 }
1113 })
1114 .into_glib()
1115 }
1116}
1117
1118unsafe extern "C" fn aggregator_decide_allocation<T: AggregatorImpl>(
1119 ptr: *mut ffi::GstAggregator,
1120 query: *mut gst::ffi::GstQuery,
1121) -> glib::ffi::gboolean {
1122 unsafe {
1123 let instance = &*(ptr as *mut T::Instance);
1124 let imp = instance.imp();
1125 let query = match gst::QueryRef::from_mut_ptr(query).view_mut() {
1126 gst::QueryViewMut::Allocation(allocation) => allocation,
1127 _ => unreachable!(),
1128 };
1129
1130 gst::panic_to_error!(imp, false, {
1131 match imp.decide_allocation(query) {
1132 Ok(()) => true,
1133 Err(err) => {
1134 err.log_with_imp(imp);
1135 false
1136 }
1137 }
1138 })
1139 .into_glib()
1140 }
1141}
1142
1143#[cfg(feature = "v1_18")]
1144#[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
1145unsafe extern "C" fn aggregator_negotiate<T: AggregatorImpl>(
1146 ptr: *mut ffi::GstAggregator,
1147) -> glib::ffi::gboolean {
1148 unsafe {
1149 let instance = &*(ptr as *mut T::Instance);
1150 let imp = instance.imp();
1151
1152 gst::panic_to_error!(imp, false, { imp.negotiate() }).into_glib()
1153 }
1154}
1155
1156#[cfg(feature = "v1_18")]
1157#[cfg_attr(docsrs, doc(cfg(feature = "v1_18")))]
1158unsafe extern "C" fn aggregator_peek_next_sample<T: AggregatorImpl>(
1159 ptr: *mut ffi::GstAggregator,
1160 pad: *mut ffi::GstAggregatorPad,
1161) -> *mut gst::ffi::GstSample {
1162 unsafe {
1163 let instance = &*(ptr as *mut T::Instance);
1164 let imp = instance.imp();
1165
1166 gst::panic_to_error!(imp, None, { imp.peek_next_sample(&from_glib_borrow(pad)) })
1167 .into_glib_ptr()
1168 }
1169}