gtkbuildable.c 10.2 KB
Newer Older
Johan Dahlin's avatar
Johan Dahlin committed
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
/* gtkbuildable.c
 * Copyright (C) 2006-2007 Async Open Source,
 *                         Johan Dahlin <jdahlin@async.com.br>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
Javier Jardón's avatar
Javier Jardón committed
16
 * License along with this library. If not, see <http://www.gnu.org/licenses/>.
Johan Dahlin's avatar
Johan Dahlin committed
17
18
 */

19
20
21
22
23
/**
 * SECTION:gtkbuildable
 * @Short_description: Interface for objects that can be built by GtkBuilder
 * @Title: GtkBuildable
 *
Volker Sobek's avatar
Volker Sobek committed
24
 * GtkBuildable allows objects to extend and customize their deserialization
25
 * from [GtkBuilder UI descriptions][BUILDER-UI].
26
27
 * The interface includes methods for setting names and properties of objects, 
 * parsing custom tags and constructing child objects.
28
29
30
 *
 * The GtkBuildable interface is implemented by all widgets and
 * many of the non-widget objects that are provided by GTK+. The
31
 * main user of this interface is #GtkBuilder. There should be
32
 * very little need for applications to call any of these functions directly.
33
 *
34
35
 * An object only needs to implement this interface if it needs to extend the
 * #GtkBuilder format or run any extra routines at deserialization time.
36
 */
Johan Dahlin's avatar
Johan Dahlin committed
37

38
#include "config.h"
Johan Dahlin's avatar
Johan Dahlin committed
39
40
41
42
#include "gtkbuildable.h"
#include "gtkintl.h"


43
44
typedef GtkBuildableIface GtkBuildableInterface;
G_DEFINE_INTERFACE (GtkBuildable, gtk_buildable, G_TYPE_OBJECT)
Johan Dahlin's avatar
Johan Dahlin committed
45

46
47
48
static void
gtk_buildable_default_init (GtkBuildableInterface *iface)
{
Johan Dahlin's avatar
Johan Dahlin committed
49
50
51
52
53
54
55
}

/**
 * gtk_buildable_set_name:
 * @buildable: a #GtkBuildable
 * @name: name to set
 *
Matthias Clasen's avatar
Matthias Clasen committed
56
 * Sets the name of the @buildable object.
Johan Dahlin's avatar
Johan Dahlin committed
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
 *
 * Since: 2.12
 **/
void
gtk_buildable_set_name (GtkBuildable *buildable,
                        const gchar  *name)
{
  GtkBuildableIface *iface;

  g_return_if_fail (GTK_IS_BUILDABLE (buildable));
  g_return_if_fail (name != NULL);

  iface = GTK_BUILDABLE_GET_IFACE (buildable);

  if (iface->set_name)
    (* iface->set_name) (buildable, name);
  else
    g_object_set_data_full (G_OBJECT (buildable),
			    "gtk-builder-name",
			    g_strdup (name),
			    g_free);
}

/**
 * gtk_buildable_get_name:
 * @buildable: a #GtkBuildable
 *
Matthias Clasen's avatar
Matthias Clasen committed
84
85
 * Gets the name of the @buildable object. 
 * 
86
 * #GtkBuilder sets the name based on the
87
 * [GtkBuilder UI definition][BUILDER-UI] 
Matthias Clasen's avatar
Matthias Clasen committed
88
 * used to construct the @buildable.
Johan Dahlin's avatar
Johan Dahlin committed
89
 *
Matthias Clasen's avatar
Matthias Clasen committed
90
91
 * Returns: the name set with gtk_buildable_set_name()
 *
Johan Dahlin's avatar
Johan Dahlin committed
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
 * Since: 2.12
 **/
const gchar *
gtk_buildable_get_name (GtkBuildable *buildable)
{
  GtkBuildableIface *iface;

  g_return_val_if_fail (GTK_IS_BUILDABLE (buildable), NULL);

  iface = GTK_BUILDABLE_GET_IFACE (buildable);

  if (iface->get_name)
    return (* iface->get_name) (buildable);
  else
    return (const gchar*)g_object_get_data (G_OBJECT (buildable),
					    "gtk-builder-name");
}

/**
111
 * gtk_buildable_add_child:
Johan Dahlin's avatar
Johan Dahlin committed
112
113
114
 * @buildable: a #GtkBuildable
 * @builder: a #GtkBuilder
 * @child: child to add
Johan Dahlin's avatar
Johan Dahlin committed
115
 * @type: (allow-none): kind of child or %NULL
Johan Dahlin's avatar
Johan Dahlin committed
116
 *
Matthias Clasen's avatar
Matthias Clasen committed
117
 * Adds a child to @buildable. @type is an optional string
Johan Dahlin's avatar
Johan Dahlin committed
118
119
120
121
122
 * describing how the child should be added.
 *
 * Since: 2.12
 **/
void
123
124
125
126
gtk_buildable_add_child (GtkBuildable *buildable,
			 GtkBuilder   *builder,
			 GObject      *child,
			 const gchar  *type)
Johan Dahlin's avatar
Johan Dahlin committed
127
128
129
130
131
132
133
{
  GtkBuildableIface *iface;

  g_return_if_fail (GTK_IS_BUILDABLE (buildable));
  g_return_if_fail (GTK_IS_BUILDER (builder));

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
134
  g_return_if_fail (iface->add_child != NULL);
Johan Dahlin's avatar
Johan Dahlin committed
135

136
  (* iface->add_child) (buildable, builder, child, type);
Johan Dahlin's avatar
Johan Dahlin committed
137
138
139
}

/**
140
 * gtk_buildable_set_buildable_property:
Johan Dahlin's avatar
Johan Dahlin committed
141
142
143
144
145
 * @buildable: a #GtkBuildable
 * @builder: a #GtkBuilder
 * @name: name of property
 * @value: value of property
 *
Matthias Clasen's avatar
Matthias Clasen committed
146
 * Sets the property name @name to @value on the @buildable object.
Johan Dahlin's avatar
Johan Dahlin committed
147
148
149
150
 *
 * Since: 2.12
 **/
void
151
152
153
154
gtk_buildable_set_buildable_property (GtkBuildable *buildable,
				      GtkBuilder   *builder,
				      const gchar  *name,
				      const GValue *value)
Johan Dahlin's avatar
Johan Dahlin committed
155
156
157
158
159
160
161
162
163
{
  GtkBuildableIface *iface;

  g_return_if_fail (GTK_IS_BUILDABLE (buildable));
  g_return_if_fail (GTK_IS_BUILDER (builder));
  g_return_if_fail (name != NULL);
  g_return_if_fail (value != NULL);

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
164
165
  if (iface->set_buildable_property)
    (* iface->set_buildable_property) (buildable, builder, name, value);
Johan Dahlin's avatar
Johan Dahlin committed
166
167
168
169
170
171
172
173
174
  else
    g_object_set_property (G_OBJECT (buildable), name, value);
}

/**
 * gtk_buildable_parser_finished:
 * @buildable: a #GtkBuildable
 * @builder: a #GtkBuilder
 *
Matthias Clasen's avatar
Matthias Clasen committed
175
 * Called when the builder finishes the parsing of a 
176
 * [GtkBuilder UI definition][BUILDER-UI]. 
Matthias Clasen's avatar
Matthias Clasen committed
177
178
179
 * Note that this will be called once for each time 
 * gtk_builder_add_from_file() or gtk_builder_add_from_string() 
 * is called on a builder.
Johan Dahlin's avatar
Johan Dahlin committed
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
 *
 * Since: 2.12
 **/
void
gtk_buildable_parser_finished (GtkBuildable *buildable,
			       GtkBuilder   *builder)
{
  GtkBuildableIface *iface;

  g_return_if_fail (GTK_IS_BUILDABLE (buildable));
  g_return_if_fail (GTK_IS_BUILDER (builder));

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
  if (iface->parser_finished)
    (* iface->parser_finished) (buildable, builder);
}

/**
Matthias Clasen's avatar
Matthias Clasen committed
198
 * gtk_buildable_construct_child:
Johan Dahlin's avatar
Johan Dahlin committed
199
200
201
202
 * @buildable: A #GtkBuildable
 * @builder: #GtkBuilder used to construct this object
 * @name: name of child to construct
 *
Matthias Clasen's avatar
Matthias Clasen committed
203
 * Constructs a child of @buildable with the name @name.
Johan Dahlin's avatar
Johan Dahlin committed
204
 *
William Jon McCann's avatar
William Jon McCann committed
205
 * #GtkBuilder calls this function if a “constructor” has been
Matthias Clasen's avatar
Matthias Clasen committed
206
 * specified in the UI definition.
Matthias Clasen's avatar
Matthias Clasen committed
207
 *
Matthias Clasen's avatar
Matthias Clasen committed
208
 * Returns: (transfer full): the constructed child
Johan Dahlin's avatar
Johan Dahlin committed
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
 *
 * Since: 2.12
 **/
GObject *
gtk_buildable_construct_child (GtkBuildable *buildable,
                               GtkBuilder   *builder,
                               const gchar  *name)
{
  GtkBuildableIface *iface;

  g_return_val_if_fail (GTK_IS_BUILDABLE (buildable), NULL);
  g_return_val_if_fail (GTK_IS_BUILDER (builder), NULL);
  g_return_val_if_fail (name != NULL, NULL);

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
  g_return_val_if_fail (iface->construct_child != NULL, NULL);

  return (* iface->construct_child) (buildable, builder, name);
}

/**
Matthias Clasen's avatar
Matthias Clasen committed
230
 * gtk_buildable_custom_tag_start:
Johan Dahlin's avatar
Johan Dahlin committed
231
232
 * @buildable: a #GtkBuildable
 * @builder: a #GtkBuilder used to construct this object
Johan Dahlin's avatar
Johan Dahlin committed
233
 * @child: (allow-none): child object or %NULL for non-child tags
Johan Dahlin's avatar
Johan Dahlin committed
234
 * @tagname: name of tag
235
 * @parser: (out): a #GMarkupParser to fill in
236
 * @data: (out): return location for user data that will be passed in 
Matthias Clasen's avatar
Matthias Clasen committed
237
 *   to parser functions
Johan Dahlin's avatar
Johan Dahlin committed
238
 *
239
 * This is called for each unknown element under `<child>`.
Johan Dahlin's avatar
Johan Dahlin committed
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
 * 
 * Returns: %TRUE if a object has a custom implementation, %FALSE
 *          if it doesn't.
 *
 * Since: 2.12
 **/
gboolean
gtk_buildable_custom_tag_start (GtkBuildable  *buildable,
                                GtkBuilder    *builder,
                                GObject       *child,
                                const gchar   *tagname,
                                GMarkupParser *parser,
                                gpointer      *data)
{
  GtkBuildableIface *iface;

  g_return_val_if_fail (GTK_IS_BUILDABLE (buildable), FALSE);
  g_return_val_if_fail (GTK_IS_BUILDER (builder), FALSE);
  g_return_val_if_fail (tagname != NULL, FALSE);

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
  g_return_val_if_fail (iface->custom_tag_start != NULL, FALSE);

  return (* iface->custom_tag_start) (buildable, builder, child,
                                      tagname, parser, data);
}

/**
Matthias Clasen's avatar
Matthias Clasen committed
268
 * gtk_buildable_custom_tag_end:
Johan Dahlin's avatar
Johan Dahlin committed
269
270
 * @buildable: A #GtkBuildable
 * @builder: #GtkBuilder used to construct this object
Johan Dahlin's avatar
Johan Dahlin committed
271
 * @child: (allow-none): child object or %NULL for non-child tags
Johan Dahlin's avatar
Johan Dahlin committed
272
 * @tagname: name of tag
273
 * @data: (type gpointer): user data that will be passed in to parser functions
Johan Dahlin's avatar
Johan Dahlin committed
274
 *
Matthias Clasen's avatar
Matthias Clasen committed
275
276
 * This is called at the end of each custom element handled by 
 * the buildable.
Johan Dahlin's avatar
Johan Dahlin committed
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
 *
 * Since: 2.12
 **/
void
gtk_buildable_custom_tag_end (GtkBuildable  *buildable,
                              GtkBuilder    *builder,
                              GObject       *child,
                              const gchar   *tagname,
                              gpointer      *data)
{
  GtkBuildableIface *iface;

  g_return_if_fail (GTK_IS_BUILDABLE (buildable));
  g_return_if_fail (GTK_IS_BUILDER (builder));
  g_return_if_fail (tagname != NULL);

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
  if (iface->custom_tag_end)
    (* iface->custom_tag_end) (buildable, builder, child, tagname, data);
}

/**
 * gtk_buildable_custom_finished:
 * @buildable: a #GtkBuildable
 * @builder: a #GtkBuilder
Johan Dahlin's avatar
Johan Dahlin committed
302
 * @child: (allow-none): child object or %NULL for non-child tags
Johan Dahlin's avatar
Johan Dahlin committed
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
 * @tagname: the name of the tag
 * @data: user data created in custom_tag_start
 *
 * This is similar to gtk_buildable_parser_finished() but is
 * called once for each custom tag handled by the @buildable.
 * 
 * Since: 2.12
 **/
void
gtk_buildable_custom_finished (GtkBuildable  *buildable,
			       GtkBuilder    *builder,
			       GObject       *child,
			       const gchar   *tagname,
			       gpointer       data)
{
  GtkBuildableIface *iface;

  g_return_if_fail (GTK_IS_BUILDABLE (buildable));
  g_return_if_fail (GTK_IS_BUILDER (builder));

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
  if (iface->custom_finished)
    (* iface->custom_finished) (buildable, builder, child, tagname, data);
}

/**
Matthias Clasen's avatar
Matthias Clasen committed
329
 * gtk_buildable_get_internal_child:
Johan Dahlin's avatar
Johan Dahlin committed
330
331
332
333
 * @buildable: a #GtkBuildable
 * @builder: a #GtkBuilder
 * @childname: name of child
 *
Matthias Clasen's avatar
Matthias Clasen committed
334
 * Get the internal child called @childname of the @buildable object.
Johan Dahlin's avatar
Johan Dahlin committed
335
 *
Matthias Clasen's avatar
Matthias Clasen committed
336
 * Returns: (transfer none): the internal child of the buildable object
Johan Dahlin's avatar
Johan Dahlin committed
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
 *
 * Since: 2.12
 **/
GObject *
gtk_buildable_get_internal_child (GtkBuildable *buildable,
                                  GtkBuilder   *builder,
                                  const gchar  *childname)
{
  GtkBuildableIface *iface;

  g_return_val_if_fail (GTK_IS_BUILDABLE (buildable), NULL);
  g_return_val_if_fail (GTK_IS_BUILDER (builder), NULL);
  g_return_val_if_fail (childname != NULL, NULL);

  iface = GTK_BUILDABLE_GET_IFACE (buildable);
  if (!iface->get_internal_child)
    return NULL;

  return (* iface->get_internal_child) (buildable, builder, childname);
}