1 | /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ |
---|
2 | /** |
---|
3 | * bonobo-widget.c: BonoboWidget object. |
---|
4 | * |
---|
5 | * Authors: |
---|
6 | * Nat Friedman (nat@helixcode.com) |
---|
7 | * |
---|
8 | * Copyright 1999 Helix Code, Inc. |
---|
9 | * |
---|
10 | * Bonobo component embedding for hydrocephalic imbeciles. |
---|
11 | * |
---|
12 | * Pure cane sugar. |
---|
13 | * |
---|
14 | * This purpose of BonoboWidget is to make container-side use of |
---|
15 | * Bonobo as easy as pie. This widget has two functions: |
---|
16 | * |
---|
17 | * 1. Provide a simple wrapper for embedding a single-view |
---|
18 | * subdocument. In this case, BonoboWidget handles creating |
---|
19 | * the embeddable, binding it to a local BonoboClientSite, |
---|
20 | * creating a view for it, and displaying the view. You can use |
---|
21 | * the accessor functions (bonobo_widget_get_view_frame, |
---|
22 | * etc) to get at the actual Bonobo objects which underlie the |
---|
23 | * whole process. |
---|
24 | * |
---|
25 | * In order to do this, just call: |
---|
26 | * |
---|
27 | * bw = bonobo_widget_new_subdoc ("moniker of subdoc embddable", |
---|
28 | * top_level_uicontainer); |
---|
29 | * |
---|
30 | * And then insert the 'bw' widget into the widget tree of your |
---|
31 | * application like so: |
---|
32 | * |
---|
33 | * gtk_container_add (some_container, bw); |
---|
34 | * |
---|
35 | * You are free to make the UIContainer argument to |
---|
36 | * bonobo_widget_new_subdoc() be CORBA_OBJECT_NIL. |
---|
37 | * |
---|
38 | * 2. Provide a simple wrapper for embedding Controls. Embedding |
---|
39 | * controls is already really easy, but BonoboWidget reduces |
---|
40 | * the work from about 5 lines to 1. To embed a given control, |
---|
41 | * just do: |
---|
42 | * |
---|
43 | * bw = bonobo_widget_new_control ("moniker for control"); |
---|
44 | * gtk_container_add (some_container, bw); |
---|
45 | * |
---|
46 | * Ta da! |
---|
47 | * |
---|
48 | * NB. A simple moniker might look like 'file:/tmp/a.jpeg' or |
---|
49 | * OAFIID:GNOME_Evolution_Calendar_Control |
---|
50 | */ |
---|
51 | |
---|
52 | #include <config.h> |
---|
53 | #include <gtk/gtksignal.h> |
---|
54 | #include <gtk/gtkmarshal.h> |
---|
55 | #include <bonobo/Bonobo.h> |
---|
56 | #include <bonobo/bonobo-main.h> |
---|
57 | #include <bonobo/bonobo-object.h> |
---|
58 | #include <bonobo/bonobo-widget.h> |
---|
59 | #include <bonobo/bonobo-exception.h> |
---|
60 | #include <bonobo/bonobo-moniker-util.h> |
---|
61 | |
---|
62 | struct _BonoboWidgetPrivate { |
---|
63 | |
---|
64 | BonoboObjectClient *server; |
---|
65 | |
---|
66 | /* |
---|
67 | * Control stuff. |
---|
68 | */ |
---|
69 | BonoboControlFrame *control_frame; |
---|
70 | |
---|
71 | /* |
---|
72 | * Subdocument (Embeddable/View) things. |
---|
73 | */ |
---|
74 | BonoboItemContainer *container; |
---|
75 | BonoboClientSite *client_site; |
---|
76 | BonoboViewFrame *view_frame; |
---|
77 | Bonobo_UIContainer uic; |
---|
78 | }; |
---|
79 | |
---|
80 | static BonoboWrapperClass *bonobo_widget_parent_class; |
---|
81 | |
---|
82 | static BonoboObjectClient * |
---|
83 | bonobo_widget_launch_component (const char *moniker, |
---|
84 | const char *if_name) |
---|
85 | { |
---|
86 | Bonobo_Unknown corba_ref; |
---|
87 | BonoboObjectClient *server; |
---|
88 | CORBA_Environment ev; |
---|
89 | |
---|
90 | CORBA_exception_init (&ev); |
---|
91 | corba_ref = bonobo_get_object (moniker, if_name, &ev); |
---|
92 | |
---|
93 | if (BONOBO_EX (&ev)) { |
---|
94 | char *txt; |
---|
95 | g_warning ("Activation exception '%s'", |
---|
96 | (txt = bonobo_exception_get_text (&ev))); |
---|
97 | g_free (txt); |
---|
98 | server = CORBA_OBJECT_NIL; |
---|
99 | } |
---|
100 | |
---|
101 | CORBA_exception_free (&ev); |
---|
102 | |
---|
103 | if (corba_ref == CORBA_OBJECT_NIL) |
---|
104 | return NULL; |
---|
105 | |
---|
106 | return bonobo_object_client_from_corba (corba_ref); |
---|
107 | } |
---|
108 | |
---|
109 | |
---|
110 | /* |
---|
111 | * |
---|
112 | * Control support for BonoboWidget. |
---|
113 | * |
---|
114 | */ |
---|
115 | /** |
---|
116 | * bonobo_widget_construct_control_from_objref: |
---|
117 | * @bw: A BonoboWidget to construct |
---|
118 | * @control: A CORBA Object reference to an IDL:Bonobo/Control:1.0 |
---|
119 | * @uic: Bonobo_UIContainer for the launched object. |
---|
120 | * |
---|
121 | * This is a constructor function. Only usable for wrapping and |
---|
122 | * derivation of new objects. For normal use, please refer to |
---|
123 | * #bonobo_widget_new_control_from_objref. |
---|
124 | * |
---|
125 | * Returns: A #BonoboWidget (the @bw) |
---|
126 | */ |
---|
127 | BonoboWidget * |
---|
128 | bonobo_widget_construct_control_from_objref (BonoboWidget *bw, |
---|
129 | Bonobo_Control control, |
---|
130 | Bonobo_UIContainer uic) |
---|
131 | { |
---|
132 | GtkWidget *control_frame_widget; |
---|
133 | |
---|
134 | /* |
---|
135 | * Create a local ControlFrame for it. |
---|
136 | */ |
---|
137 | bw->priv->control_frame = bonobo_control_frame_new (uic); |
---|
138 | |
---|
139 | bonobo_control_frame_bind_to_control (bw->priv->control_frame, control); |
---|
140 | |
---|
141 | /* |
---|
142 | * People that pass us controls get them sunk. |
---|
143 | */ |
---|
144 | bonobo_object_release_unref (control, NULL); |
---|
145 | |
---|
146 | bonobo_control_frame_set_autoactivate (bw->priv->control_frame, TRUE); |
---|
147 | |
---|
148 | /* |
---|
149 | * Grab the actual widget which visually contains the remote |
---|
150 | * Control. This is a GtkSocket, in reality. |
---|
151 | */ |
---|
152 | control_frame_widget = bonobo_control_frame_get_widget (bw->priv->control_frame); |
---|
153 | |
---|
154 | /* |
---|
155 | * Now stick it into this BonoboWidget. |
---|
156 | */ |
---|
157 | gtk_container_add (GTK_CONTAINER (bw), |
---|
158 | control_frame_widget); |
---|
159 | gtk_widget_show (control_frame_widget); |
---|
160 | |
---|
161 | if (uic != CORBA_OBJECT_NIL) |
---|
162 | bw->priv->uic = bonobo_object_dup_ref (uic, NULL); |
---|
163 | |
---|
164 | return bw; |
---|
165 | } |
---|
166 | |
---|
167 | /** |
---|
168 | * bonobo_widget_construct_control: |
---|
169 | * @bw: A BonoboWidget to construct |
---|
170 | * @moniker: A Moniker describing the object to be activated |
---|
171 | * @uic: Bonobo_UIContainer for the launched object. |
---|
172 | * |
---|
173 | * This is a constructor function. Only usable for wrapping and |
---|
174 | * derivation of new objects. For normal use, please refer to |
---|
175 | * #bonobo_widget_new_control. |
---|
176 | * |
---|
177 | * This function will unref the passed in @bw in case it cannot launch |
---|
178 | * the component and return %NULL in such a case. Otherwise it returns |
---|
179 | * the @bw itself. |
---|
180 | * |
---|
181 | * Returns: A #BonoboWidget or %NULL |
---|
182 | */ |
---|
183 | BonoboWidget * |
---|
184 | bonobo_widget_construct_control (BonoboWidget *bw, |
---|
185 | const char *moniker, |
---|
186 | Bonobo_UIContainer uic) |
---|
187 | { |
---|
188 | Bonobo_Control control; |
---|
189 | |
---|
190 | /* |
---|
191 | * Create the remote Control object. |
---|
192 | */ |
---|
193 | bw->priv->server = bonobo_widget_launch_component ( |
---|
194 | moniker, "IDL:Bonobo/Control:1.0"); |
---|
195 | if (bw->priv->server == NULL) { |
---|
196 | gtk_object_unref (GTK_OBJECT (bw)); |
---|
197 | return NULL; |
---|
198 | } |
---|
199 | |
---|
200 | control = BONOBO_OBJREF (bw->priv->server); |
---|
201 | |
---|
202 | return bonobo_widget_construct_control_from_objref (bw, control, uic); |
---|
203 | } |
---|
204 | |
---|
205 | /** |
---|
206 | * bonobo_widget_new_control_from_objref: |
---|
207 | * @control: A CORBA Object reference to an IDL:Bonobo/Control:1.0 |
---|
208 | * @uic: Bonobo_UIContainer for the launched object. |
---|
209 | * |
---|
210 | * This function is a simple wrapper for easily embedding controls |
---|
211 | * into applications. This function is used when you have already |
---|
212 | * a CORBA object reference to an IDL:Bonobo/Control:1.0 (the |
---|
213 | * @control) argument. |
---|
214 | * |
---|
215 | * Returns: the @control wrapped as a #GtkWidget. |
---|
216 | */ |
---|
217 | GtkWidget * |
---|
218 | bonobo_widget_new_control_from_objref (Bonobo_Control control, |
---|
219 | Bonobo_UIContainer uic) |
---|
220 | { |
---|
221 | BonoboWidget *bw; |
---|
222 | |
---|
223 | g_return_val_if_fail (control != CORBA_OBJECT_NIL, NULL); |
---|
224 | |
---|
225 | bw = gtk_type_new (BONOBO_WIDGET_TYPE); |
---|
226 | |
---|
227 | bw = bonobo_widget_construct_control_from_objref (bw, control, uic); |
---|
228 | |
---|
229 | if (bw == NULL) |
---|
230 | return NULL; |
---|
231 | |
---|
232 | return GTK_WIDGET (bw); |
---|
233 | } |
---|
234 | |
---|
235 | /** |
---|
236 | * bonobo_widget_new_control: |
---|
237 | * @moniker: A Moniker describing the object to be activated |
---|
238 | * @uic: Bonobo_UIContainer for the launched object. |
---|
239 | * |
---|
240 | * This function is a simple wrapper for easily embedding controls |
---|
241 | * into applications. It will launch the component identified by @id |
---|
242 | * and will return it as a GtkWidget. |
---|
243 | * |
---|
244 | * Returns: A #GtkWidget that is bound to the Bonobo Control. |
---|
245 | */ |
---|
246 | GtkWidget * |
---|
247 | bonobo_widget_new_control (const char *moniker, |
---|
248 | Bonobo_UIContainer uic) |
---|
249 | { |
---|
250 | BonoboWidget *bw; |
---|
251 | |
---|
252 | g_return_val_if_fail (moniker != NULL, NULL); |
---|
253 | |
---|
254 | bw = gtk_type_new (BONOBO_WIDGET_TYPE); |
---|
255 | |
---|
256 | bw = bonobo_widget_construct_control (bw, moniker, uic); |
---|
257 | |
---|
258 | if (bw == NULL) |
---|
259 | return NULL; |
---|
260 | else |
---|
261 | return GTK_WIDGET (bw); |
---|
262 | } |
---|
263 | |
---|
264 | /** |
---|
265 | * bonobo_widget_get_control_frame: |
---|
266 | * @bonobo_widget: a Bonobo Widget returned by one of the bonobo_widget_new() functions. |
---|
267 | * |
---|
268 | * Every IDL:Bonobo/Control:1.0 needs to be placed inside an |
---|
269 | * IDL:Bonobo/ControlFrame:1.0. This returns the BonoboControlFrame |
---|
270 | * object that wraps the Control in the @bonobo_widget. |
---|
271 | * |
---|
272 | * Returns: The BonoboControlFrame associated with the @bonobo_widget |
---|
273 | */ |
---|
274 | BonoboControlFrame * |
---|
275 | bonobo_widget_get_control_frame (BonoboWidget *bonobo_widget) |
---|
276 | { |
---|
277 | g_return_val_if_fail (bonobo_widget != NULL, NULL); |
---|
278 | g_return_val_if_fail (BONOBO_IS_WIDGET (bonobo_widget), NULL); |
---|
279 | |
---|
280 | return bonobo_widget->priv->control_frame; |
---|
281 | } |
---|
282 | |
---|
283 | |
---|
284 | /* |
---|
285 | * |
---|
286 | * Subdocument support for BonoboWidget. |
---|
287 | * |
---|
288 | */ |
---|
289 | static BonoboWidget * |
---|
290 | bonobo_widget_create_subdoc_object (BonoboWidget *bw, |
---|
291 | const char *moniker, |
---|
292 | Bonobo_UIContainer uic) |
---|
293 | { |
---|
294 | GtkWidget *view_widget; |
---|
295 | |
---|
296 | /* |
---|
297 | * Create the BonoboContainer. This will contain |
---|
298 | * just one BonoboClientSite. |
---|
299 | */ |
---|
300 | bw->priv->container = bonobo_item_container_new (); |
---|
301 | |
---|
302 | bw->priv->server = bonobo_widget_launch_component ( |
---|
303 | moniker, "IDL:Bonobo/Embeddable:1.0"); |
---|
304 | if (bw->priv->server == NULL) |
---|
305 | return NULL; |
---|
306 | |
---|
307 | /* |
---|
308 | * Create the client site. This is the container-side point |
---|
309 | * of contact for the remote component. |
---|
310 | */ |
---|
311 | bw->priv->client_site = bonobo_client_site_new (bw->priv->container); |
---|
312 | |
---|
313 | /* |
---|
314 | * Bind the local ClientSite object to the remote Embeddable |
---|
315 | * component. |
---|
316 | */ |
---|
317 | if (!bonobo_client_site_bind_embeddable (bw->priv->client_site, bw->priv->server)) |
---|
318 | return NULL; |
---|
319 | |
---|
320 | /* |
---|
321 | * Now create a new view for the remote object. |
---|
322 | */ |
---|
323 | bw->priv->view_frame = bonobo_client_site_new_view (bw->priv->client_site, uic); |
---|
324 | |
---|
325 | /* |
---|
326 | * Add the view frame. |
---|
327 | */ |
---|
328 | view_widget = bonobo_view_frame_get_wrapper (bw->priv->view_frame); |
---|
329 | gtk_container_add (GTK_CONTAINER (bw), view_widget); |
---|
330 | gtk_widget_show (view_widget); |
---|
331 | |
---|
332 | if (uic != CORBA_OBJECT_NIL) |
---|
333 | bw->priv->uic = bonobo_object_dup_ref (uic, NULL); |
---|
334 | |
---|
335 | return bw; |
---|
336 | } |
---|
337 | |
---|
338 | /** |
---|
339 | * bonobo_widget_new_subdoc: |
---|
340 | * @moniker: A moniker description of the Object to be activated. |
---|
341 | * @uic: Bonobo_UIContainer for the launched object. |
---|
342 | * |
---|
343 | * This function is a simple wrapper for easily embedding documents |
---|
344 | * into applications. It will launch the component identified by @id |
---|
345 | * and will return it as a GtkWidget. |
---|
346 | * |
---|
347 | * This will launch a single view of the embeddable activated by @moniker. |
---|
348 | * |
---|
349 | * FIXME: this function should really be using bonobo_get_object() instead |
---|
350 | * of bonobo_activate_object() to launch the object. |
---|
351 | * |
---|
352 | * Returns: A #GtkWidget that is bound to the Bonobo Control. |
---|
353 | */ |
---|
354 | GtkWidget * |
---|
355 | bonobo_widget_new_subdoc (const char *moniker, |
---|
356 | Bonobo_UIContainer uic) |
---|
357 | { |
---|
358 | BonoboWidget *bw; |
---|
359 | |
---|
360 | g_return_val_if_fail (moniker != NULL, NULL); |
---|
361 | |
---|
362 | bw = gtk_type_new (BONOBO_WIDGET_TYPE); |
---|
363 | |
---|
364 | if (bw == NULL) |
---|
365 | return NULL; |
---|
366 | |
---|
367 | if (!bonobo_widget_create_subdoc_object (bw, moniker, uic)) { |
---|
368 | gtk_object_destroy (GTK_OBJECT (bw)); |
---|
369 | return NULL; |
---|
370 | } |
---|
371 | |
---|
372 | bonobo_view_frame_set_covered (bw->priv->view_frame, FALSE); |
---|
373 | |
---|
374 | return GTK_WIDGET (bw); |
---|
375 | } |
---|
376 | |
---|
377 | /** |
---|
378 | * bonobo_widget_get_container |
---|
379 | * @bonobo_widget: the #BonoboWidget to query. |
---|
380 | * |
---|
381 | * This operation is only valid for BonoboWidgets that were created |
---|
382 | * by the bonobo_widget_new_subdoc(). |
---|
383 | * |
---|
384 | * Returns: the BonoboItemContainer associated with this @bonobo_widget |
---|
385 | */ |
---|
386 | BonoboItemContainer * |
---|
387 | bonobo_widget_get_container (BonoboWidget *bonobo_widget) |
---|
388 | { |
---|
389 | g_return_val_if_fail (bonobo_widget != NULL, NULL); |
---|
390 | g_return_val_if_fail (BONOBO_IS_WIDGET (bonobo_widget), NULL); |
---|
391 | |
---|
392 | return bonobo_widget->priv->container; |
---|
393 | } |
---|
394 | |
---|
395 | /** |
---|
396 | * bonobo_widget_get_client_site: |
---|
397 | * @bonobo_widget: the #BonoboWidget to query. |
---|
398 | * |
---|
399 | * This operation is only valid for BonoboWidgets that were created |
---|
400 | * by the bonobo_widget_new_subdoc(). |
---|
401 | * |
---|
402 | * Returns: the #BonoboClientSite associated with this @bonobo_widget |
---|
403 | */ |
---|
404 | BonoboClientSite * |
---|
405 | bonobo_widget_get_client_site (BonoboWidget *bonobo_widget) |
---|
406 | { |
---|
407 | g_return_val_if_fail (bonobo_widget != NULL, NULL); |
---|
408 | g_return_val_if_fail (BONOBO_IS_WIDGET (bonobo_widget), NULL); |
---|
409 | |
---|
410 | return bonobo_widget->priv->client_site; |
---|
411 | } |
---|
412 | |
---|
413 | /** |
---|
414 | * bonobo_widget_get_view_frame: |
---|
415 | * @bonobo_widget: the #BonoboWidget to query. |
---|
416 | * |
---|
417 | * This operation is only valid for BonoboWidgets that were created |
---|
418 | * by the bonobo_widget_new_subdoc(). |
---|
419 | * |
---|
420 | * Returns: The #BonoboViewFrame associated with this @bonobo_widget. |
---|
421 | */ |
---|
422 | BonoboViewFrame * |
---|
423 | bonobo_widget_get_view_frame (BonoboWidget *bonobo_widget) |
---|
424 | { |
---|
425 | g_return_val_if_fail (bonobo_widget != NULL, NULL); |
---|
426 | g_return_val_if_fail (BONOBO_IS_WIDGET (bonobo_widget), NULL); |
---|
427 | |
---|
428 | return bonobo_widget->priv->view_frame; |
---|
429 | } |
---|
430 | |
---|
431 | /** |
---|
432 | * bonobo_widget_get_uih: |
---|
433 | * @bonobo_widget: the #BonoboWidget to query. |
---|
434 | * |
---|
435 | * Returns: the CORBA object reference to the Bonobo_UIContainer |
---|
436 | * associated with the @bonobo_widget. |
---|
437 | */ |
---|
438 | Bonobo_UIContainer |
---|
439 | bonobo_widget_get_uih (BonoboWidget *bonobo_widget) |
---|
440 | { |
---|
441 | g_return_val_if_fail (bonobo_widget != NULL, NULL); |
---|
442 | g_return_val_if_fail (BONOBO_IS_WIDGET (bonobo_widget), NULL); |
---|
443 | |
---|
444 | return bonobo_widget->priv->uic; |
---|
445 | } |
---|
446 | |
---|
447 | |
---|
448 | |
---|
449 | /* |
---|
450 | * |
---|
451 | * Generic (non-control/subdoc specific) BonoboWidget stuff. |
---|
452 | * |
---|
453 | */ |
---|
454 | |
---|
455 | /** |
---|
456 | * bonobo_widget_get_server: |
---|
457 | * @bonobo_widget: the #BonoboWidget to query. |
---|
458 | * |
---|
459 | * Returns: The BonoboObjectClient (a wrapper for the CORBA object |
---|
460 | * reference) to the object that this BonoboWidget is wrapping. |
---|
461 | */ |
---|
462 | BonoboObjectClient * |
---|
463 | bonobo_widget_get_server (BonoboWidget *bonobo_widget) |
---|
464 | { |
---|
465 | g_return_val_if_fail (bonobo_widget != NULL, NULL); |
---|
466 | g_return_val_if_fail (BONOBO_IS_WIDGET (bonobo_widget), NULL); |
---|
467 | |
---|
468 | return bonobo_widget->priv->server; |
---|
469 | } |
---|
470 | |
---|
471 | Bonobo_Unknown |
---|
472 | bonobo_widget_get_objref (BonoboWidget *bonobo_widget) |
---|
473 | { |
---|
474 | g_return_val_if_fail (bonobo_widget != NULL, NULL); |
---|
475 | g_return_val_if_fail (BONOBO_IS_WIDGET (bonobo_widget), NULL); |
---|
476 | |
---|
477 | return BONOBO_OBJREF (bonobo_widget->priv->server); |
---|
478 | } |
---|
479 | |
---|
480 | static void |
---|
481 | bonobo_widget_destroy (GtkObject *object) |
---|
482 | { |
---|
483 | BonoboWidget *bw = BONOBO_WIDGET (object); |
---|
484 | BonoboWidgetPrivate *priv = bw->priv; |
---|
485 | |
---|
486 | if (priv->control_frame) |
---|
487 | bonobo_object_unref (BONOBO_OBJECT (priv->control_frame)); |
---|
488 | if (priv->container) |
---|
489 | bonobo_object_unref (BONOBO_OBJECT (priv->container)); |
---|
490 | if (priv->client_site) |
---|
491 | bonobo_object_unref (BONOBO_OBJECT (priv->client_site)); |
---|
492 | if (priv->view_frame) |
---|
493 | bonobo_object_unref (BONOBO_OBJECT (priv->view_frame)); |
---|
494 | if (priv->uic != CORBA_OBJECT_NIL) |
---|
495 | bonobo_object_release_unref (priv->uic, NULL); |
---|
496 | |
---|
497 | g_free (priv); |
---|
498 | GTK_OBJECT_CLASS (bonobo_widget_parent_class)->destroy (object); |
---|
499 | } |
---|
500 | |
---|
501 | static void |
---|
502 | bonobo_widget_size_request (GtkWidget *widget, |
---|
503 | GtkRequisition *requisition) |
---|
504 | { |
---|
505 | GtkBin *bin; |
---|
506 | |
---|
507 | g_return_if_fail (widget != NULL); |
---|
508 | g_return_if_fail (BONOBO_IS_WIDGET (widget)); |
---|
509 | g_return_if_fail (requisition != NULL); |
---|
510 | |
---|
511 | bin = GTK_BIN (widget); |
---|
512 | |
---|
513 | if (bin->child && GTK_WIDGET_VISIBLE (bin->child)) { |
---|
514 | GtkRequisition child_requisition; |
---|
515 | |
---|
516 | gtk_widget_size_request (bin->child, &child_requisition); |
---|
517 | |
---|
518 | requisition->width = child_requisition.width; |
---|
519 | requisition->height = child_requisition.height; |
---|
520 | } |
---|
521 | } |
---|
522 | |
---|
523 | static void |
---|
524 | bonobo_widget_size_allocate (GtkWidget *widget, |
---|
525 | GtkAllocation *allocation) |
---|
526 | { |
---|
527 | GtkBin *bin; |
---|
528 | GtkAllocation child_allocation; |
---|
529 | |
---|
530 | g_return_if_fail (widget != NULL); |
---|
531 | g_return_if_fail (BONOBO_IS_WIDGET (widget)); |
---|
532 | g_return_if_fail (allocation != NULL); |
---|
533 | |
---|
534 | widget->allocation = *allocation; |
---|
535 | bin = GTK_BIN (widget); |
---|
536 | |
---|
537 | child_allocation.x = allocation->x; |
---|
538 | child_allocation.y = allocation->y; |
---|
539 | child_allocation.width = allocation->width; |
---|
540 | child_allocation.height = allocation->height; |
---|
541 | |
---|
542 | if (bin->child) { |
---|
543 | gtk_widget_size_allocate (bin->child, &child_allocation); |
---|
544 | } |
---|
545 | } |
---|
546 | |
---|
547 | static void |
---|
548 | bonobo_widget_class_init (BonoboWidgetClass *klass) |
---|
549 | { |
---|
550 | GtkObjectClass *object_class = (GtkObjectClass *) klass; |
---|
551 | GtkWidgetClass *widget_class = (GtkWidgetClass *) klass; |
---|
552 | |
---|
553 | bonobo_widget_parent_class = gtk_type_class (GTK_TYPE_BIN); |
---|
554 | |
---|
555 | widget_class->size_request = bonobo_widget_size_request; |
---|
556 | widget_class->size_allocate = bonobo_widget_size_allocate; |
---|
557 | |
---|
558 | object_class->destroy = bonobo_widget_destroy; |
---|
559 | } |
---|
560 | |
---|
561 | static void |
---|
562 | bonobo_widget_init (BonoboWidget *bw) |
---|
563 | { |
---|
564 | bw->priv = g_new0 (BonoboWidgetPrivate, 1); |
---|
565 | } |
---|
566 | |
---|
567 | GtkType |
---|
568 | bonobo_widget_get_type (void) |
---|
569 | { |
---|
570 | static GtkType type = 0; |
---|
571 | |
---|
572 | if (! type) { |
---|
573 | static const GtkTypeInfo info = { |
---|
574 | "BonoboWidget", |
---|
575 | sizeof (BonoboWidget), |
---|
576 | sizeof (BonoboWidgetClass), |
---|
577 | (GtkClassInitFunc) bonobo_widget_class_init, |
---|
578 | (GtkObjectInitFunc) bonobo_widget_init, |
---|
579 | NULL, /* reserved_1 */ |
---|
580 | NULL, /* reserved_2 */ |
---|
581 | (GtkClassInitFunc) NULL |
---|
582 | }; |
---|
583 | |
---|
584 | type = gtk_type_unique (gtk_bin_get_type (), &info); |
---|
585 | } |
---|
586 | |
---|
587 | return type; |
---|
588 | } |
---|
589 | |
---|
590 | /** |
---|
591 | * bonobo_widget_set_property: |
---|
592 | * @control: A #BonoboWidget that represents an IDL:Bonobo/Control:1.0 |
---|
593 | * @first_prop: first property name to set. |
---|
594 | * |
---|
595 | * This is a utility function used to set a number of properties |
---|
596 | * in the Bonobo Control in @control. |
---|
597 | * |
---|
598 | * This function takes a variable list of arguments that must be NULL |
---|
599 | * terminated. Arguments come in tuples: a string (for the argument |
---|
600 | * name) and the data type that is to be transfered. The |
---|
601 | * implementation of the actual setting of the PropertyBag values is |
---|
602 | * done by the bonobo_property_bag_client_setv() function). |
---|
603 | * |
---|
604 | * FIXME: This function is error prone because it depends on the |
---|
605 | * client and the server to agree on the data types to be sent. If |
---|
606 | * the server arguments change the data type, this routine will not |
---|
607 | * be able to cope gracefully with this condition. |
---|
608 | * |
---|
609 | * This only works for BonoboWidgets that represent controls (ie, |
---|
610 | * that were returned by bonobo_widget_new_control_from_objref() or |
---|
611 | * bonobo_widget_new_control(). |
---|
612 | */ |
---|
613 | void |
---|
614 | bonobo_widget_set_property (BonoboWidget *control, |
---|
615 | const char *first_prop, ...) |
---|
616 | { |
---|
617 | Bonobo_PropertyBag pb; |
---|
618 | CORBA_Environment ev; |
---|
619 | |
---|
620 | va_list args; |
---|
621 | va_start (args, first_prop); |
---|
622 | |
---|
623 | g_return_if_fail (control != NULL); |
---|
624 | g_return_if_fail (first_prop != NULL); |
---|
625 | g_return_if_fail (control->priv != NULL); |
---|
626 | g_return_if_fail (BONOBO_IS_WIDGET (control)); |
---|
627 | |
---|
628 | CORBA_exception_init (&ev); |
---|
629 | |
---|
630 | pb = bonobo_control_frame_get_control_property_bag ( |
---|
631 | control->priv->control_frame, &ev); |
---|
632 | |
---|
633 | if (BONOBO_EX (&ev)) |
---|
634 | g_warning ("Error getting property bag from control"); |
---|
635 | else { |
---|
636 | /* FIXME: this should use ev */ |
---|
637 | char *err = bonobo_property_bag_client_setv (pb, &ev, first_prop, args); |
---|
638 | |
---|
639 | if (err) |
---|
640 | g_warning ("Error '%s'", err); |
---|
641 | } |
---|
642 | |
---|
643 | bonobo_object_release_unref (pb, &ev); |
---|
644 | |
---|
645 | CORBA_exception_free (&ev); |
---|
646 | |
---|
647 | va_end (args); |
---|
648 | } |
---|
649 | |
---|
650 | |
---|
651 | /** |
---|
652 | * bonobo_widget_get_property: |
---|
653 | * @control: A #BonoboWidget that represents an IDL:Bonobo/Control:1.0 |
---|
654 | * @first_prop: first property name to set. |
---|
655 | * |
---|
656 | * This is a utility function used to get a number of properties |
---|
657 | * in the Bonobo Control in @control. |
---|
658 | * |
---|
659 | * This function takes a variable list of arguments that must be NULL |
---|
660 | * terminated. Arguments come in tuples: a string (for the argument |
---|
661 | * name) and a pointer where the data will be stored. The |
---|
662 | * implementation of the actual setting of the PropertyBag values is |
---|
663 | * done by the bonobo_property_bag_client_setv() function). |
---|
664 | * |
---|
665 | * FIXME: This function is error prone because it depends on the |
---|
666 | * client and the server to agree on the data types to be sent. If |
---|
667 | * the server arguments change the data type, this routine will not |
---|
668 | * be able to cope gracefully with this condition. |
---|
669 | * |
---|
670 | * This only works for BonoboWidgets that represent controls (ie, |
---|
671 | * that were returned by bonobo_widget_new_control_from_objref() or |
---|
672 | * bonobo_widget_new_control(). |
---|
673 | */ |
---|
674 | void |
---|
675 | bonobo_widget_get_property (BonoboWidget *control, |
---|
676 | const char *first_prop, ...) |
---|
677 | { |
---|
678 | Bonobo_PropertyBag pb; |
---|
679 | CORBA_Environment ev; |
---|
680 | |
---|
681 | va_list args; |
---|
682 | va_start (args, first_prop); |
---|
683 | |
---|
684 | g_return_if_fail (control != NULL); |
---|
685 | g_return_if_fail (first_prop != NULL); |
---|
686 | g_return_if_fail (control->priv != NULL); |
---|
687 | g_return_if_fail (BONOBO_IS_WIDGET (control)); |
---|
688 | |
---|
689 | CORBA_exception_init (&ev); |
---|
690 | |
---|
691 | pb = bonobo_control_frame_get_control_property_bag ( |
---|
692 | control->priv->control_frame, &ev); |
---|
693 | |
---|
694 | if (BONOBO_EX (&ev)) |
---|
695 | g_warning ("Error getting property bag from control"); |
---|
696 | else { |
---|
697 | /* FIXME: this should use ev */ |
---|
698 | char *err = bonobo_property_bag_client_getv (pb, &ev, first_prop, args); |
---|
699 | |
---|
700 | if (err) |
---|
701 | g_warning ("Error '%s'", err); |
---|
702 | } |
---|
703 | |
---|
704 | bonobo_object_release_unref (pb, &ev); |
---|
705 | |
---|
706 | CORBA_exception_free (&ev); |
---|
707 | |
---|
708 | va_end (args); |
---|
709 | } |
---|