24c6253fd73cf99d5023379d3c6cba5cb77195a1
[pkgs/u/ui-gadget.git] / include / SLP_UI_Gadget_PG.h
1 /*
2  * Copyright (c) 2000 - 2012 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  * This file is part of the UI Gadget
5  * Written by Jayoun Lee <airjany@samsung.com>, Jinwoo Nam <jwoo.nam@samsung.com>
6  *
7  * PROPRIETARY/CONFIDENTIAL
8  *
9  * This software is the confidential and proprietary information of
10  * SAMSUNG ELECTRONICS (Confidential Information).
11  * You shall not disclose such Confidential Information and shall
12  * use it only in accordance with the terms of the license agreement
13  * you entered into with SAMSUNG ELECTRONICS.  SAMSUNG make no
14  * representations or warranties about the suitability
15  * of the software, either express or implied, including but not
16  * limited to the implied warranties of merchantability, fitness for a particular purpose, or non-
17  * infringement. SAMSUNG shall not be liable for any damages suffered by licensee as
18  * a result of using, modifying or distributing this software or its derivatives.
19  *
20  */
21
22 /**
23  *
24  * @ingroup SLP_PG
25  * @defgroup SLP_PG_UI_GADGET UI gadget library
26  * @{
27
28 <h1 class="pg">Introduction</h1>
29 <h2 class="pg">Purpose of this document</h2>
30 The purpose of this document is to describe how to develop/use UI gadget. This document gives programming guidelines to UI gadget devlopers and users.
31 <h2 class="pg">Scope</h2>
32 The scope of this document is limited to UI gadget component interface and API usage.
33
34 <h1 class="pg">UI gadget architecture</h1>
35 <h2 class="pg">UI gadget</h2>
36 An UI gadget is a visual component providing views (or features) of other applications, e.g., phonebook, myfile. Because UI gadgets are supposed to deliver most commonly used features that the platform can natively support, developers can avoid unnecessary massive code writing using UI gadgets. Hence an UI gadget eventually includes logics to handle simple request. UI gadget is able to be managed by UI gadget library.
37 \image html SLP_UI_Gadget_PG_image00.png "Picture 1. UI gadget architecture diagram"
38
39 <h2 class="pg">UI gadget features</h2>
40 UI Gadget Library has the following features:
41 - It provides component interfaces for UI Gadget
42 - It manages UI gadget instances in an application according to their lifecycle
43
44 <h2 class="pg">Lifecycle</h2>
45 Essentially, an UI gadget has following five states (See Picture 2)
46 - The initial state is \b Ready
47 - If an UI gadget has been created, it is \b Created
48 - If an UI gadget has been started, it is \b Running
49 - If the application that is using an UI gadget is put into background, it is \b Stopped
50 - If an UI gadget has been destroyed, it is \b Destroyed
51
52 An UI gadget has five callback methods that you can implement to perform operations when the UI gadget moves between states
53 - When an UI gadget is created, \b create() is invoked
54 - When an UI gadget is started, \b start() is invoked
55 - When the application that is using an UI gadget is put into background, \b pause() is invoked
56 - When the application that is using an UI gadget is brought to the foreground, \b resume() is invoked.
57 - When an UI gadget is destroyed, \b destroy() is invoked
58
59 In addition, an UI gadget has callback methods for system events and message:
60 - When an system event is generated, event() is invoked
61 - When an UI gadget receives message from the caller, message() is invoked
62
63 \image html SLP_UI_Gadget_PG_image01.png "Picture 2. UI gadget state diagram"
64
65 <h2 class="pg">Management</h2>
66 UI gadgets in an application are managed as a TREE structure (See Picture 3.) The features for the tree are:
67 - Root of the tree is the UI gadget manager
68 - UI gadget caller is parent of callees
69 - Parents arrange the layout of their children
70
71 Every application which is using UI gadgets has one UI gadget manager as a root of the tree. And the UI gadget manager propagates system events and task management events by post-order traversal. Available system events are <i>low memory, low battery, language changed, and window rotate event</i>. And task management events are <i>pause and resume</i>.
72
73 \image html SLP_UI_Gadget_PG_image02.png "Picture 3. UI gadget management policy"
74
75 <h1 class="pg">Getting started</h1>
76 <h2 class="pg">How to make UI gadget</h2>
77 In this section, we are going to write your first UI gadget called "helloUG-efl". Before we get started, make sure you have read the overview, especially, lifecycle section. We will mainly deal with the operations of lifecycle.
78
79 \note <b>Sample codes</b> are included in the UI gadget source package. The samples for UI gadget developers are located in "/test/ug/", and the samples for UI gadget users are in "/test/app/." For instance, "helloUG-efl" codes are in "/test/ug/helloUG-efl/."
80 \note <b>Naming rule:</b> The name of UI gadget must be "{NAME}-{UI LIB NAME}", e.g., "helloUG-efl"
81
82 <br>
83 <h3 class="pg">UI gadget template</h3>
84 To create an UI gadget, start by generating boilerplate code using UI gadget template as follow:
85 @verbatim
86 # ug-gen.sh helloUG-efl helloUG-efl EFL
87 @endverbatim
88
89 \note <b>How to install UI gadget template:</b>
90 @verbatim
91 # apt-get install ui-gadget-template
92 @endverbatim
93
94 \note <b>How to use UI gadget template:</b>
95 @verbatim
96 # ug-gen.sh [destination] [name] [UI library]
97 @endverbatim
98 - destination: destination directory
99 - name: UI gadget name
100 - UI library: UI library to use. Only EFL is available for now
101
102 After you generate code, you get following files:
103 - <i>helloUG-efl.c</i>  (Source)
104 - <i>helloUG-efl.h</i>  (Private header)
105 - <i>CMakeList.txt</i>  (Build script)
106 - <i>po/*</i>           (I18N files)
107
108 <i>helloUG-efl.c</i> contains base code, and the most important parts are <i>UG_MODULE_INIT</i> and <i>UG_MODULE_EXIT</i> which are symbols to export for dynamic linking. <i>UG_MODULE_INIT</i> is invoked when the UI gadget is loading, and it sets operations, private data, and the option. <i>UG_MODULE_EXIT</i> is invoked when the UI gadget is unloading, and it clears private data.<br><br>
109 Even if you don't understand generated code right now, don't worry about it. What you have to do is just implementation of operations according to their role (see next section.)
110 @code
111 // in helloUG-efl.c
112 UG_MODULE_API int UG_MODULE_INIT(struct ug_module_ops *ops)
113 {
114         struct ug_data *ugd;            // User defined private data
115
116         if (!ops)
117                 return -1;
118
119         ugd = calloc(1, sizeof(struct ug_data));
120         if (!ugd)
121                 return -1;
122
123         // create operation
124         ops->create = on_create;
125         // start operation
126         ops->start = on_start;
127         // pause operation
128         ops->pause = on_pause;
129         // resume operation
130         ops->resume = on_resume;
131         // destroy operation
132         ops->destroy = on_destroy;
133         // message operation
134         ops-> message = on_message;
135         // event operation
136         ops->event = on_event;
137         // private data
138         ops->priv = ugd;
139         // option
140         ops->opt = UG_OPT_INDICATOR_ENABLE;
141
142         return 0;
143 }
144
145 UG_MODULE_API void UG_MODULE_EXIT(struct ug_module_ops *ops)
146 {
147         struct ug_data *ugd;
148
149         if (!ops)
150                 return;
151
152         ugd = ops->priv;
153         if (ugd)
154                 free(ugd);              // clear private data
155 }
156
157 @endcode
158
159 \note <b>struct ug_module_ops</b> is a data structure describing operations, private data, and the option of UI gadget:
160 @code
161 struct ug_module_ops {
162         void *(*create)(struct ui_gadget *ug, enum ug_mode mode, bundle *data, void *priv);
163         void (*start)(struct ui_gadget *ug, bundle *data, void *priv);
164         void (*pause)(struct ui_gadget *ug, bundle *data, void *priv);
165         void (*resume)(struct ui_gadget *ug, bundle *data, void *priv);
166         void (*destroy)(struct ui_gadget *ug, bundle *data, void *priv);
167         void (*message)(struct ui_gadget *ug, bundle *msg, bundle *data, void *priv);
168         void (*event)(struct ui_gadget *ug, enum ug_event event, bundle *data, void *priv);
169         void *reserved[5];
170         void *priv;
171         enum ug_option opt;
172 };
173 @endcode
174
175 \note <b>enum ug_option</b> is UI gadget options, available options are:
176 @code
177 // Enable indicator
178 UG_OPT_INDICATOR_ENABLE
179 // Enable indicator with portrait window
180 UG_OPT_INDICATOR_PORTRAIT_ONLY
181 // Enable indicator with landscape window
182 UG_OPT_INDICATOR_LANDSCAPE_ONLY
183 // Disable indicator
184 UG_OPT_INDICATOR_DISABLE
185 @endcode
186
187 \note <b>struct ug_data</b> is a user defined private data structure describing base layout, own UI gadget handler, and whatever you need:
188 @code
189 struct ug_data {
190         Evas_Object *base;
191         struct ui_gadget *ug;
192
193         // PUT WHATEVER YOU NEED
194 }
195 @endcode
196
197 <br>
198 <h3 class="pg">Operations</h3>
199 There are five state operations, a message operation, and an event operation: <i>create, start, pause, resume, destroy, message, and event.</i>
200 <br><br>
201 When "helloUG-efl" is created, the create operation is invoked. The implementation of create operation is <b>on_create()</b>. Basically, in the operation, we have to make a base layout and return it. Hence, we made base layout using <i>"window layout winset."</i> In case of fullview, we let indicator area be shown, otherwise, we don't (see <i>create_fullview()</i> and <i>create_frameview()</i>.) In addition, in the base layout, we put a box including a label and two buttons (see <i>create_content()</i>.) The label is labeled "Hello UI Gadget." And the first button, labeled "Send result", is for sending result to the "helloUG-efl" caller. The other button, labeled "Back", is for sending destroy request to the caller. For more information about two buttons, please see <i>Send results and request to destroy section</i>.
202
203 \note <b>Arguments:</b> All operations receive bundle type data which is named <i>data</i> (see \ref bundle_PG "bundle programming guide") And the argument <i>data</i> is automatically released by UI gadget manager after the UI gadget is destroyed.
204
205 @code
206 // in helloUG-efl.c
207 static void *on_create(struct ui_gadget *ug, enum ug_mode mode, bundle *data, void *priv)
208 {
209         Evas_Object *parent;
210         Evas_Object *content;
211         struct ug_data *ugd;
212
213         if (!ug || !priv)
214                 return NULL;
215
216         ugd = priv;
217         ugd->ug = ug;
218
219         parent = ug_get_parent_layout(ug);
220         if (!parent)
221                 return NULL;
222
223         if (mode == UG_MODE_FULLVIEW)
224                 ugd->base = create_fullview(parent, ugd);
225         else
226                 ugd->base = create_frameview(parent, ugd);
227
228         if (ugd->base) {
229                 content = create_content(parent, ugd);
230                 elm_layout_content_set(ugd->base, "elm.swallow.content", content);
231         }
232         return ugd->base;
233 }
234
235 static Evas_Object *create_fullview(Evas_Object *parent, struct ug_data *ugd)
236 {
237         Evas_Object *base;
238
239         base = elm_layout_add(parent);
240         if (!base)
241                 return NULL;
242
243         elm_layout_theme_set(base, "standard", "window", "integration");
244         // In case of fullview, show indicator area
245         edje_object_signal_emit(_EDJ(base), "elm,state,show,indicator", "elm");
246         edje_object_signal_emit(_EDJ(base), "elm,state,show,content", "elm");
247
248         return base;
249 }
250
251 static Evas_Object *create_frameview(Evas_Object *parent, struct ug_data *ugd)
252 {
253         Evas_Object *base;
254
255         base = elm_layout_add(parent);
256         if (!base)
257                 return NULL;
258
259         // In case of frameview, do not show indicator area
260
261         elm_layout_theme_set(base, "standard", "window", "integration");
262         edje_object_signal_emit(_EDJ(base), "elm,state,show,content", "elm");
263
264         return base;
265 }
266
267 static Evas_Object *create_content(Evas_Object *parent, struct ug_data *ugd)
268 {
269         Evas_Object *bx, *eo;
270
271         // add box
272         bx = elm_box_add(parent);
273
274         // add label and pack it in the box
275         eo = elm_label_add(parent);
276         elm_label_label_set(eo, _("Hello UI Gadget"));
277         evas_object_size_hint_align_set(eo, 0.5, EVAS_HINT_FILL);
278         evas_object_size_hint_weight_set(eo, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
279         evas_object_show(eo);
280         elm_box_pack_end(bx, eo);
281
282         // add buttons and pack it in the box
283         eo = elm_button_add(parent);
284         elm_button_label_set(eo, _("Send result"));
285         evas_object_size_hint_align_set(eo, EVAS_HINT_FILL, EVAS_HINT_FILL);
286         evas_object_smart_callback_add(eo, "clicked", result_cb, ugd);
287         elm_object_style_set(eo, "bottom_btn");
288
289         evas_object_show(eo);
290         elm_box_pack_end(bx, eo);
291
292         eo = elm_button_add(parent);
293         elm_button_label_set(eo, _("Back"));
294         evas_object_size_hint_align_set(eo, EVAS_HINT_FILL, EVAS_HINT_FILL);
295         evas_object_smart_callback_add(eo, "clicked", back_cb, ugd);
296         elm_object_style_set(eo, "bottom_btn");
297
298         evas_object_show(eo);
299         elm_box_pack_end(bx, eo);
300         return bx;
301 }
302
303 @endcode
304
305 When "helloUG-efl" starts, the start operation is invoked. The implementation of start operation is <b>on_start()</b>. In this operation, we do nothing:
306
307 @code
308 // in helloUG-efl.c
309 static void on_start(struct ui_gadget *ug, bundle *data, void *priv)
310 {
311
312 }
313 @endcode
314
315 When "helloUG-efl" is destroyed, the destroy operation is invoked. The implementation of destroy operation is <b>on_destroy()</b>. In the method, we delete base layout:
316
317 @code
318 // in helloUG-efl.c
319 static void on_destroy(struct ui_gadget *ug, bundle *data, void *priv)
320 {
321         struct ug_data *ugd;
322
323         if (!ug || !priv)
324                 return;
325
326         ugd = priv;
327
328         evas_object_del(ugd->base);
329         ugd->base = NULL;
330 }
331 @endcode
332
333 When the application using "helloUG-efl" is put into background, the pause operation is invoked. When the application is brought to the foreground, the resume operation is invoked. Besides, when an UI gadget receives message from its caller, the message operation is invoked. And when a system event is generated, the event operation is invoked. The implementation of pause, resume, message, and event operations are <b>on_pause(), on_resume(), on_message(), and on_event()</b>. In these operations, we do nothing:
334
335 @code
336 // in helloUG-efl.c
337 static void on_pause(struct ui_gadget *ug, bundle *data, void *priv)
338 {
339 }
340 static void on_resume(struct ui_gadget *ug, bundle *data, void *priv)
341 {
342 }
343
344 static void on_message(struct ui_gadget *ug, bundle *msg, bundle *data, void *priv)
345 {
346 }
347
348 static void on_event(struct ui_gadget *ug, enum ug_event event, bundle *data, void *priv)
349 {
350         switch (event) {
351                 case UG_EVENT_LOW_MEMORY:
352                         break;
353                 case UG_EVENT_LOW_BATTERY:
354                         break;
355                 case UG_EVENT_LANG_CHANGE:
356                         break;
357                 case UG_EVENT_ROTATE_PORTRAIT:
358                         break;
359                 case UG_EVENT_ROTATE_PORTRAIT_UPSIDEDOWN:
360                         break;
361                 case UG_EVENT_ROTATE_LANDSCAPE:
362                         break;
363                 case UG_EVENT_ROTATE_LANDSCAPE_UPSIDEDOWN:
364                         break;
365                 default:
366                         break;
367         }
368 }
369 @endcode
370
371 \warning Message data of message operation is bundle type data, named <i>msg.</i> <b>Because the message data is released after message operation is finished,</b> if you want to keep using it, please use <b>bundle_dup()</b> which duplicates given bundle data (see \ref bundle_PG "bundle programming guide")
372
373 <br>
374 <h3 class="pg">Send results and request to destroy</h3>
375 Usually, an UI gadget needs to send results or destroy request to the UI gadget caller. To send result, use <b>ug_send_result()</b>, and to send the destroy request, use <b>ug_destroy_me().</b>
376 <br>
377 We use bundle library for composing result data. The bundle provides us a few APIs to make a list of dictionary data that consists of key and value. (ex. {"name"  "John Doe"}) To get more information of bundle, please see \ref bundle_PG "bundle programming guide".
378
379 \warning After send your result data, you have to release it using <b>bundle_free()</b> API.
380
381 In our "helloUG-efl", we made two buttons for sending results and destroy request as below:
382 @code
383 // in helloUG-efl.c
384
385 //Include to use bundle APIs
386 #include <bundle.h>
387
388 static void result_cb(void *data, Evas_Object *obj, void *event_info)
389 {
390         bundle *b;
391         struct ug_data *ugd;
392
393         if (!data)
394                 return;
395
396         ugd = data;
397         b = bundle_create();
398         if (!b)
399                 return;
400
401         bundle_add(b, "name", "helloUG-efl");
402         bundle_add(b, "description", "sample UI gadget");
403         //Send result
404         ug_send_result(ugd->ug, b);
405
406         //release bundle
407         bundle_free(b);
408 }
409
410 static void back_cb(void *data, Evas_Object *obj, void *event_info)
411 {
412         struct ug_data *ugd;
413
414         if (!data)
415                 return;
416         ugd = data;
417
418         //Send destroy request
419         ug_destroy_me(ugd->ug);
420 }
421 @endcode
422
423 \note <b>To use bundle</b>
424 - Install libbundle-dev package
425 - Modify CMakeFile.txt to use bundle package as follow:
426 @code
427         â€¦
428                 pkg_check_modules(pkgs REQUIRED elementary ui-gadget-efl bundle)
429         â€¦
430 @endcode
431
432 <br>
433 <h3 class="pg">Internationalization</h3>
434 Basically, we use <b><i>dgettext</i></b> for translating a text string into the user's native language because each UI gadget uses different textdomain. Fortunately, if you generate your code using UI gadget template, you don't need to worry about <i>dgettext</i> and textdomain because a few macros are kindly provided by template. In helloUG-efl.h, which is a generated private header of "helloUG-efl", there are a few macros for convenience:
435 @code
436 // in helloUG-efl.h
437 #define PKGNAME                 "ug-helloUG-efl"
438 #define _(s)                    dgettext(PKGNAME, s)
439 #define dgettext_noop(s)        (s)
440 #define N_(s)                   dgettext_noop(s)
441 @endcode
442
443 The PKGNAME is textdomain of "helloUG-efl", and _() is a dgettext wrapper, and N_() is dummy macro. In addition, _() and N_() are additional keywords for marking translatable string for xgettext. Especially, N_() is a dummy keyword for special case as follow:
444 @code
445 static const char *message[] = {
446         N_("translatable string"),
447 };
448 @endcode
449
450 For more information, please see <a href="http://www.gnu.org/software/gettext/manual/gettext.html">GNU gettext utilities</a>.
451
452 \note <b>xgettext</b> extracts gettext strings from given input files. The canonical keyword for marking translatable strings is 'gettext'. For convenience, many packages use '_' as a keyword instead of 'gettext', and write '_("translatable string")' instead of 'gettext("translatable string")'.
453
454 <br>
455 <h3 class="pg">Rotation and indicator</h3>
456 When the UI gadget is created as fullview, we have to consider whether the indicator is shown or not. For instance, "Image viewer" shows the indicator on the portrait mode but not on the landscape mode. Hence, we provided option field named <i>opt</i> of <i>struct ug_module_ops</i> in UG_MODULE_INIT.
457 Available options are as following:
458 - UG_OPT_INDICATOR_ENABLE (default)
459 - UG_OPT_INDICATOR_POTRAIT_ONLY
460 - UG_OPT_LANDSCAPE_ONLY
461 - UG_OPT_INDICATOR_DISABLE
462
463 And we used UG_OPT_INDICATOR_ENABLE in "helloUG-efl"
464
465 <br>
466 <h3 class="pg">Build and test</h3>
467 Before you build, you have to make sure whether translatable strings exist or not. IF translatable strings EXIST, please follow these steps before you build:
468 @verbatim
469 # cd po
470 # ./update-po.sh
471 # cd ..
472 @endverbatim
473 IF NOT, please remove the following line in your CMakeList.txt
474 @verbatim
475 ADD_SUBDIRECTORY(po)
476 @endverbatim
477
478 To build "helloUG-efl", follow these steps:
479 @verbatim
480 # mkdir build
481 # cd build
482 # cmake -DCMAKE_INSTALL_PREFIX=/usr ..
483 # make
484 # make install
485 @endverbatim
486
487 \note <b>Naming rule:</b> The output library name is <b>"libug-helloUG-efl.so"</b>, and we use <b>"helloUG-efl"</b> as UI gadget name except prefix <b>"libug-"</b> and postfix ".so" In other word, when you make an UI gadget, the name of library MUST be <b>"libug-XXXXXX.so"</b>
488 \note <b>Installation directory:</b> UI gadgets MUST be installed in "${PREFIX}/lib/ug/"
489
490 Finally, we made our first UI gadget, "helloUG-efl." Let's test it using <i>ug-launcher</i> which is simple UI gadget launcher. Because we are using beat style buttons in our UI gadget, we specify "beat" as ELM_THEME.
491 Fullview test
492 @verbatim
493 # ELM_THEME=beat ug-launcher -n helloUG-efl
494 @endverbatim
495 Frameview test
496 @verbatim
497 # ELM_THEME=beat ug-launcher -n helloUG-efl -f
498 @endverbatim
499
500 \note <b>How to install UG launcher</b>
501 @verbatim
502 # apt-get install ui-gadget-tools
503 @endverbatim
504 \note <b>How to use UG launcher</b>
505 @verbatim
506 # ug-launcher [-F] [-f] -n <UG_NAME> [-d <Argument>]
507 @endverbatim
508 - -d: argument, key, value pair.
509 - -F: Fullview mode (default)
510 - -f: frameview mode
511 \note <b> Example: </b>
512 @verbatim
513 # ug-launcher -F -n helloUG-efl -d "name,John doe" -d "age,30"
514 @endverbatim
515
516 \image html SLP_UI_Gadget_PG_image03.png "Picture 3. helloUG-efl test: Fullview (left) and Frameview (right)
517
518 <br>
519 <h2 class="pg">How to use UI gadget</h2>
520 Now, we are going to use "helloUG-efl" of previous section.
521
522 <br>
523 <h3 class="pg">Initialize</h3>
524
525 If you are UI gadget developer who is trying to use UI gadgets, please skip this section. This section is for application developers who use UI gadgets.
526 You have to initialize UI gadget manager before you use UI gadgets. To initialize, use <b>ug_init()</b> with arguments: <i>disp, xid, win and opt</i>. <i>disp</i> is default display, and <i>xid</i> is X window id of win. <i>win</i> is window evas object for UI gadgets, and it is usually main window. <i>opti</i> is rotation and indicator option for your application (see <i>Rotation and indicator section</i>.)
527
528 The <i>disp</i> and <i>xid</i> are used for indicator management. If you don't know how to get display and X window ID, just use following macro: <b>UG_INIT_EFL(win, opt);</b>
529
530 \note <b>Prototype of ug_init():</b>
531 @code
532 int ug_init (Display *disp, Window xid, void *win, enum ug_option opt);
533 @endcode
534 \note <b>Macros for convenience (see 3 API reference quide):</b>
535 @code
536 UG_INIT_EFL(win, opt);
537 @endcode
538
539 <br>
540 <h3 class="pg">Create UI gadget instance</h3>
541
542 To create UI gadget instance, you have to invoke <b>ug_create()</b> which has five arguments: <i>parent, name, mode, data, and cbs.</i>
543
544 First, the <i>parent</i> is provided for specifying parent UI gadget, and it helps UI gadget manager to manage UI gadget tree (see <i>Management section.</i>) For instance, if the UI gadget 'A' uses other UI gadgets,  the parent has to be the 'A.' Otherwise, if an application uses UI gadgets, the <i>parent</i> has to be NULL.
545
546 Second, the <i>name</i> is the UI gadget's name (ex. "helloUG-efl")
547
548 Third, the <i>mode</i> could be UG_MODE_FULLVIEW to show the UI gadget as fullview, or UG_MODE_FRAMEVIEW to show it as frameview.
549
550 Fourth, the <i>data</i> is arguments for the UI gadget which is bundle type (see \ref bundle_PG "bundle programming guide")
551
552 \warning After create UI gadget, you have to release the argument using <b>bundle_free()</b> API.
553
554 Fifth, the <i>cbs</i> is data describing layout callback, result callback, destroy callback, and private data. In detail, layout callback is used for layout arrangement, and it invoked after the UI gadget is created, and result callback is invoked to receive result from the UI gadget. And destroy callback is invoked to deal with destroy request from the UI gadget.
555
556 \warning Result data of the result callback is bundle type data, named <i>result</i>. <b>Because the result data is released after result callback is finished</b>, if you want to keep using it, please use <b>bundle_dup()</b> which duplicates given bundle data (see \ref bundle_PG "bundle programming guide")
557
558 \note <b>Prototype of ug_create():</b>
559 @code
560 struct ui_gadget *ug_create (struct ui_gadget *parent,
561                         const char *name,
562                         enum ug_mode mode,
563                         bundle *data,
564                         struct ug_cbs *cbs);
565
566 \note <b>struct ug_cbs</b> is describing some callbacks and private data:
567 @code
568 struct ug_cbs {
569         void (*layout_cb)(struct ui_gadget *ug, enum ug_mode mode, void *priv);
570         void (*result_cb)(struct ui_gadget *ug, bundle *result, void *priv);
571         void (*destroy_cb)(struct ui_gadget *ug, void *priv);
572         void *priv;
573 };
574 @endcode
575
576 Here are some examples:
577
578 @code
579 // FULLVIEW example
580 struct my_data {
581         struct ui_gadget *ug;
582 };
583
584 static void layout_cb(struct ui_gadget *ug, enum ug_mode mode, void *priv)
585 {
586         Evas_Object *base, *win;
587
588         if (!ug || !priv)
589                 return;
590
591         base = ug_get_layout(ug);
592         if (!base)
593                 return;
594
595         win = ug_get_window();
596
597         switch (mode) {
598                 case UG_MODE_FULLVIEW:
599                         evas_object_size_hint_weight_set(base, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
600                         elm_win_resize_object_add(win, base);
601                         evas_object_show(base);
602                         break;
603                 default:
604                         break;
605         }
606 }
607
608 static void result_cb(struct ui_gadget *ug, bundle *result, void *priv)
609 {
610         struct my_data *mydata;
611         const char *val;
612
613         if (!ug || !priv)
614                 return;
615
616         mydata = priv;
617         if (result) {
618                 val = bundle_get_val(result, "name");
619                 if (val)
620                         fprintf(stderr, "The name of UI gadget that sends result is %s\n", val);
621         }
622         ug_destroy(ug);
623         mydata->ug = NULL;
624
625 }
626
627 static void destroy_cb(struct ui_gadget *ug, void *priv)
628 {
629         struct my_data *mydata;
630
631         if (!ug || !priv)
632                 return;
633
634         mydata = priv;
635
636         ug_destroy(ug);
637         mydata->ug = NULL;
638 }
639
640 struct ui_gadget *create_ug(struct my_data *data)
641 {
642         struct ui_gadget *ug;
643         struct ug_cbs cbs = {0, };
644
645         cbs.layout_cb = layout_cb;
646         cbs.result_cb = result_cb;
647         cbs.destroy_cb = destroy_cb;
648         cbs.priv = (void *)data;
649
650         ug = ug_create(NULL, "helloUG-efl", UG_MODE_FULLVIEW, NULL, &cbs);
651
652         return ug;
653 }
654 @endcode
655
656 @code
657 // FRAMEVIEW example
658 struct my_data {
659         struct ui_gadget *ug;
660         Evas_Object *main_layout;
661 };
662
663 static void layout_cb(struct ui_gadget *ug, enum ug_mode mode, void *priv)
664 {
665         Evas_Object *base, *win;
666         struct my_data *mydata;
667
668         if (!ug || !priv)
669                 return;
670
671         mydata = priv;
672
673         base = ug_get_layout(ug);
674         if (!base)
675                 return;
676
677         win = ug_get_window();
678
679         switch (mode) {
680                 case UG_MODE_FRAMEVIEW:
681                         elm_layout_content_set(mydata->main_layout, "content", base);
682                         break;
683                 default:
684                         break;
685         }
686 }
687
688 static void result_cb(struct ui_gadget *ug, bundle *result, void *priv)
689 {
690         struct my_data *mydata;
691         const char *val;
692
693         if (!ug || !priv)
694                 return;
695
696         mydata = priv;
697
698         if (result) {
699                 val = bundle_get_val(result, "name");
700                 if (val)
701                         fprintf(stderr, "The name of UI gadget that sends result is %s\n", val);
702         }
703
704         ug_destroy(ug);
705         mydata->ug = NULL;
706
707 }
708
709 static void destroy_cb(struct ui_gadget *ug, void *priv)
710 {
711         struct my_data *mydata;
712
713         if (!ug || !priv)
714                 return;
715
716         mydata = priv;
717
718         ug_destroy(ug);
719         mydata->ug = NULL;
720 }
721
722 struct ui_gadget *create_ug(struct my_data *data)
723 {
724         struct ui_gadget *ug;
725         struct ug_cbs cbs = {0, };
726
727         cbs.layout_cb = layout_cb;
728         cbs.result_cb = result_cb;
729         cbs.destroy_cb = destroy_cb;
730         cbs.priv = (void *)data;
731
732         ug = ug_create(NULL, "helloUG-efl", UG_MODE_FRAMEVIEW, NULL, &cbs);
733
734         return ug;
735 }
736 @endcode
737
738 <br>
739 <h2 class="pg">Send message</h2>
740
741 We provide API for sending message: <b>ug_send_message()</b>. When you send a message, you have to use bundle type data (see \ref bundle_PG "bundle programming guide").
742
743 \note <b>Prototype of ug_send_message():</b>
744 @code
745 int ug_send_message (struct ui_gadget *ug, bundle *msg);
746 @endcode
747
748 \warning After send your message, you have to release it using <b>bundle_free()</b> API.
749 @code
750 //example
751 bundle *b;
752
753 b = bundle_create();
754 if (!b)
755         return;
756
757         bundle_add(b, "name", "helloUG-efl");
758         bundle_add(b, "type", "test message");
759
760         //Send message
761         ug_send_message(ug b);
762
763         //release bundle
764         bundle_free(b);
765
766 @endcode
767
768 <br>
769 <h2 class="pg">Propagate event</h2>
770
771 If you are UI gadget developer who is trying to use UI gadgets, please skip this section. This section is for application developers who use UI gadgets.
772
773 We provide some APIs for event propagation: <b>ug_pause(), ug_resume(), and ug_send_event()</b>. <b>ug_pause()</b> and <b>ug_resume()</b> are used for task-managing. If the application is put into background, invoke <b>ug_pause()</b>, otherwise, if the application is brought to the foreground, invoke <b>ug_resume()</b>. <b>ug_send_event()</b> is used for system event: <i>low memory, low battery, language change, rotate portrait, rotate portrait upside-down, rotate landscape, and rotate landscape upside-down.</i>
774
775 \note <b>Prototype of ug_pause(), ug_resume(), and ug_send_event():</b>
776 @code
777 int ug_pause (void);
778 int ug_resume (void);
779 int ug_send_event (enum ug_event event);
780 @endcode
781
782 <br>
783 <h2 class="pg">Destroy all UI gadgets</h2>
784
785 If you are UI gadget developer who is trying to use UI gadgets, please skip this section. This section is for application developers who use UI gadgets.
786
787 When you terminate your application, destroy all UI gadgets using <b>ug_destroy_all()</b>.
788
789 \note <b>Prototype of ug_destroy_all: </b>
790 @code
791 int ug_destroy_all (void);
792 @endcode
793
794  * @}
795  */