Commit 26c9fb0d authored by Ronald S. Bultje's avatar Ronald S. Bultje
Browse files

docs/pwg/advanced_interfaces.xml: Add documentation on propertyprobing.

Original commit message from CVS:
2004-01-28  Ronald Bultje  <rbultje@ronald.bitfreak.net>

* docs/pwg/advanced_interfaces.xml:
Add documentation on propertyprobing.
* docs/pwg/advanced_events.xml:
* docs/pwg/advanced_tagging.xml:
* docs/pwg/building_boiler.xml:
* docs/pwg/building_filterfactory.xml:
* docs/pwg/pwg.xml:
Move filterfactory and tagging into their own chapter, add a chapter
on events. all these are empty placeholders that will be filled in
some day.
parent d4b1febd
2004-01-28 Ronald Bultje <rbultje@ronald.bitfreak.net>
* docs/pwg/advanced_interfaces.xml:
Add documentation on propertyprobing.
* docs/pwg/advanced_events.xml:
* docs/pwg/advanced_tagging.xml:
* docs/pwg/building_boiler.xml:
* docs/pwg/building_filterfactory.xml:
* docs/pwg/pwg.xml:
Move filterfactory and tagging into their own chapter, add a chapter
on events. all these are empty placeholders that will be filled in
some day.
2004-01-28 Ronald Bultje <rbultje@ronald.bitfreak.net>
* docs/pwg/advanced_interfaces.xml:
......
<chapter id="cha-advanced-events">
<title>Events: Seeking, Navigation and More</title>
<para>
WRITEME
</para>
</chapter>
......@@ -39,6 +39,13 @@
allows us to query for interface availability based on runtime properties.
This extension is called <classname>GstImplementsInterface</classname>.
</para>
<para>
One important note: interfaces do <emphasis>not</emphasis> replace
properties. Rather, interfaces should be built <emphasis>next to</emphasis>
properties. There are two important reasons for this. Firstly, properties
can be saved in XML files. Secondly, properties can be specified on the
commandline (<filename>gst-launch</filename>).
</para>
<sect1 id="sect1-iface-general" xreflabel="How to Implement Interfaces">
<title>How to Implement Interfaces</title>
......@@ -137,6 +144,8 @@ gst_my_filter_some_interface_init (GstSomeInterface *iface)
to the implementation here.
</para>
<programlisting>
#include &lt;gst/mixer/mixer.h&gt;
typedef struct _GstMyFilter {
[..]
gint volume;
......@@ -277,7 +286,164 @@ gst_my_filter_mixer_interface_init (GstMixerClass *iface)
<sect1 id="sect1-iface-propprobe" xreflabel="Property Probe Interface">
<title>Property Probe Interface</title>
<para>
WRITEME
Property probing is a generic solution to the problem that properties'
value lists in an enumeration are static. We've shown enumerations in
<xref linkend="cha-building-args"/>. Property probing tries to accomplish
a goal similar to enumeration lists: to have a limited, explicit list of
allowed values for a property. There are two differences between
enumeration lists and probing. Firstly, enumerations only allow strings
as values; property probing works for any value type. Secondly, the
contents of a probed list of allowed values may change during the life
of an element. The contents of a enumeraiton list are static. Crrently,
property probing is being used for detection of devices (e.g. for OSS
elements, Video4linux elements, etc.). It could - in theory - be used
for any property, though.
</para>
<para>
Property probing stores the list of allowed (or recommended) values in a
<classname>GValueArray</classname> and returns that to the user.
<classname>NULL</classname> is a valid return value, too. The process of
property probing is separated over two virtual functions: one for probing
the property to create a <classname>GValueArray</classname>, and one to
retrieve the current <classname>GValueArray</classname>. Those two are
separated because probing might take a long time (several seconds). Also,
this simpliies interface implementation in elements. For the application,
there are functions that wrap those two. For more information on this,
have a look at the API reference for the
<classname>GstPropertyProbe</classname> interface.
</para>
<para>
Below is a example of property probing for the audio filter element; it
will probe for allowed values for the <quote>silent</quote> property.
Indeed, this value is a <classname>gboolean</classname> so it doesn't
make much sense. Then again, it's only an example.
</para>
<programlisting>
#include &lt;gst/propertyprobe/propertyprobe.h&gt;
static void gst_my_filter_probe_interface_init (GstPropertyProbeInterface *iface);
GType
gst_my_filter_get_type (void)
{
[..]
static const GInterfaceInfo probe_interface_info = {
(GInterfaceInitFunc) gst_my_filter_probe_interface_init,
NULL,
NULL
};
[..]
g_type_add_interface_static (my_filter_type,
GST_TYPE_PROPERTY_PROBE,
&amp;probe_interface_info);
[..]
}
static const GList *
gst_my_filter_probe_get_properties (GstPropertyProbe *probe)
{
GObjectClass *klass = G_OBJECT_GET_CLASS (probe);
static GList *props = NULL;
if (!props) {
GParamSpec *pspec;
pspec = g_object_class_find_property (klass, "silent");
props = g_list_append (props, pspec);
}
return props;
}
static gboolean
gst_my_filter_probe_needs_probe (GstPropertyProbe *probe,
guint prop_id,
const GParamSpec *pspec)
{
gboolean res = FALSE;
switch (prop_id) {
case ARG_SILENT:
res = FALSE;
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (probe, prop_id, pspec);
break;
}
return res;
}
static void
gst_my_filter_probe_probe_property (GstPropertyProbe *probe,
guint prop_id,
const GParamSpec *pspec)
{
switch (prop_id) {
case ARG_SILENT:
/* don't need to do much here... */
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (probe, prop_id, pspec);
break;
}
}
static GValueArray *
gst_my_filter_get_silent_values (GstMyFilter *filter)
{
GValueArray *array = g_value_array_new (2);
GValue value = { 0 };
g_value_init (&amp;value, G_TYPE_BOOLEAN);
/* add TRUE */
g_value_set_boolean (&amp;value, TRUE);
g_value_array_append (array, &amp;value);
/* add FALSE */
g_value_set_boolean (&amp;value, FALSE);
g_value_array_append (array, &amp;value);
g_value_unset (&amp;value);
return array;
}
static GValueArray *
gst_my_filter_probe_get_values (GstPropertyProbe *probe,
guint prop_id,
const GParamSpec *pspec)
{
GstMyFilter *filter = GST_MY_FILTER (probe);
GValueArray *array = NULL;
switch (prop_id) {
case ARG_SILENT:
array = gst_my_filter_get_silent_values (filter);
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (probe, prop_id, pspec);
break;
}
return array;
}
static void
gst_my_filter_probe_interface_init (GstPropertyProbeInterface *iface)
{
iface->get_properties = gst_my_filter_probe_get_properties;
iface->needs_probe = gst_my_filter_probe_needs_probe;
iface->probe_property = gst_my_filter_probe_probe_property;
iface->get_values = gst_my_filter_probe_get_values;
}
</programlisting>
<para>
You don't need to support any functions for getting or setting values.
All that is handled via the standard <classname>GObject</classname>
<function>_set_property ()</function> and <function>_get_property ()</function>
functions.
</para>
</sect1>
......@@ -301,11 +467,4 @@ gst_my_filter_mixer_interface_init (GstMixerClass *iface)
WRITEME
</para>
</sect1>
<sect1 id="sect1-iface-tagging" xreflabel="Tagging Interface">
<title>Tagging Interface</title>
<para>
WRITEME
</para>
</sect1>
</chapter>
<chapter id="cha-advanced-tagging">
<title>Tagging (Metadata and Streaminfo)</title>
<para>
WRITEME
</para>
</chapter>
......@@ -167,34 +167,6 @@ U gst-template/gst-app/src/Makefile.am
<!-- ############ sect1 ############# -->
<sect1 id="sect1-boiler-filterfactory" xreflabel="Creating a Filter With FilterFactory">
<title>Creating a Filter With FilterFactory (Future)</title>
<para>
A plan for the future is to create a FilterFactory, to make the process of
making a new filter a simple process of specifying a few details, and
writing a small amount of code to perform the actual data processing.
Ideally, a FilterFactory would perform the tasks of boilerplate creation,
code functionality implementation, and filter registration.
</para>
<para>
Unfortunately, this has not yet been implemented. Even when someone
eventually does write a FilterFactory, this element will not be able to
cover all the possibilities available for filter writing. Thus, some
plugins will always need to be manually coded and registered.
</para>
<para>
Here is a rough outline of what is planned: You run the FilterFactory and
give the factory a list of appropriate function pointers and data
structures to define a filter. With a reasonable measure of preprocessor
magic, you just need to provide a name for the filter and definitions of
the functions and data structures desired. Then you call a macro from
within plugin_init() that registers the new filter. All the fluff that
goes into the definition of a filter is thus be hidden from view.
</para>
</sect1>
<!-- ############ sect1 ############# -->
<sect1 id="sect1-boiler-details">
<title>GstElementDetails</title>
<para>
......
<chapter id="cha-building-filterfactory">
<title>Creating a Filter with a Filter Factory</title>
<para>
A plan for the future is to create a FilterFactory, to make the process of making a new filter a simple process of specifying a few details, and
writing a small amount of code to perform the actual data processing.
Ideally, a FilterFactory would perform the tasks of boilerplate creation,
code functionality implementation, and filter registration.
</para>
<para>
Unfortunately, this has not yet been implemented. Even when someone
eventually does write a FilterFactory, this element will not be able to
cover all the possibilities available for filter writing. Thus, some
plugins will always need to be manually coded and registered.
</para>
<para>
Here is a rough outline of what is planned: You run the FilterFactory and
give the factory a list of appropriate function pointers and data
structures to define a filter. With a reasonable measure of preprocessor
magic, you just need to provide a name for the filter and definitions of
the functions and data structures desired. Then you call a macro from
within plugin_init() that registers the new filter. All the fluff that
goes into the definition of a filter is thus be hidden from view.
</para>
</chapter>
......@@ -17,6 +17,7 @@
<!ENTITY BUILDING_PROPS SYSTEM "building_props.xml">
<!ENTITY BUILDING_SIGNALS SYSTEM "building_signals.xml">
<!ENTITY BUILDING_TESTAPP SYSTEM "building_testapp.xml">
<!ENTITY BUILDING_FILTERFACT SYSTEM "building_filterfactory.xml">
<!ENTITY ADVANCED_SCHEDULING SYSTEM "advanced_scheduling.xml">
<!ENTITY ADVANCED_TYPES SYSTEM "advanced_types.xml">
......@@ -25,6 +26,8 @@
<!ENTITY ADVANCED_DPARAMS SYSTEM "advanced_dparams.xml">
<!ENTITY ADVANCED_MIDI SYSTEM "advanced_midi.xml">
<!ENTITY ADVANCED_INTERFACES SYSTEM "advanced_interfaces.xml">
<!ENTITY ADVANCED_TAGGING SYSTEM "advanced_tagging.xml">
<!ENTITY ADVANCED_EVENTS SYSTEM "advanced_events.xml">
<!ENTITY OTHER_SOURCE SYSTEM "other_source.xml">
<!ENTITY OTHER_SINK SYSTEM "other_sink.xml">
......@@ -108,6 +111,7 @@
&BUILDING_PROPS;
&BUILDING_SIGNALS;
&BUILDING_TESTAPP;
&BUILDING_FILTERFACT;
</part>
<!-- ############ part ############# -->
......@@ -126,6 +130,8 @@
&ADVANCED_DPARAMS;
&ADVANCED_MIDI;
&ADVANCED_INTERFACES;
&ADVANCED_TAGGING;
&ADVANCED_EVENTS;
</part>
<!-- ############ part ############# -->
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment