1 /*
2  * This file is part of gtkD.
3  *
4  * gtkD is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU Lesser General Public License
6  * as published by the Free Software Foundation; either version 3
7  * of the License, or (at your option) any later version, with
8  * some exceptions, please read the COPYING file.
9  *
10  * gtkD is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public License
16  * along with gtkD; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110, USA
18  */
19  
20 // generated automatically - do not change
21 // find conversion definition on APILookup.txt
22 // implement new conversion functionalities on the wrap.utils pakage
23 
24 /*
25  * Conversion parameters:
26  * inFile  = GstBin.html
27  * outPack = gstreamer
28  * outFile = Bin
29  * strct   = GstBin
30  * realStrct=
31  * ctorStrct=GstElement
32  * clss    = Bin
33  * interf  = 
34  * class Code: Yes
35  * interface Code: No
36  * template for:
37  * extend  = 
38  * implements:
39  * prefixes:
40  * 	- gst_bin_
41  * omit structs:
42  * omit prefixes:
43  * omit code:
44  * omit signals:
45  * imports:
46  * 	- glib.Str
47  * 	- gstreamer.Element
48  * 	- gstreamer.Iterator
49  * 	- gstreamer.Pad
50  * structWrap:
51  * 	- GstElement* -> Element
52  * 	- GstIterator* -> Iterator
53  * 	- GstPad* -> Pad
54  * module aliases:
55  * local aliases:
56  * overrides:
57  */
58 
59 module gstreamer.Bin;
60 
61 public  import gstreamerc.gstreamertypes;
62 
63 private import gstreamerc.gstreamer;
64 private import glib.ConstructionException;
65 private import gobject.ObjectG;
66 
67 private import gobject.Signals;
68 public  import gtkc.gdktypes;
69 
70 private import glib.Str;
71 private import gstreamer.Element;
72 private import gstreamer.Iterator;
73 private import gstreamer.Pad;
74 
75 
76 
77 private import gstreamer.Element;
78 
79 /**
80  * GstBin is an element that can contain other GstElement, allowing them to be
81  * managed as a group.
82  * Pads from the child elements can be ghosted to the bin, see GstGhostPad.
83  * This makes the bin look like any other elements and enables creation of
84  * higher-level abstraction elements.
85  *
86  * A new GstBin is created with gst_bin_new(). Use a GstPipeline instead if you
87  * want to create a toplevel bin because a normal bin doesn't have a bus or
88  * handle clock distribution of its own.
89  *
90  * After the bin has been created you will typically add elements to it with
91  * gst_bin_add(). You can remove elements with gst_bin_remove().
92  *
93  * An element can be retrieved from a bin with gst_bin_get_by_name(), using the
94  * elements name. gst_bin_get_by_name_recurse_up() is mainly used for internal
95  * purposes and will query the parent bins when the element is not found in the
96  * current bin.
97  *
98  * An iterator of elements in a bin can be retrieved with
99  * gst_bin_iterate_elements(). Various other iterators exist to retrieve the
100  * elements in a bin.
101  *
102  * gst_object_unref() is used to drop your reference to the bin.
103  *
104  * The "element-added" signal is fired whenever a new element is added to
105  * the bin. Likewise the "element-removed" signal is fired whenever an
106  * element is removed from the bin.
107  *
108  * Notes
109  *
110  * A GstBin internally intercepts every GstMessage posted by its children and
111  * implements the following default behaviour for each of them:
112  *
113  * GST_MESSAGE_EOS
114  *
115  * This message is only posted by sinks in the PLAYING
116  *  state. If all sinks posted the EOS message, this bin will post and EOS
117  *  message upwards.
118  *
119  * GST_MESSAGE_SEGMENT_START
120  *
121  * just collected and never forwarded upwards.
122  *  The messages are used to decide when all elements have completed playback
123  *  of their segment.
124  *
125  * GST_MESSAGE_SEGMENT_DONE
126  *
127  *  Is posted by GstBin when all elements that posted
128  *  a SEGMENT_START have posted a SEGMENT_DONE.
129  *
130  * GST_MESSAGE_DURATION_CHANGED
131  *
132  *  Is posted by an element that detected a change
133  *  in the stream duration. The default bin behaviour is to clear any
134  *  cached duration values so that the next duration query will perform
135  *  a full duration recalculation. The duration change is posted to the
136  *  application so that it can refetch the new duration with a duration
137  *  query. Note that these messages can be posted before the bin is
138  *  prerolled, in which case the duration query might fail.
139  *
140  * GST_MESSAGE_CLOCK_LOST
141  *
142  *  This message is posted by an element when it
143  *  can no longer provide a clock. The default bin behaviour is to
144  *  check if the lost clock was the one provided by the bin. If so and
145  *  the bin is currently in the PLAYING state, the message is forwarded to
146  *  the bin parent.
147  *  This message is also generated when a clock provider is removed from
148  *  the bin. If this message is received by the application, it should
149  *  PAUSE the pipeline and set it back to PLAYING to force a new clock
150  *  distribution.
151  *
152  * GST_MESSAGE_CLOCK_PROVIDE
153  *
154  *  This message is generated when an element
155  *  can provide a clock. This mostly happens when a new clock
156  *  provider is added to the bin. The default behaviour of the bin is to
157  *  mark the currently selected clock as dirty, which will perform a clock
158  *  recalculation the next time the bin is asked to provide a clock.
159  *  This message is never sent tot the application but is forwarded to
160  *  the parent of the bin.
161  *
162  * OTHERS
163  *
164  *  posted upwards.
165  *
166  * A GstBin implements the following default behaviour for answering to a
167  * GstQuery:
168  *
169  * GST_QUERY_DURATION
170  *
171  * If the query has been asked before with the same format
172  *  and the bin is a toplevel bin (ie. has no parent),
173  *  use the cached previous value. If no previous value was cached, the
174  *  query is sent to all sink elements in the bin and the MAXIMUM of all
175  *  values is returned. If the bin is a toplevel bin the value is cached.
176  *  If no sinks are available in the bin, the query fails.
177  *
178  * GST_QUERY_POSITION
179  *
180  * The query is sent to all sink elements in the bin and the
181  *  MAXIMUM of all values is returned. If no sinks are available in the bin,
182  *  the query fails.
183  *
184  * OTHERS
185  *
186  * the query is forwarded to all sink elements, the result
187  *  of the first sink that answers the query successfully is returned. If no
188  *  sink is in the bin, the query fails.
189  *
190  * A GstBin will by default forward any event sent to it to all sink elements.
191  * If all the sinks return TRUE, the bin will also return TRUE, else FALSE is
192  * returned. If no sinks are in the bin, the event handler will return TRUE.
193  *
194  * Last reviewed on 2012-03-28 (0.11.3)
195  */
196 public class Bin : Element
197 {
198 	
199 	/** the main Gtk struct */
200 	protected GstBin* gstBin;
201 	
202 	
203 	public GstBin* getBinStruct()
204 	{
205 		return gstBin;
206 	}
207 	
208 	
209 	/** the main Gtk struct as a void* */
210 	protected override void* getStruct()
211 	{
212 		return cast(void*)gstBin;
213 	}
214 	
215 	/**
216 	 * Sets our main struct and passes it to the parent class
217 	 */
218 	public this (GstBin* gstBin)
219 	{
220 		super(cast(GstElement*)gstBin);
221 		this.gstBin = gstBin;
222 	}
223 	
224 	protected override void setStruct(GObject* obj)
225 	{
226 		super.setStruct(obj);
227 		gstBin = cast(GstBin*)obj;
228 	}
229 	
230 	/** */
231 	public this(Element elem)
232 	{
233 		super( elem.getElementStruct() );
234 		this.gstBin = cast(GstBin*)elem.getElementStruct();
235 	}
236 	
237 	/**
238 	 */
239 	int[string] connectedSignals;
240 	
241 	bool delegate(Bin)[] onDoLatencyListeners;
242 	/**
243 	 * Will be emitted when the bin needs to perform latency calculations. This
244 	 * signal is only emited for toplevel bins or when async-handling is
245 	 * enabled.
246 	 * Only one signal handler is invoked. If no signals are connected, the
247 	 * default handler is invoked, which will query and distribute the lowest
248 	 * possible latency to all sinks.
249 	 * Connect to this signal if the default latency calculations are not
250 	 * sufficient, like when you need different latencies for different sinks in
251 	 * the same pipeline.
252 	 */
253 	void addOnDoLatency(bool delegate(Bin) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
254 	{
255 		if ( !("do-latency" in connectedSignals) )
256 		{
257 			Signals.connectData(
258 			getStruct(),
259 			"do-latency",
260 			cast(GCallback)&callBackDoLatency,
261 			cast(void*)this,
262 			null,
263 			connectFlags);
264 			connectedSignals["do-latency"] = 1;
265 		}
266 		onDoLatencyListeners ~= dlg;
267 	}
268 	extern(C) static gboolean callBackDoLatency(GstBin* binStruct, Bin _bin)
269 	{
270 		foreach ( bool delegate(Bin) dlg ; _bin.onDoLatencyListeners )
271 		{
272 			if ( dlg(_bin) )
273 			{
274 				return 1;
275 			}
276 		}
277 		
278 		return 0;
279 	}
280 	
281 	void delegate(Element, Bin)[] onElementAddedListeners;
282 	/**
283 	 * Will be emitted after the element was added to the bin.
284 	 */
285 	void addOnElementAdded(void delegate(Element, Bin) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
286 	{
287 		if ( !("element-added" in connectedSignals) )
288 		{
289 			Signals.connectData(
290 			getStruct(),
291 			"element-added",
292 			cast(GCallback)&callBackElementAdded,
293 			cast(void*)this,
294 			null,
295 			connectFlags);
296 			connectedSignals["element-added"] = 1;
297 		}
298 		onElementAddedListeners ~= dlg;
299 	}
300 	extern(C) static void callBackElementAdded(GstBin* binStruct, GstElement* element, Bin _bin)
301 	{
302 		foreach ( void delegate(Element, Bin) dlg ; _bin.onElementAddedListeners )
303 		{
304 			dlg(ObjectG.getDObject!(Element)(element), _bin);
305 		}
306 	}
307 	
308 	void delegate(Element, Bin)[] onElementRemovedListeners;
309 	/**
310 	 * Will be emitted after the element was removed from the bin.
311 	 */
312 	void addOnElementRemoved(void delegate(Element, Bin) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
313 	{
314 		if ( !("element-removed" in connectedSignals) )
315 		{
316 			Signals.connectData(
317 			getStruct(),
318 			"element-removed",
319 			cast(GCallback)&callBackElementRemoved,
320 			cast(void*)this,
321 			null,
322 			connectFlags);
323 			connectedSignals["element-removed"] = 1;
324 		}
325 		onElementRemovedListeners ~= dlg;
326 	}
327 	extern(C) static void callBackElementRemoved(GstBin* binStruct, GstElement* element, Bin _bin)
328 	{
329 		foreach ( void delegate(Element, Bin) dlg ; _bin.onElementRemovedListeners )
330 		{
331 			dlg(ObjectG.getDObject!(Element)(element), _bin);
332 		}
333 	}
334 	
335 	
336 	/**
337 	 * Creates a new bin with the given name.
338 	 * Params:
339 	 * name = the name of the new bin
340 	 * Throws: ConstructionException GTK+ fails to create the object.
341 	 */
342 	public this (string name)
343 	{
344 		// GstElement * gst_bin_new (const gchar *name);
345 		auto p = gst_bin_new(Str.toStringz(name));
346 		if(p is null)
347 		{
348 			throw new ConstructionException("null returned by gst_bin_new(Str.toStringz(name))");
349 		}
350 		this(cast(GstBin*) p);
351 	}
352 	
353 	/**
354 	 * Adds the given element to the bin. Sets the element's parent, and thus
355 	 * takes ownership of the element. An element can only be added to one bin.
356 	 * If the element's pads are linked to other pads, the pads will be unlinked
357 	 * before the element is added to the bin.
358 	 * Note
359 	 * When you add an element to an already-running pipeline, you will have to
360 	 * take care to set the state of the newly-added element to the desired
361 	 * state (usually PLAYING or PAUSED, same you set the pipeline to originally)
362 	 * with gst_element_set_state(), or use gst_element_sync_state_with_parent().
363 	 * The bin or pipeline will not take care of this for you.
364 	 * MT safe.
365 	 * Params:
366 	 * element = the GstElement to add. [transfer full]
367 	 * Returns: TRUE if the element could be added, FALSE if the bin does not want to accept the element.
368 	 */
369 	public int add(Element element)
370 	{
371 		// gboolean gst_bin_add (GstBin *bin,  GstElement *element);
372 		return gst_bin_add(gstBin, (element is null) ? null : element.getElementStruct());
373 	}
374 	
375 	/**
376 	 * Removes the element from the bin, unparenting it as well.
377 	 * Unparenting the element means that the element will be dereferenced,
378 	 * so if the bin holds the only reference to the element, the element
379 	 * will be freed in the process of removing it from the bin. If you
380 	 * want the element to still exist after removing, you need to call
381 	 * gst_object_ref() before removing it from the bin.
382 	 * If the element's pads are linked to other pads, the pads will be unlinked
383 	 * before the element is removed from the bin.
384 	 * MT safe.
385 	 * Params:
386 	 * element = the GstElement to remove. [transfer none]
387 	 * Returns: TRUE if the element could be removed, FALSE if the bin does not want to remove the element.
388 	 */
389 	public int remove(Element element)
390 	{
391 		// gboolean gst_bin_remove (GstBin *bin,  GstElement *element);
392 		return gst_bin_remove(gstBin, (element is null) ? null : element.getElementStruct());
393 	}
394 	
395 	/**
396 	 * Gets the element with the given name from a bin. This
397 	 * function recurses into child bins.
398 	 * Returns NULL if no element with the given name is found in the bin.
399 	 * MT safe. Caller owns returned reference.
400 	 * Params:
401 	 * name = the element name to search for
402 	 * Returns: the GstElement with the given name, or NULL. [transfer full]
403 	 */
404 	public Element getByName(string name)
405 	{
406 		// GstElement * gst_bin_get_by_name (GstBin *bin,  const gchar *name);
407 		auto p = gst_bin_get_by_name(gstBin, Str.toStringz(name));
408 		
409 		if(p is null)
410 		{
411 			return null;
412 		}
413 		
414 		return ObjectG.getDObject!(Element)(cast(GstElement*) p);
415 	}
416 	
417 	/**
418 	 * Gets the element with the given name from this bin. If the
419 	 * element is not found, a recursion is performed on the parent bin.
420 	 * Params:
421 	 * name = the element name to search for
422 	 * Returns: the GstElement with the given name, or NULL. [transfer full]
423 	 */
424 	public Element getByNameRecurseUp(string name)
425 	{
426 		// GstElement * gst_bin_get_by_name_recurse_up (GstBin *bin,  const gchar *name);
427 		auto p = gst_bin_get_by_name_recurse_up(gstBin, Str.toStringz(name));
428 		
429 		if(p is null)
430 		{
431 			return null;
432 		}
433 		
434 		return ObjectG.getDObject!(Element)(cast(GstElement*) p);
435 	}
436 	
437 	/**
438 	 * Looks for an element inside the bin that implements the given
439 	 * interface. If such an element is found, it returns the element.
440 	 * You can cast this element to the given interface afterwards. If you want
441 	 * all elements that implement the interface, use
442 	 * gst_bin_iterate_all_by_interface(). This function recurses into child bins.
443 	 * MT safe. Caller owns returned reference.
444 	 * Params:
445 	 * iface = the GType of an interface
446 	 * Returns: A GstElement inside the bin implementing the interface. [transfer full]
447 	 */
448 	public Element getByInterface(GType iface)
449 	{
450 		// GstElement * gst_bin_get_by_interface (GstBin *bin,  GType iface);
451 		auto p = gst_bin_get_by_interface(gstBin, iface);
452 		
453 		if(p is null)
454 		{
455 			return null;
456 		}
457 		
458 		return ObjectG.getDObject!(Element)(cast(GstElement*) p);
459 	}
460 	
461 	/**
462 	 * Gets an iterator for the elements in this bin.
463 	 * MT safe. Caller owns returned value.
464 	 * Returns: a GstIterator of GstElement, or NULL. [transfer full]
465 	 */
466 	public Iterator iterateElements()
467 	{
468 		// GstIterator * gst_bin_iterate_elements (GstBin *bin);
469 		auto p = gst_bin_iterate_elements(gstBin);
470 		
471 		if(p is null)
472 		{
473 			return null;
474 		}
475 		
476 		return ObjectG.getDObject!(Iterator)(cast(GstIterator*) p);
477 	}
478 	
479 	/**
480 	 * Gets an iterator for the elements in this bin.
481 	 * This iterator recurses into GstBin children.
482 	 * MT safe. Caller owns returned value.
483 	 * Returns: a GstIterator of GstElement, or NULL. [transfer full]
484 	 */
485 	public Iterator iterateRecurse()
486 	{
487 		// GstIterator * gst_bin_iterate_recurse (GstBin *bin);
488 		auto p = gst_bin_iterate_recurse(gstBin);
489 		
490 		if(p is null)
491 		{
492 			return null;
493 		}
494 		
495 		return ObjectG.getDObject!(Iterator)(cast(GstIterator*) p);
496 	}
497 	
498 	/**
499 	 * Gets an iterator for all elements in the bin that have the
500 	 * GST_ELEMENT_FLAG_SINK flag set.
501 	 * MT safe. Caller owns returned value.
502 	 * Returns: a GstIterator of GstElement, or NULL. [transfer full]
503 	 */
504 	public Iterator iterateSinks()
505 	{
506 		// GstIterator * gst_bin_iterate_sinks (GstBin *bin);
507 		auto p = gst_bin_iterate_sinks(gstBin);
508 		
509 		if(p is null)
510 		{
511 			return null;
512 		}
513 		
514 		return ObjectG.getDObject!(Iterator)(cast(GstIterator*) p);
515 	}
516 	
517 	/**
518 	 * Gets an iterator for the elements in this bin in topologically
519 	 * sorted order. This means that the elements are returned from
520 	 * the most downstream elements (sinks) to the sources.
521 	 * This function is used internally to perform the state changes
522 	 * of the bin elements and for clock selection.
523 	 * MT safe. Caller owns returned value.
524 	 * Returns: a GstIterator of GstElement, or NULL. [transfer full]
525 	 */
526 	public Iterator iterateSorted()
527 	{
528 		// GstIterator * gst_bin_iterate_sorted (GstBin *bin);
529 		auto p = gst_bin_iterate_sorted(gstBin);
530 		
531 		if(p is null)
532 		{
533 			return null;
534 		}
535 		
536 		return ObjectG.getDObject!(Iterator)(cast(GstIterator*) p);
537 	}
538 	
539 	/**
540 	 * Gets an iterator for all elements in the bin that have the
541 	 * GST_ELEMENT_FLAG_SOURCE flag set.
542 	 * MT safe. Caller owns returned value.
543 	 * Returns: a GstIterator of GstElement, or NULL. [transfer full]
544 	 */
545 	public Iterator iterateSources()
546 	{
547 		// GstIterator * gst_bin_iterate_sources (GstBin *bin);
548 		auto p = gst_bin_iterate_sources(gstBin);
549 		
550 		if(p is null)
551 		{
552 			return null;
553 		}
554 		
555 		return ObjectG.getDObject!(Iterator)(cast(GstIterator*) p);
556 	}
557 	
558 	/**
559 	 * Looks for all elements inside the bin that implements the given
560 	 * interface. You can safely cast all returned elements to the given interface.
561 	 * The function recurses inside child bins. The iterator will yield a series
562 	 * of GstElement that should be unreffed after use.
563 	 * MT safe. Caller owns returned value.
564 	 * Params:
565 	 * iface = the GType of an interface
566 	 * Returns: a GstIterator of GstElement for all elements in the bin implementing the given interface, or NULL. [transfer full]
567 	 */
568 	public Iterator iterateAllByInterface(GType iface)
569 	{
570 		// GstIterator * gst_bin_iterate_all_by_interface (GstBin *bin,  GType iface);
571 		auto p = gst_bin_iterate_all_by_interface(gstBin, iface);
572 		
573 		if(p is null)
574 		{
575 			return null;
576 		}
577 		
578 		return ObjectG.getDObject!(Iterator)(cast(GstIterator*) p);
579 	}
580 	
581 	/**
582 	 * Query bin for the current latency using and reconfigures this latency to all the
583 	 * elements with a LATENCY event.
584 	 * This method is typically called on the pipeline when a GST_MESSAGE_LATENCY
585 	 * is posted on the bus.
586 	 * This function simply emits the 'do-latency' signal so any custom latency
587 	 * calculations will be performed.
588 	 * Returns: TRUE if the latency could be queried and reconfigured.
589 	 */
590 	public int recalculateLatency()
591 	{
592 		// gboolean gst_bin_recalculate_latency (GstBin *bin);
593 		return gst_bin_recalculate_latency(gstBin);
594 	}
595 	
596 	/**
597 	 * Recursively looks for elements with an unlinked pad of the given
598 	 * direction within the specified bin and returns an unlinked pad
599 	 * if one is found, or NULL otherwise. If a pad is found, the caller
600 	 * owns a reference to it and should use gst_object_unref() on the
601 	 * pad when it is not needed any longer.
602 	 * Params:
603 	 * direction = whether to look for an unlinked source or sink pad
604 	 * Returns: unlinked pad of the given direction, or NULL. [transfer full]
605 	 */
606 	public Pad findUnlinkedPad(GstPadDirection direction)
607 	{
608 		// GstPad * gst_bin_find_unlinked_pad (GstBin *bin,  GstPadDirection direction);
609 		auto p = gst_bin_find_unlinked_pad(gstBin, direction);
610 		
611 		if(p is null)
612 		{
613 			return null;
614 		}
615 		
616 		return ObjectG.getDObject!(Pad)(cast(GstPad*) p);
617 	}
618 }