summaryrefslogtreecommitdiff
path: root/src/bin
diff options
context:
space:
mode:
authorYakov Goldberg <yakov.g@samsung.com>2014-10-27 19:25:30 +0200
committerYakov Goldberg <yakov.g@samsung.com>2014-11-26 11:03:18 +0200
commitb0197f09cf94072b176769ecc6dab5c9e86dc3aa (patch)
tree811c130970786fbcd482bc906513e0e95523738f /src/bin
parent9ca8bd8b7bceb956d5edf847050bbaeb8c6f8263 (diff)
Start implementing DnD
Diffstat (limited to 'src/bin')
-rw-r--r--src/bin/egui_gui/CMakeLists.txt1
-rw-r--r--src/bin/egui_gui/dnd.c433
-rw-r--r--src/bin/egui_gui/dnd.h28
-rw-r--r--src/bin/egui_gui/editor.c660
-rw-r--r--src/bin/egui_gui/egui_logic.c17
-rw-r--r--src/bin/egui_gui/egui_logic_private.h1
6 files changed, 1115 insertions, 25 deletions
diff --git a/src/bin/egui_gui/CMakeLists.txt b/src/bin/egui_gui/CMakeLists.txt
index e44e2ab..8c6fe62 100644
--- a/src/bin/egui_gui/CMakeLists.txt
+++ b/src/bin/egui_gui/CMakeLists.txt
@@ -68,6 +68,7 @@ add_executable(${TARGET}
68 rmview.c 68 rmview.c
69 settings_view.c 69 settings_view.c
70 editor.c 70 editor.c
71 dnd.c
71 ) 72 )
72 73
73add_dependencies(${TARGET} erigo_cmd) 74add_dependencies(${TARGET} erigo_cmd)
diff --git a/src/bin/egui_gui/dnd.c b/src/bin/egui_gui/dnd.c
new file mode 100644
index 0000000..75b3e39
--- /dev/null
+++ b/src/bin/egui_gui/dnd.c
@@ -0,0 +1,433 @@
1
2#include <Eo.h>
3#include <Evas.h>
4#include <Ecore.h>
5#include "egui_log.h"
6#include "egui_layout.h"
7#include "gui_widget.h"
8
9typedef struct
10{
11 const char *data; /*DnD data*/
12 Eo *image; /* image for DnD icon. */
13 Eo *obj; /*object, where drag starts */
14} Drag_Info;
15
16typedef struct
17{
18 Ecore_Timer *tm;
19 Drag_Info *drag_info;
20} DnD_Info;
21
22typedef struct
23{
24 const Gui_Widget *wdg;
25 void (*drop_target_enter)(void *data, Evas_Object *obj);
26 void *enterdata;
27 void (*drop_target_leave)(void *data, Evas_Object *obj);
28 void *leavedata;
29 Elm_Drop_Cb drop_target_drop;
30 void *dropdata;
31 Elm_Drag_Pos drop_target_pos;
32 void *posdata;
33
34 Eo *obj; /* This obj is used only to properly call elm_drop_target_del() */
35 const Gui_Widget *drop_target;
36} Target_Info;
37
38#define TIME_TO_DRAG 0.1
39#define DND_IMAGE_SIZE 15
40#define DROP_TARGET "__drop_target__"
41
42static DnD_Info _dnd_info;
43
44
45const char*
46dnd_drag_data_get()
47{
48 return _dnd_info.drag_info->data;
49}
50
51static void
52_dragpos(void *data EINA_UNUSED, Eo * obj EINA_UNUSED, Evas_Coord x EINA_UNUSED, Evas_Coord y EINA_UNUSED, Elm_Xdnd_Action action EINA_UNUSED)
53{
54 //ERR("%s: %d %d", (char *) data, x, y);
55}
56
57static void
58_dragaccept(void *data EINA_UNUSED, Evas_Object *obj EINA_UNUSED, Eina_Bool doaccept EINA_UNUSED)
59{
60 //ERR("accept: %d", doaccept);
61}
62
63static void
64_dragstate(void *data EINA_UNUSED, Evas_Object *obj EINA_UNUSED)
65{
66 //ERR("%s", (char *) data);
67}
68
69/* This callback is called only for a window object.
70 * So Target_Info -> wdg is always Main Widget.
71 * Obj is not NULL only for Canvas, which can be also be a drop target. */
72static void
73_dropenter(void *data, Evas_Object *obj)
74{
75 Target_Info *ti = data;
76 ti->drop_target = ti->wdg;
77
78 if (ti->drop_target_enter)
79 ti->drop_target_enter(ti->enterdata, obj);
80}
81
82/* This callback is called only for a window object.
83 * So Target_Info -> wdg is always Main Widget.
84 * Obj is not NULL only for Canvas, which can be also be a drop target. */
85static void
86_dropleave(void *data, Evas_Object *obj)
87{
88 Target_Info *main_wdg_ti = data;
89
90 /* if ti->drop_target is not current main widget, then it means,
91 * that prev drop target, box for example wasn't leaved properly.
92 * For example moving mouse fast from one window to another will cause "jump".
93 * So need to call leave properly.
94 * */
95 if (main_wdg_ti->drop_target != main_wdg_ti->wdg)
96 {
97 Target_Info *ti = wdg_data_get(main_wdg_ti->drop_target, DROP_TARGET);
98 if (ti->drop_target_leave)
99 ti->drop_target_leave(ti->leavedata, obj);
100 }
101 main_wdg_ti->drop_target = NULL;
102
103 if (main_wdg_ti->drop_target_leave)
104 main_wdg_ti->drop_target_leave(main_wdg_ti->leavedata, obj);
105}
106
107static Eina_Bool
108_dropcb(void *data EINA_UNUSED, Evas_Object *obj, Elm_Selection_Data *ev)
109{
110 Target_Info *main_wdg_ti = data;
111 Target_Info *ti;
112 /* if drop_target == NULL, then we drop on MAIN CANVAS*/
113 if (main_wdg_ti->drop_target)
114 {
115 ti = wdg_data_get(main_wdg_ti->drop_target, DROP_TARGET);
116 }
117 else
118 {
119 ti = main_wdg_ti;
120 }
121
122 if (ti->drop_target_drop)
123 ti->drop_target_drop(ti->dropdata, obj, ev);
124 return EINA_TRUE;
125}
126
127static void
128_drop_target_iterate(Gui_Widget **drop_candidate, Gui_Session *session, Evas_Coord x, Evas_Coord y)
129{
130 Eina_Bool stop = EINA_TRUE;
131 Dep_Id *wdg_id;
132 Eo *o;
133 Evas_Coord ox, oy, ow, oh;
134
135 const Eina_List *lst, *l;
136 lst = wdg_children_list_get(*drop_candidate);
137 EINA_LIST_FOREACH(lst, l, wdg_id)
138 {
139 Gui_Widget *w = wdg_get(wdg_id);
140 if (!wdg_data_get(w, DROP_TARGET))
141 continue;
142 o = session_eo_get(session, w);
143 eo_do(o, evas_obj_position_get(&ox, &oy));
144 eo_do(o, evas_obj_size_get(&ow, &oh));
145 if (((x >= ox) && (x <= ox + ow)) &&
146 ((y >= oy) && (y <= oy + oh)))
147 {
148 *drop_candidate = w;
149 stop = EINA_FALSE;
150 }
151 }
152
153 if (!stop)
154 _drop_target_iterate(drop_candidate, session, x, y);
155}
156
157/* This callback is called every time for a window object.
158 * So Target_Info -> wdg is always Main Widget*/
159static void
160_droppos(void *data, Eo *obj, Evas_Coord x, Evas_Coord y, Elm_Xdnd_Action action)
161{
162 Target_Info *main_wdg_ti = data;
163 const Gui_Widget *wdg = main_wdg_ti->wdg;
164
165 /* For canvas only*/
166 if (!wdg)
167 {
168 ERR("drop target: MAIN CANVAS:: %d %d", x, y);
169 if (main_wdg_ti->drop_target_pos)
170 {
171 main_wdg_ti->drop_target_pos(main_wdg_ti->posdata, obj, x, y, action);
172 }
173 return;
174 }
175
176 ERR("drop target: %s:: %d %d", wdg_name_get(wdg), x, y);
177
178 Eo *wdg_eo, *iwin;
179 Evas_Coord p_x = 0, p_y = 0;
180 Evas_Coord iwin_x = 0, iwin_y = 0;
181 Gui_Widget *drop_candidate = (Gui_Widget *) wdg;
182
183 Gui_Session *session = (Gui_Session *) gui_context_editor_session_get(wdg_context_get(wdg));
184 wdg_eo = session_eo_get(session, wdg);
185 /* Usually main_wdg is win.
186 * But when it is not, need to get image of Editor win */
187 if (IS_WIN(wdg))
188 {
189 iwin = elm_win_inlined_image_object_get(wdg_eo);
190 }
191 else
192 {
193 Eo *main_obj_inlined_win_img = eo_do(wdg_eo, eo_key_data_get("__editor_win"));
194 iwin = elm_win_inlined_image_object_get(main_obj_inlined_win_img);
195 }
196 eo_do(iwin, evas_obj_position_get(&iwin_x, &iwin_y));
197
198 /* if p_x or p_y is < 0, but we inside this callback, drop to window*/
199 p_x = x - iwin_x;
200 p_y = y - iwin_y;
201 _drop_target_iterate(&drop_candidate, session, p_x, p_y);
202 ERR("Drop Candidate: %s", wdg_class_name_get(drop_candidate));
203
204 if (main_wdg_ti->drop_target != drop_candidate)
205 {
206 /* Call leave callback for previous target widget.
207 * If prev wdg is MainWdg, don't call leave. */
208 if (main_wdg_ti->drop_target != wdg)
209 {
210 Target_Info *ti = wdg_data_get(main_wdg_ti->drop_target, DROP_TARGET);
211 if (ti->drop_target_leave)
212 {
213 ti->drop_target_leave(ti->leavedata, NULL);
214 }
215 }
216
217 /* Call enter callback for new target widget.
218 * If new wdg is MainWdg, don't call enter. */
219 if (drop_candidate != wdg)
220 {
221 Target_Info *ti = wdg_data_get(drop_candidate, DROP_TARGET);
222 if (ti->drop_target_enter)
223 {
224 ti->drop_target_enter(ti->enterdata, NULL);
225 }
226 }
227 main_wdg_ti->drop_target = drop_candidate;
228 }
229
230 /* Need to calculate coord inside object */
231 if (drop_candidate != wdg)
232 {
233 wdg_eo = session_eo_get(session, drop_candidate);
234 Evas_Coord obj_x, obj_y;
235 eo_do(wdg_eo, evas_obj_position_get(&obj_x, &obj_y));
236 p_x = p_x - obj_x;
237 p_y = p_y - obj_y;
238 }
239
240 /* Simulate poscb inside drop candidate.
241 * Get callbacks from drop candidate and call. */
242 Target_Info *ti = wdg_data_get(drop_candidate, DROP_TARGET);
243 if (ti->drop_target_pos)
244 {
245 ti->drop_target_pos(ti->posdata, NULL, p_x, p_y, action);
246 }
247}
248
249static Evas_Object *
250_image_create_icon(void *data, Evas_Object *parent, Evas_Coord *xoff, Evas_Coord *yoff)
251{
252 Evas_Object *ic;
253 Evas_Object *io = data;
254 const char *f, *g;
255 Evas_Coord x, y, w, h, xm, ym;
256
257 elm_image_file_get(io, &f, &g);
258 ic = elm_image_add(parent);
259 elm_image_file_set(ic, f, g);
260 evas_object_geometry_get(io, &x, &y, &w, &h);
261 evas_object_move(ic, x, y);
262 evas_object_resize(ic, 40, 40);
263 evas_object_show(ic);
264
265 evas_pointer_canvas_xy_get(evas_object_evas_get(io), &xm, &ym);
266 if (xoff) *xoff = xm - 30;
267 if (yoff) *yoff = ym - 30;
268
269 return ic;
270}
271
272static Eina_Bool
273_drag_start(void *data)
274{
275 Drag_Info *di = data;
276 _dnd_info.tm = NULL;
277 _dnd_info.drag_info = di;
278 elm_drag_start(di->obj, ELM_SEL_FORMAT_TEXT,
279 di->data, ELM_XDND_ACTION_COPY,
280 _image_create_icon, di->image,
281 _dragpos, "drag",
282 _dragaccept, NULL,
283 _dragstate, "drag");
284 return ECORE_CALLBACK_CANCEL;
285}
286
287static Eina_Bool
288_drag_mouse_up(void *data EINA_UNUSED, Eo *obj, const Eo_Event_Description *desc EINA_UNUSED, void *event_info EINA_UNUSED)
289{
290 eo_do(obj, eo_event_callback_del(EVAS_OBJECT_EVENT_MOUSE_UP, _drag_mouse_up, NULL));
291 if (_dnd_info.tm)
292 {
293 ecore_timer_del(_dnd_info.tm);
294 _dnd_info.tm = NULL;
295 }
296 return EO_CALLBACK_CONTINUE;
297}
298
299static Eina_Bool
300_drag_mouse_down(void *data, Eo *obj, const Eo_Event_Description *desc EINA_UNUSED, void *event_info EINA_UNUSED)
301{
302 Drag_Info *di = data;
303 eo_do(obj, eo_event_callback_add(EVAS_OBJECT_EVENT_MOUSE_UP, _drag_mouse_up, NULL));
304
305 ecore_timer_del(_dnd_info.tm);
306 _dnd_info.tm = ecore_timer_add(TIME_TO_DRAG, _drag_start, di);
307 return EO_CALLBACK_CONTINUE;
308}
309
310static Eina_Bool
311_drag_data_free(void *data, Eo *obj EINA_UNUSED, const Eo_Event_Description *desc EINA_UNUSED, void *event_info EINA_UNUSED)
312{
313 Drag_Info *di = data;
314 free(di);
315 return EO_CALLBACK_CONTINUE;
316}
317
318void
319drag_add(Eo *obj, Eo *image, const char *data)
320{
321 Drag_Info *di = calloc(1, sizeof(Drag_Info));
322 di->image = image;
323 di->data = data;
324 di->obj = obj;
325 eo_do(obj, eo_event_callback_add(EVAS_OBJECT_EVENT_MOUSE_DOWN, _drag_mouse_down, di));
326 eo_do(obj, eo_event_callback_add(EVAS_OBJECT_EVENT_DEL, _drag_data_free, di));
327}
328
329static Target_Info*
330_target_info_new(Gui_Widget *wdg, Eo *obj)
331{
332 Target_Info *ti;
333
334 if (wdg)
335 {
336 ti = wdg_data_get(wdg, DROP_TARGET);
337 if (!ti)
338 {
339 ti = calloc(1, sizeof(Target_Info));
340 ti->wdg = wdg;
341 wdg_data_set(wdg, DROP_TARGET, ti);
342 }
343 }
344 else if (obj)
345 {
346 ti = eo_do(obj, eo_key_data_get(DROP_TARGET));
347 if (!ti)
348 {
349 ti = calloc(1, sizeof(Target_Info));
350 eo_do(obj, eo_key_data_set(DROP_TARGET, ti, NULL));
351 }
352 }
353 return ti;
354}
355
356void
357drop_target_wdg_set(Gui_Widget *wdg,
358 void (*drop_target_enter)(void *, Evas_Object *obj), void *enterdata,
359 void (*drop_target_leave)(void *, Evas_Object *obj), void *leavedata,
360 Elm_Drag_Pos drop_target_pos, void *posdata,
361 Elm_Drop_Cb drop_target_drop, void *dropdata)
362{
363 Target_Info *ti = _target_info_new(wdg, NULL);
364
365 ti->drop_target_enter = drop_target_enter;
366 ti->enterdata = enterdata;
367 ti->drop_target_leave = drop_target_leave;
368 ti->leavedata = leavedata;
369 ti->drop_target_pos = drop_target_pos;
370 ti->posdata = posdata;
371 ti->drop_target_drop = drop_target_drop;
372 ti->dropdata = dropdata;
373
374 /* if Elm DnD will work, call here elm_drop_target_add() for widget's Eo */
375}
376
377void
378drop_target_main_wdg_set(Gui_Widget *wdg, Eo *obj,
379 void (*drop_target_enter)(void *, Evas_Object *obj), void *enterdata,
380 void (*drop_target_leave)(void *, Evas_Object *obj), void *leavedata,
381 Elm_Drag_Pos drop_target_pos, void *posdata,
382 Elm_Drop_Cb drop_target_drop, void *dropdata)
383{
384 Target_Info *ti = _target_info_new(wdg, obj);
385 ti->obj = obj;
386
387 ti->drop_target_enter = drop_target_enter;
388 ti->enterdata = enterdata;
389 ti->drop_target_leave = drop_target_leave;
390 ti->leavedata = leavedata;
391 ti->drop_target_pos = drop_target_pos;
392 ti->posdata = posdata;
393 ti->drop_target_drop = drop_target_drop;
394 ti->dropdata = dropdata;
395
396 elm_drop_target_add(obj, ELM_SEL_FORMAT_TEXT,
397 _dropenter, ti,
398 _dropleave, ti,
399 _droppos, ti,
400 _dropcb, ti
401 );
402}
403
404void
405drop_target_wdg_del(Gui_Widget *wdg, Eo *obj)
406{
407 Target_Info *ti = NULL;
408
409 if (wdg)
410 {
411 ti = wdg_data_get(wdg, DROP_TARGET);
412 wdg_data_set(wdg, DROP_TARGET, NULL);
413 }
414 else if (obj)
415 {
416 ti = eo_do(obj, eo_key_data_get(DROP_TARGET));
417 eo_do(obj, eo_key_data_del(DROP_TARGET));
418 }
419
420 if (!ti) return;
421 /* call elm_drop_target_del() only for main objects, t.e. if obj exists. */
422 if (ti->obj)
423 {
424 elm_drop_target_del(ti->obj, ELM_SEL_FORMAT_TEXT,
425 _dropenter, ti,
426 _dropleave, ti,
427 _droppos, ti,
428 _dropcb, ti);
429 }
430 free(ti);
431}
432
433
diff --git a/src/bin/egui_gui/dnd.h b/src/bin/egui_gui/dnd.h
new file mode 100644
index 0000000..8f214b5
--- /dev/null
+++ b/src/bin/egui_gui/dnd.h
@@ -0,0 +1,28 @@
1
2#ifndef _DND_H
3#define _DND_H
4
5void
6drag_add(Eo *obj, Eo *image, const char *data);
7
8void
9drop_target_wdg_set(Gui_Widget *wdg,
10 void (*drop_target_enter)(void *, Evas_Object *obj), void *enterdata,
11 void (*drop_target_leave)(void *, Evas_Object *obj), void *leavedata,
12 Elm_Drag_Pos drop_target_pos, void *posdata,
13 Elm_Drop_Cb drop_target_drop, void *dropdata);
14
15void
16drop_target_main_wdg_set(Gui_Widget *wdg, Eo *obj,
17 void (*drop_target_enter)(void *, Evas_Object *obj), void *enterdata,
18 void (*drop_target_leave)(void *, Evas_Object *obj), void *leavedata,
19 Elm_Drag_Pos drop_target_pos, void *posdata,
20 Elm_Drop_Cb drop_target_drop, void *dropdata);
21
22void
23drop_target_wdg_del(Gui_Widget *wdg, Eo *obj);
24
25const char*
26dnd_drag_data_get();
27
28#endif
diff --git a/src/bin/egui_gui/editor.c b/src/bin/egui_gui/editor.c
index 9f1f322..d576a07 100644
--- a/src/bin/egui_gui/editor.c
+++ b/src/bin/egui_gui/editor.c
@@ -13,6 +13,8 @@
13#include "propview.h" 13#include "propview.h"
14#include "cbview.h" 14#include "cbview.h"
15 15
16#include "dnd.h"
17
16#include "gui_parser.h" 18#include "gui_parser.h"
17#include "egui_logic_private.h" 19#include "egui_logic_private.h"
18 20
@@ -29,6 +31,9 @@
29static void 31static void
30_editor_undo_redo_post(const Gui_Memento *memento); 32_editor_undo_redo_post(const Gui_Memento *memento);
31 33
34static void
35_wdg_parent_win_reload(const Gui_Widget *wdg);
36
32static Gui_Context *_active_ctx = NULL; 37static Gui_Context *_active_ctx = NULL;
33static const Egui_Layout_Widgets *g; 38static const Egui_Layout_Widgets *g;
34 39
@@ -1036,16 +1041,587 @@ _content_set(Gui_Session *session, const Gui_Widget *container, const Gui_Widget
1036 return ret; 1041 return ret;
1037} 1042}
1038 1043
1044/*********************************************************/
1045/************ DnD Functions ******************************/
1046/*********************************************************/
1047
1048#define EDITOR_DND_DATA "__EDITOR_DND_DATA__"
1049
1050typedef struct
1051{
1052 Eo *eo_cur;
1053
1054 Eina_Bool packed; /* Need this, because no API to check if object is packed into table
1055 and unpack causes error message. */
1056 int box_pack_idx;
1057
1058 int cell_part_x; /* Which fifth part of sell was selected*/
1059 int cell_part_y; /* Used in order to check if need to repack or not. */
1060
1061 int table_w; /* Table width/height. Calculate it once in the beginning. */
1062 int table_h;
1063
1064 int table_pack_x;
1065 int table_pack_y;
1066 Eina_List *table_borders;
1067}
1068DnD_Info;
1069
1070/* Draw border rectangles in table cells. */
1071static inline void
1072_table_borders_draw(Eo *table, int w, int h, Eina_List **_border_objects)
1073{
1074 Eina_List *border_objects = *_border_objects;
1075 int i = 0, j = 0;
1076 char path[100];
1077 getcwd(path, sizeof(path));
1078 sprintf(path, "%s/data/images/table_cell_border.png", path);
1079 Eo *o;
1080 EINA_LIST_FREE(border_objects, o)
1081 {
1082 eo_do(table, elm_obj_table_unpack(o));
1083 eo_del(o);
1084 }
1085 border_objects = NULL;
1086 for (i = w; i >= 0; i--)
1087 {
1088 for (j = h; j >= 0; j--)
1089 {
1090 o = eo_add(ELM_IMAGE_CLASS, table);
1091 eo_do(o, evas_obj_size_hint_weight_set(EVAS_HINT_EXPAND, EVAS_HINT_EXPAND),
1092 evas_obj_size_hint_align_set(EVAS_HINT_FILL, EVAS_HINT_FILL),
1093 evas_obj_visibility_set(EINA_TRUE),
1094 efl_file_set(path, NULL));
1095 eo_do(table, elm_obj_table_pack(o, i, j, 1, 1));
1096 border_objects = eina_list_append(border_objects, o);
1097 }
1098 }
1099 *_border_objects = border_objects;
1100}
1101
1102static void
1103_drop_target_main_wdg_enter(void *data, Evas_Object *obj)
1104{
1105 Eo *canvas_drop_target = obj;
1106 Eo *canvas = NULL;
1107 Gui_Widget *wdg = data;
1108 DnD_Info *di;
1109 /* If wdg == NULL, then canvas is a drop target or we have a error.*/
1110 if (wdg)
1111 {
1112 Gui_Session *session = (Gui_Session *) gui_context_editor_session_get(wdg_context_get(wdg));
1113 di = wdg_data_get(wdg_main_wdg_get(wdg), EDITOR_DND_DATA);
1114 canvas = session_eo_get(session, wdg);
1115 }
1116 else if (canvas_drop_target != NULL)
1117 {
1118 di = eo_do(canvas_drop_target, eo_key_data_get(EDITOR_DND_DATA));
1119 canvas = canvas_drop_target;
1120 }
1121 else
1122 {
1123 ERR("Drop target is wrong. If you see this message something is terribly wrong!");
1124 }
1125
1126 const Eo_Class* (*kl_func)();
1127 kl_func = db_class_func_get(dnd_drag_data_get());
1128 if (di->eo_cur) eo_del(di->eo_cur);
1129 di->eo_cur = eo_add(kl_func(), canvas);
1130 eo_do(di->eo_cur, evas_obj_size_set(80, 30));
1131 eo_do(di->eo_cur, evas_obj_size_hint_weight_set(EVAS_HINT_EXPAND, EVAS_HINT_EXPAND));
1132 eo_do(di->eo_cur, evas_obj_visibility_set(EINA_TRUE));
1133 eo_do(di->eo_cur, elm_obj_widget_part_text_set(NULL, dnd_drag_data_get()));
1134}
1135
1136static void
1137_drop_target_main_wdg_leave(void *data, Evas_Object *obj)
1138{
1139 Gui_Widget *wdg = data;
1140 Eo *canvas_drop_target = obj;
1141 DnD_Info *di;
1142 if (wdg)
1143 {
1144 di = wdg_data_get(wdg_main_wdg_get(wdg), EDITOR_DND_DATA);
1145 }
1146 else if (canvas_drop_target != NULL)
1147 {
1148 di = eo_do(canvas_drop_target, eo_key_data_get(EDITOR_DND_DATA));
1149 }
1150 else
1151 {
1152 ERR("Drop target is wrong. If you see this message something is terribly wrong!");
1153 }
1154
1155 eo_del(di->eo_cur);
1156 di->eo_cur = NULL;
1157}
1158
1159static void
1160_drop_target_enter(void *data, Evas_Object *obj EINA_UNUSED)
1161{
1162 Gui_Widget *wdg = data;
1163 Eo *wdg_eo = NULL;
1164 ERR("Enter: %s", wdg_name_get(wdg));
1165 DnD_Info *di = wdg_data_get(wdg_main_wdg_get(wdg), EDITOR_DND_DATA);
1166 if (!IS_MAIN(wdg))
1167 {
1168 Gui_Session *session = (Gui_Session *) gui_context_editor_session_get(wdg_context_get(wdg));
1169 wdg_eo = session_eo_get(session, wdg);
1170 }
1171 if (wdg_eo && !strcmp(wdg_class_name_get(wdg), DB_DEF_BOX_CLASS))
1172 {
1173 }
1174 else if (wdg_eo && !strcmp(wdg_class_name_get(wdg), DB_DEF_TABLE_CLASS))
1175 {
1176 Object_Container_Item *it;
1177 Eina_List *lst = wdg_obj_container_contents_list_get(wdg), *l;
1178 int maxw = 0, maxh = 0;
1179 EINA_LIST_FOREACH(lst, l, it)
1180 {
1181 Gui_Widget_Property *prop = obj_container_item_prop_get(it);
1182 int ix, iy, iw, ih;
1183 ix = INT_GET(prop_value_nth_get(prop, 1));
1184 iy = INT_GET(prop_value_nth_get(prop, 2));
1185 iw = INT_GET(prop_value_nth_get(prop, 3));
1186 ih = INT_GET(prop_value_nth_get(prop, 4));
1187 /* Calculating max number of cells vertically and horizontally. */
1188 if (ix + iw > maxw) maxw = ix + iw;
1189 if (iy + iy > maxh) maxh = iy + ih;
1190 }
1191 di->table_w = maxw;
1192 di->table_h = maxh;
1193 di->cell_part_x = -1;
1194 di->cell_part_y = -1;
1195 }
1196}
1197
1198static void
1199_drop_target_leave(void *data, Evas_Object *obj EINA_UNUSED)
1200{
1201 Gui_Widget *wdg = data;
1202 ERR("LEave: %s", wdg_name_get(wdg));
1203 DnD_Info *di = wdg_data_get(wdg_main_wdg_get(wdg), EDITOR_DND_DATA);
1204 Eo *wdg_eo = NULL;
1205 /* Coordinates of object relative to canvas. */
1206 if (!IS_MAIN(wdg))
1207 {
1208 Gui_Session *session = (Gui_Session *) gui_context_editor_session_get(wdg_context_get(wdg));
1209 wdg_eo = session_eo_get(session, wdg);
1210 }
1211 if (wdg_eo && !strcmp(wdg_class_name_get(wdg), DB_DEF_BOX_CLASS))
1212 {
1213 if (di->packed)
1214 {
1215 eo_do(wdg_eo, elm_obj_box_unpack(di->eo_cur));
1216 di->packed = EINA_FALSE;
1217 }
1218 }
1219 else if (wdg_eo && !strcmp(wdg_class_name_get(wdg), DB_DEF_TABLE_CLASS))
1220 {
1221 if (di->packed)
1222 {
1223 Eo *o;
1224 EINA_LIST_FREE(di->table_borders, o)
1225 {
1226 eo_do(wdg_eo, elm_obj_table_unpack(o));
1227 eo_del(o);
1228 }
1229 di->table_borders = NULL;
1230 eo_do(wdg_eo, elm_obj_table_unpack(di->eo_cur));
1231
1232 Gui_Session *session = (Gui_Session *) gui_context_editor_session_get(wdg_context_get(wdg));
1233 Eina_List *lst = wdg_obj_container_contents_list_get(wdg), *l;
1234 Object_Container_Item *it;
1235 EINA_LIST_FOREACH(lst, l, it)
1236 {
1237 Gui_Widget_Property *prop = obj_container_item_prop_get(it);
1238 int ix, iy, iw, ih;
1239 Dep_Id *dep_id;
1240 ix = INT_GET(prop_value_nth_get(prop, 1));
1241 iy = INT_GET(prop_value_nth_get(prop, 2));
1242 iw = INT_GET(prop_value_nth_get(prop, 3));
1243 ih = INT_GET(prop_value_nth_get(prop, 4));
1244 dep_id = DEP_ID_GET(prop_value_nth_get(prop, 0));
1245 Eo *c = session_eo_get(session, wdg_get(dep_id));
1246 eo_do(wdg_eo, elm_obj_table_pack(c, ix, iy, iw, ih));
1247 }
1248 di->packed = EINA_FALSE;
1249 }
1250 }
1251}
1252
1253static Gui_Widget*
1254_editor_factory_wdg_create(const char *class_name, const Gui_Widget *focused_wdg);
1255
1039static Eina_Bool 1256static Eina_Bool
1040_widget_del(Gui_Session *session, const Gui_Widget *wdg, void *data EINA_UNUSED) 1257_drop_target_drop(void *data, Evas_Object *obj, Elm_Selection_Data *ev)
1041{ 1258{
1042 Eo *o = session_eo_get(session, wdg); 1259 Gui_Widget *wdg = data;
1043 objtree_item_remove(wdg); 1260 Eo *canvas_drop_target = obj;
1044 session_wdg_existence_set(session, wdg, EINA_FALSE); 1261 DnD_Info *di;
1045 eo_del(o); 1262 if (wdg)
1263 {
1264 di = wdg_data_get(wdg_main_wdg_get(wdg), EDITOR_DND_DATA);
1265 }
1266 else if (canvas_drop_target != NULL)
1267 {
1268 di = eo_do(canvas_drop_target, eo_key_data_get(EDITOR_DND_DATA));
1269 }
1270 else
1271 {
1272 ERR("Drop target is wrong. If you see this message something is terribly wrong!");
1273 }
1274
1275 if (di->eo_cur) eo_del(di->eo_cur);
1276
1277 const char *drag_data = ev->data;
1278 Gui_Widget *new_wdg = _editor_factory_wdg_create(drag_data, wdg);
1279
1280 if (wdg && !strcmp(wdg_class_name_get(wdg), DB_DEF_BOX_CLASS))
1281 {
1282 /* Append content memento to the creation memento (which was created in _editor_factory_wdg_create()
1283 * in order to correctly manage internals. */
1284 Object_Container *_old_container, *_new_container;
1285 _old_container = (Object_Container *) wdg_obj_container_get(wdg);
1286 _new_container = obj_container_copy(_old_container);
1287
1288 Gui_Memento *memento_next = gui_memento_new(wdg_dep_id_get(wdg),
1289 MEMENTO_OBJ_CONTAINER_ITEM,
1290 _old_container, _new_container);
1291 gui_memento_append((Gui_Memento *) gui_context_current_memento_get(wdg_context_get(wdg)), memento_next);
1292 wdg_obj_container_unset(wdg);
1293 wdg_obj_container_set(wdg, _new_container);
1294
1295 const Op_Desc *op_desc = db_container_desc_op_desc_get(db_container_desc_get(wdg_class_name_get(wdg)), CONTAINER_PACK);
1296 Gui_Widget_Property *prop = prop_create_for_op(op_desc);
1297 Gui_Value *val = prop_value_nth_get(prop, 0);
1298 gui_value_name_id_set(val, GUI_TYPE_OBJECT, wdg_dep_id_get(new_wdg));
1299
1300 Object_Container_Item *ci = obj_container_item_new(prop, wdg_dep_id_get(new_wdg));
1301 wdg_obj_container_item_add(wdg, ci, di->box_pack_idx);
1302
1303 _wdg_parent_win_reload(new_wdg);
1304 _editor_wdg_selected_set(new_wdg);
1305 objtree_item_selected_set(new_wdg);
1306 }
1307 else if (wdg && !strcmp(wdg_class_name_get(wdg), DB_DEF_TABLE_CLASS))
1308 {
1309 Gui_Session *session = (Gui_Session *) gui_context_editor_session_get(wdg_context_get(wdg));
1310 Eo *wdg_eo = session_eo_get(session, wdg);
1311 Object_Container_Item *it;
1312
1313 Object_Container *_old_container, *_new_container;
1314 _old_container = (Object_Container *) wdg_obj_container_get(wdg);
1315 _new_container = obj_container_copy(_old_container);
1316
1317 Gui_Memento *memento_next = gui_memento_new(wdg_dep_id_get(wdg),
1318 MEMENTO_OBJ_CONTAINER_ITEM,
1319 _old_container, _new_container);
1320 gui_memento_append((Gui_Memento *) gui_context_current_memento_get(wdg_context_get(wdg)), memento_next);
1321
1322 Eina_List *old_lst = wdg_obj_container_contents_list_get(wdg);
1323 wdg_obj_container_unset(wdg);
1324 wdg_obj_container_set(wdg, _new_container);
1325
1326 /* Delete everythin in new_container */
1327 Eina_List *lst = wdg_obj_container_contents_list_get(wdg), *l, *l2;
1328 EINA_LIST_FOREACH_SAFE(lst, l, l2, it)
1329 {
1330 wdg_obj_container_item_remove(wdg, it);
1331 }
1332
1333 /* Iterate over old list and clreate new container items and properties.
1334 * Also get packing coordinates from Eo object and put it into property. */
1335 EINA_LIST_FOREACH(old_lst, l, it)
1336 {
1337 Gui_Widget_Property *prop = obj_container_item_prop_get(it);
1338 Gui_Widget_Property *new_prop = prop_copy(prop);
1339 int ix, iy, iw, ih;
1340 Dep_Id *dep_id = obj_container_item_dep_id_get(it);
1341 Eo *c = session_eo_get(session, wdg_get(dep_id));
1342 eo_do(wdg_eo, elm_obj_table_pack_get(c, &ix, &iy, &iw, &ih));
1343
1344 gui_value_int_set(prop_value_nth_get(new_prop, 1), ix);
1345 gui_value_int_set(prop_value_nth_get(new_prop, 2), iy);
1346
1347 Object_Container_Item *ci = obj_container_item_new(new_prop, dep_id);
1348 wdg_obj_container_item_add((Gui_Widget *) wdg, ci, -1);
1349 }
1350
1351 /* Add new element into the container */
1352 const Op_Desc *op_desc = db_container_desc_op_desc_get(db_container_desc_get(wdg_class_name_get(wdg)), CONTAINER_PACK);
1353 Gui_Widget_Property *prop = prop_create_for_op(op_desc);
1354
1355 gui_value_name_id_set(prop_value_nth_get(prop, 0), GUI_TYPE_OBJECT, wdg_dep_id_get(new_wdg));
1356 gui_value_int_set(prop_value_nth_get(prop, 1), di->table_pack_x);
1357 gui_value_int_set(prop_value_nth_get(prop, 2), di->table_pack_y);
1358 gui_value_int_set(prop_value_nth_get(prop, 3), 1);
1359 gui_value_int_set(prop_value_nth_get(prop, 4), 1);
1360
1361 Object_Container_Item *ci = obj_container_item_new(prop, wdg_dep_id_get(new_wdg));
1362 wdg_obj_container_item_add(wdg, ci, -1);
1363
1364 _wdg_parent_win_reload(new_wdg);
1365 _editor_wdg_selected_set(new_wdg);
1366 objtree_item_selected_set(new_wdg);
1367 }
1368
1046 return EINA_TRUE; 1369 return EINA_TRUE;
1047} 1370}
1048 1371
1372static void
1373_table_cell_segment_get(int x, int y, int cell_w, int cell_h, int *_part_x, int *_part_y)
1374{
1375 int pack_x = 0, pack_y = 0;
1376 int part_x = 0, part_y = 0;
1377 pack_x = x / cell_w;
1378 pack_y = y / cell_h;
1379 /* Detect in which third of the cell pointer is located.
1380 * 0 - first; 1 - second; 2 - third; */
1381 part_x = (x - pack_x * cell_w) / (cell_w * 1 / 5);
1382 part_y = (y - pack_y * cell_h) / (cell_h * 1 / 5);
1383
1384 if (_part_x) *_part_x = part_x;
1385 if (_part_y) *_part_y = part_y;
1386}
1387
1388
1389/* x, y - coordinates of pointers relative to droppable object. */
1390static void
1391_drop_target_pos(void *data, Eo *obj, Evas_Coord x, Evas_Coord y, Elm_Xdnd_Action action EINA_UNUSED)
1392{
1393 Eo *canvas_drop_target = obj;
1394 Gui_Widget *wdg = data;
1395 DnD_Info *di;
1396 Eo *wdg_eo;
1397 Evas_Coord obj_x = 0, obj_y = 0;
1398 /* If wdg == NULL, then canvas is a drop target or we have a error.*/
1399 ERR("pointer: %d %d", x ,y);
1400 Gui_Session *session = (Gui_Session *) gui_context_editor_session_get(wdg_context_get(wdg));
1401 if (wdg)
1402 {
1403 di = wdg_data_get(wdg_main_wdg_get(wdg), EDITOR_DND_DATA);
1404 wdg_eo = session_eo_get(session, wdg);
1405 if (!IS_MAIN(wdg))
1406 {
1407 eo_do(wdg_eo, evas_obj_position_get(&obj_x, &obj_y));
1408 }
1409 }
1410 else if (canvas_drop_target != NULL)
1411 {
1412 di = eo_do(canvas_drop_target, eo_key_data_get(EDITOR_DND_DATA));
1413 }
1414 else
1415 {
1416 ERR("Drop target is wrong. If you see this message something is terribly wrong!");
1417 }
1418
1419 if (!di->packed)
1420 eo_do(di->eo_cur, evas_obj_position_set(obj_x + x, obj_y + y));
1421
1422 if (wdg && !strcmp(wdg_class_name_get(wdg), DB_DEF_BOX_CLASS))
1423 {
1424 Eo *child, *candidate = NULL;
1425 int idx = 0;
1426 if (di->packed)
1427 eo_do(wdg_eo, elm_obj_box_unpack(di->eo_cur));
1428 Eina_List *box_chld = eo_do(wdg_eo, elm_obj_box_children_get()), *l;
1429 di->box_pack_idx = 0;
1430 EINA_LIST_FOREACH(box_chld, l, child)
1431 {
1432 Evas_Coord child_x, child_y, child_w, child_h;
1433 eo_do(child, evas_obj_position_get(&child_x, &child_y));
1434 eo_do(child, evas_obj_size_get(&child_w, &child_h));
1435
1436 Eina_Bool hor_box = eo_do(wdg_eo, elm_obj_box_horizontal_get());
1437
1438 /* Check box layout, cursor position and elements inside the box and
1439 * determine where to pack new object. */
1440 if ((hor_box && (x > (child_x + child_w / 2))) ||
1441 (!hor_box && (y > (child_y + child_h / 2))))
1442 {
1443 candidate = child;
1444 di->box_pack_idx = idx + 1;
1445 }
1446 idx++;
1447 }
1448 eina_list_free(box_chld);
1449 if (!candidate)
1450 {
1451 eo_do(wdg_eo, elm_obj_box_pack_start(di->eo_cur));
1452 }
1453 else
1454 {
1455 eo_do(wdg_eo, elm_obj_box_pack_after(di->eo_cur, candidate));
1456 }
1457 di->packed = EINA_TRUE;
1458 }
1459 if (wdg && !strcmp(wdg_class_name_get(wdg), DB_DEF_TABLE_CLASS))
1460 {
1461 Eina_List *lst = wdg_obj_container_contents_list_get(wdg), *l;
1462 Object_Container_Item *it;
1463 int cell_w = 0, cell_h = 0;
1464 int table_w = 0, table_h = 0;
1465 int pack_x = 0, pack_y = 0;
1466 int pointer_x_cell = 0, pointer_y_cell = 0;
1467 eo_do(wdg_eo, evas_obj_size_get(&table_w, &table_h));
1468
1469 cell_w = table_w / di->table_w;
1470 cell_h = table_h / di->table_h;
1471 pointer_x_cell = x / cell_w;
1472 pointer_y_cell = y / cell_h;
1473
1474 int part_x, part_y;
1475 _table_cell_segment_get(x, y, cell_w, cell_h, &part_x, &part_y);
1476
1477 Eina_Bool new_column = EINA_FALSE, new_line = EINA_FALSE;
1478 Eina_Bool new_cell_x = EINA_FALSE, new_cell_y = EINA_FALSE;
1479
1480 Eina_Bool repack = EINA_FALSE;
1481 /* Check if repacking is needed. */
1482 if (di->cell_part_x != part_x)
1483 {
1484 di->cell_part_x = part_x;
1485 repack = EINA_TRUE;
1486 }
1487 if (di->cell_part_y != part_y)
1488 {
1489 di->cell_part_y = part_y;
1490 repack = EINA_TRUE;
1491 }
1492
1493 if (repack)
1494 {
1495 switch (part_x)
1496 {
1497 case 0:
1498 {
1499 pack_x = pointer_x_cell;
1500 new_column = EINA_TRUE;
1501 break;
1502 }
1503 case 1:
1504 {
1505 pack_x = pointer_x_cell;
1506 new_cell_x = EINA_TRUE;
1507 break;
1508 }
1509 case 2:
1510 {
1511 pack_x = pointer_x_cell;
1512 break;
1513 }
1514 case 3:
1515 {
1516 pack_x = pointer_x_cell + 1;
1517 new_cell_x = EINA_TRUE;
1518 break;
1519 }
1520 case 4:
1521 {
1522 pack_x = pointer_x_cell + 1;
1523 new_column = EINA_TRUE;
1524 break;
1525 }
1526 }
1527 switch (part_y)
1528 {
1529 case 0:
1530 {
1531 pack_y = pointer_y_cell;
1532 new_line = EINA_TRUE;
1533 break;
1534 }
1535 case 1:
1536 {
1537 pack_y = pointer_y_cell;
1538 new_cell_y = EINA_TRUE;
1539 break;
1540 }
1541 case 2:
1542 {
1543 pack_y = pointer_y_cell;
1544 break;
1545 }
1546 case 3:
1547 {
1548 pack_y = pointer_y_cell + 1;
1549 new_cell_y = EINA_TRUE;
1550 break;
1551 }
1552 case 4:
1553 {
1554 pack_y = pointer_y_cell + 1;
1555 new_line = EINA_TRUE;
1556 break;
1557 }
1558 }
1559 int max_pack_x = pack_x, max_pack_y = pack_y;
1560
1561 /* Put objects to default places */
1562 if (di->packed)
1563 {
1564 eo_do(wdg_eo, elm_obj_table_unpack(di->eo_cur));
1565 EINA_LIST_FOREACH(lst, l, it)
1566 {
1567 Gui_Widget_Property *prop = obj_container_item_prop_get(it);
1568 int ix, iy, iw, ih;
1569 Dep_Id *dep_id;
1570 ix = INT_GET(prop_value_nth_get(prop, 1));
1571 iy = INT_GET(prop_value_nth_get(prop, 2));
1572 iw = INT_GET(prop_value_nth_get(prop, 3));
1573 ih = INT_GET(prop_value_nth_get(prop, 4));
1574 dep_id = DEP_ID_GET(prop_value_nth_get(prop, 0));
1575 Eo *c = session_eo_get(session, wdg_get(dep_id));
1576 eo_do(wdg_eo, elm_obj_table_pack_set(c, ix, iy, iw, ih));
1577 }
1578 }
1579
1580 /* Move elements if new one is packed before. */
1581 EINA_LIST_FOREACH(lst, l, it)
1582 {
1583 Gui_Widget_Property *prop = obj_container_item_prop_get(it);
1584 int ix, iy, iw, ih;
1585 Dep_Id *dep_id = DEP_ID_GET(prop_value_nth_get(prop, 0));
1586 Eo *c = session_eo_get(session, wdg_get(dep_id));
1587
1588 eo_do(wdg_eo, elm_obj_table_pack_get(c, &ix, &iy, &iw, &ih));
1589 max_pack_x = (max_pack_x < ix) ? ix : max_pack_x;
1590 max_pack_y = (max_pack_y < iy) ? iy : max_pack_y;
1591
1592 /* If need to add a column, move all elements which are on the right side of new column,
1593 * if need to add a cell, move elements which are on the right in current row. */
1594 if ((new_column && (ix >= pack_x)) ||
1595 (new_cell_x && (ix >= pack_x) && (iy == pack_y)))
1596 {
1597 eo_do(wdg_eo, elm_obj_table_pack_set(c, ix + 1, iy, iw, ih));
1598 max_pack_x = (max_pack_x < ix + 1) ? ix + 1 : max_pack_x;
1599 }
1600
1601 /* If need to add a row, move all elements which are lower then new row,
1602 * if need to add a cell, move elements which are lower in current column. */
1603 eo_do(wdg_eo, elm_obj_table_pack_get(c, &ix, NULL, NULL, NULL));
1604 if ((new_line && (iy >= pack_y)) ||
1605 (new_cell_y && (iy >= pack_y) && (ix == pack_x)))
1606 {
1607 eo_do(wdg_eo, elm_obj_table_pack_set(c, ix, iy + 1, iw, ih));
1608 max_pack_y = (max_pack_y < iy + 1) ? iy + 1 : max_pack_y;
1609 }
1610 }
1611
1612 /* Draw borders of the table. */
1613 _table_borders_draw(wdg_eo, max_pack_x, max_pack_y, &(di->table_borders));
1614
1615 eo_do(wdg_eo, elm_obj_table_pack(di->eo_cur, pack_x, pack_y, 1, 1));
1616 di->table_pack_x = pack_x;
1617 di->table_pack_y = pack_y;
1618 di->packed = EINA_TRUE;
1619 }
1620 }
1621}
1622
1623/*********************************************************/
1624
1049static Eina_Bool 1625static Eina_Bool
1050_widget_add(Gui_Session *session, const Gui_Widget *wdg, void *data) 1626_widget_add(Gui_Session *session, const Gui_Widget *wdg, void *data)
1051{ 1627{
@@ -1067,6 +1643,23 @@ _widget_add(Gui_Session *session, const Gui_Widget *wdg, void *data)
1067 eo_do(o, eo_event_callback_add(EVAS_OBJECT_EVENT_RESIZE, _wdg_resize, NULL)); 1643 eo_do(o, eo_event_callback_add(EVAS_OBJECT_EVENT_RESIZE, _wdg_resize, NULL));
1068 /* Add specific callbacks, related to UI. */ 1644 /* Add specific callbacks, related to UI. */
1069 session_eo_set(session, wdg, o); 1645 session_eo_set(session, wdg, o);
1646
1647 if (!strcmp(wdg_class_name_get(wdg), DB_DEF_BOX_CLASS))
1648 {
1649 drop_target_wdg_set((Gui_Widget *) wdg,
1650 _drop_target_enter, (void *) wdg,
1651 _drop_target_leave, (void *) wdg,
1652 _drop_target_pos, (void *) wdg,
1653 _drop_target_drop, (void *) wdg);
1654 }
1655 else if (!strcmp(wdg_class_name_get(wdg), DB_DEF_TABLE_CLASS))
1656 {
1657 drop_target_wdg_set((Gui_Widget *) wdg,
1658 _drop_target_enter, (void *) wdg,
1659 _drop_target_leave, (void *) wdg,
1660 _drop_target_pos, (void *) wdg,
1661 _drop_target_drop, (void *) wdg);
1662 }
1070 } 1663 }
1071 else 1664 else
1072 { 1665 {
@@ -1097,6 +1690,7 @@ _widget_add(Gui_Session *session, const Gui_Widget *wdg, void *data)
1097 { 1690 {
1098 Evas_Coord x, y, x_par, y_par; 1691 Evas_Coord x, y, x_par, y_par;
1099 fr = eo_add(ELM_FRAME_CLASS, parent_win); 1692 fr = eo_add(ELM_FRAME_CLASS, parent_win);
1693
1100 /* This frame does not have any smart as parent. So in order to show menu above the frame, 1694 /* This frame does not have any smart as parent. So in order to show menu above the frame,
1101 * we add this frame as a member of smart object. */ 1695 * we add this frame as a member of smart object. */
1102 1696
@@ -1112,7 +1706,6 @@ _widget_add(Gui_Session *session, const Gui_Widget *wdg, void *data)
1112 main_wdg_info_frame_set(wi, fr); 1706 main_wdg_info_frame_set(wi, fr);
1113 wdg_data_set(wdg, MAIN_WDG_INFO, wi); 1707 wdg_data_set(wdg, MAIN_WDG_INFO, wi);
1114 1708
1115
1116 //evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); 1709 //evas_object_size_hint_weight_set(fr, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
1117 //evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL); 1710 //evas_object_size_hint_align_set(fr, EVAS_HINT_FILL, EVAS_HINT_FILL);
1118 const char *fr_title = wdg_name_get(wdg); 1711 const char *fr_title = wdg_name_get(wdg);
@@ -1129,6 +1722,15 @@ _widget_add(Gui_Session *session, const Gui_Widget *wdg, void *data)
1129 eo_do(fr, eo_key_data_set("winwdg", wdg, NULL)); 1722 eo_do(fr, eo_key_data_set("winwdg", wdg, NULL));
1130 } 1723 }
1131 fr = main_wdg_info_frame_get(wi); 1724 fr = main_wdg_info_frame_get(wi);
1725
1726 DnD_Info *di = calloc (1, sizeof(DnD_Info));
1727 wdg_data_set(wdg, EDITOR_DND_DATA, di);
1728 drop_target_main_wdg_set((Gui_Widget *) wdg, fr,
1729 _drop_target_main_wdg_enter, (void *) wdg,
1730 _drop_target_main_wdg_leave, (void *) wdg,
1731 _drop_target_pos, (void *) wdg,
1732 _drop_target_drop, (void *) wdg);
1733
1132 eo_do(fr, evas_obj_visibility_set(EINA_TRUE)); 1734 eo_do(fr, evas_obj_visibility_set(EINA_TRUE));
1133 eo_do(win, eo_key_data_set("__editor_frame", fr, NULL)); 1735 eo_do(win, eo_key_data_set("__editor_frame", fr, NULL));
1134 elm_object_content_set(fr, iwin); 1736 elm_object_content_set(fr, iwin);
@@ -1168,6 +1770,25 @@ _widget_add(Gui_Session *session, const Gui_Widget *wdg, void *data)
1168 return EINA_TRUE; 1770 return EINA_TRUE;
1169} 1771}
1170 1772
1773static Eina_Bool
1774_widget_del(Gui_Session *session, const Gui_Widget *wdg, void *data EINA_UNUSED)
1775{
1776 Eo *o = session_eo_get(session, wdg);
1777 objtree_item_remove(wdg);
1778 session_wdg_existence_set(session, wdg, EINA_FALSE);
1779
1780 DnD_Info *di = wdg_data_get(wdg, EDITOR_DND_DATA);
1781 if (di)
1782 {
1783 free(di);
1784 wdg_data_set(wdg, EDITOR_DND_DATA, NULL);
1785 }
1786
1787 drop_target_wdg_del((Gui_Widget *) wdg, NULL);
1788 eo_del(o);
1789 return EINA_TRUE;
1790}
1791
1171/* Remove only Eo objects or also widgets*/ 1792/* Remove only Eo objects or also widgets*/
1172static Eina_Bool 1793static Eina_Bool
1173_editor_layout_clear(const Gui_Context *ctx) 1794_editor_layout_clear(const Gui_Context *ctx)
@@ -1615,6 +2236,13 @@ _editor_undo_redo_post(const Gui_Memento *memento)
1615 } 2236 }
1616 case MEMENTO_WIDGET: 2237 case MEMENTO_WIDGET:
1617 { 2238 {
2239 Gui_Widget *head_memento_wdg = wdg_get(gui_memento_wdg_get(memento));
2240 if (head_memento_wdg)
2241 {
2242 _wdg_parent_win_reload(head_memento_wdg);
2243 _editor_wdg_selected_set(head_memento_wdg);
2244 objtree_item_selected_set(head_memento_wdg);
2245 }
1618 break; 2246 break;
1619 } 2247 }
1620 case MEMENTO_NONE: 2248 case MEMENTO_NONE:
@@ -1694,7 +2322,7 @@ _editor_selected_wdg_del_cb()
1694 _editor_wdg_selected_set(parent_wdg); 2322 _editor_wdg_selected_set(parent_wdg);
1695} 2323}
1696 2324
1697static void 2325static Gui_Widget*
1698_editor_factory_wdg_create(const char *class_name, const Gui_Widget *focused_wdg) 2326_editor_factory_wdg_create(const char *class_name, const Gui_Widget *focused_wdg)
1699{ 2327{
1700 const Gui_Widget *parent_win = NULL; 2328 const Gui_Widget *parent_win = NULL;
@@ -1706,7 +2334,7 @@ _editor_factory_wdg_create(const char *class_name, const Gui_Widget *focused_wdg
1706 if (!ctx) 2334 if (!ctx)
1707 { 2335 {
1708 ERR("No active context"); 2336 ERR("No active context");
1709 return; 2337 return NULL;
1710 } 2338 }
1711 2339
1712 char *new_name = gui_context_free_name_get(ctx, class_name); 2340 char *new_name = gui_context_free_name_get(ctx, class_name);
@@ -1804,11 +2432,17 @@ _editor_factory_wdg_create(const char *class_name, const Gui_Widget *focused_wdg
1804 manager_widget_create(session, mmenu, MODE_EDITOR, NULL); 2432 manager_widget_create(session, mmenu, MODE_EDITOR, NULL);
1805 manager_widget_configure(session, mmenu, MODE_EDITOR, NULL); 2433 manager_widget_configure(session, mmenu, MODE_EDITOR, NULL);
1806 } 2434 }
2435 return wdg;
1807} 2436}
1808 2437
1809void 2438void
1810editor_shutdown() 2439editor_shutdown()
1811{ 2440{
2441 DnD_Info *di = eo_do(g->main_win->canvas_bg, eo_key_data_get(EDITOR_DND_DATA));
2442 eo_do(g->main_win->canvas_bg, eo_key_data_del(EDITOR_DND_DATA));
2443 free(di);
2444 drop_target_wdg_del(NULL, g->main_win->canvas_bg);
2445
1812 target_db_shutdown(); 2446 target_db_shutdown();
1813 proplayout_shutdown(); 2447 proplayout_shutdown();
1814 objtree_shutdown(); 2448 objtree_shutdown();
@@ -2873,7 +3507,6 @@ editor_init(GuiLogicCbs *_guilogic_cbs)
2873 _guilogic_cbs->_layout_clear = _editor_layout_clear; 3507 _guilogic_cbs->_layout_clear = _editor_layout_clear;
2874 _guilogic_cbs->_editor_ctx_call = _editor_ctx_call; 3508 _guilogic_cbs->_editor_ctx_call = _editor_ctx_call;
2875 _guilogic_cbs->_editor_selected_wdg_del_cb = _editor_selected_wdg_del_cb; 3509 _guilogic_cbs->_editor_selected_wdg_del_cb = _editor_selected_wdg_del_cb;
2876 _guilogic_cbs->_editor_factory_wdg_create = _editor_factory_wdg_create;
2877 _guilogic_cbs->_editor_selected_wdg_get = _editor_wdg_selected_get; 3510 _guilogic_cbs->_editor_selected_wdg_get = _editor_wdg_selected_get;
2878 _guilogic_cbs->_project_close = _project_close; 3511 _guilogic_cbs->_project_close = _project_close;
2879 _guilogic_cbs->_project_new = _project_new; 3512 _guilogic_cbs->_project_new = _project_new;
@@ -2882,5 +3515,14 @@ editor_init(GuiLogicCbs *_guilogic_cbs)
2882 proplayout_init(); 3515 proplayout_init();
2883 target_db_init(); 3516 target_db_init();
2884 ecore_idle_enterer_add(_wdg_border_draw_on_idle, NULL); 3517 ecore_idle_enterer_add(_wdg_border_draw_on_idle, NULL);
3518
3519 DnD_Info *di = calloc (1, sizeof(DnD_Info));
3520 eo_do(g->main_win->canvas_bg, eo_key_data_set(EDITOR_DND_DATA, di, NULL));
3521 drop_target_main_wdg_set(NULL, g->main_win->canvas_bg,
3522 _drop_target_main_wdg_enter, NULL,
3523 _drop_target_main_wdg_leave, NULL,
3524 _drop_target_pos, NULL,
3525 _drop_target_drop, NULL
3526 );
2885} 3527}
2886 3528
diff --git a/src/bin/egui_gui/egui_logic.c b/src/bin/egui_gui/egui_logic.c
index 344d4be..4e3e003 100644
--- a/src/bin/egui_gui/egui_logic.c
+++ b/src/bin/egui_gui/egui_logic.c
@@ -16,6 +16,7 @@
16#include "simulator.h" 16#include "simulator.h"
17#include "ffi_glue.h" 17#include "ffi_glue.h"
18#include "target.h" 18#include "target.h"
19#include "dnd.h"
19 20
20/*FIXME: remove this include */ 21/*FIXME: remove this include */
21#include "objtree.h" 22#include "objtree.h"
@@ -383,19 +384,6 @@ _event(void *data EINA_UNUSED, Evas_Object *obj EINA_UNUSED, Evas_Object *src EI
383} 384}
384#endif 385#endif
385 386
386Eina_Bool
387_on_factory_item_down(void *data, Eo *obj EINA_UNUSED, const Eo_Event_Description *desc EINA_UNUSED, void *event_info EINA_UNUSED)
388{
389 const char *class_name = data;
390 _guilogic_cbs->_editor_factory_wdg_create(class_name,
391 _guilogic_cbs->_editor_selected_wdg_get());
392 return EO_CALLBACK_CONTINUE;
393}
394
395#define FACTORY_CB_ADD(obj1, obj2) eo_do((obj1), eo_event_callback_add(EVAS_OBJECT_EVENT_MOUSE_DOWN, _on_factory_item_down, eo_class_name_get(eo_class_get((obj2)))));
396
397#define FACTORY_CB_ADD_NAME(obj1, name) eo_do((obj1), eo_event_callback_add(EVAS_OBJECT_EVENT_MOUSE_DOWN, _on_factory_item_down, (name)));
398
399static void 387static void
400_factory_vertical_pack(Eina_Bool vertical_pack); 388_factory_vertical_pack(Eina_Bool vertical_pack);
401 389
@@ -746,8 +734,6 @@ static void
746_factory_item_finalize(Eo *item_box, char *image_name, char *egui_class_name) 734_factory_item_finalize(Eo *item_box, char *image_name, char *egui_class_name)
747{ 735{
748 if (!item_box) return; 736 if (!item_box) return;
749 /* Add MOUSE_DOWN callback to factory widget. */
750 FACTORY_CB_ADD_NAME(item_box, egui_class_name);
751 evas_object_size_hint_align_set(item_box, 0, EVAS_HINT_FILL); 737 evas_object_size_hint_align_set(item_box, 0, EVAS_HINT_FILL);
752 738
753 Eina_List *lst = elm_box_children_get(item_box); 739 Eina_List *lst = elm_box_children_get(item_box);
@@ -757,6 +743,7 @@ _factory_item_finalize(Eo *item_box, char *image_name, char *egui_class_name)
757 char path[100] = {'\0'}; 743 char path[100] = {'\0'};
758 sprintf(path, "%s/images/%s", PACKAGE_DATA_DIR, image_name); 744 sprintf(path, "%s/images/%s", PACKAGE_DATA_DIR, image_name);
759 eo_do(o, efl_file_set(path, NULL)); 745 eo_do(o, efl_file_set(path, NULL));
746 drag_add(item_box, o, egui_class_name);
760 747
761 eina_list_free(lst); 748 eina_list_free(lst);
762} 749}
diff --git a/src/bin/egui_gui/egui_logic_private.h b/src/bin/egui_gui/egui_logic_private.h
index 6651ca1..0f72498 100644
--- a/src/bin/egui_gui/egui_logic_private.h
+++ b/src/bin/egui_gui/egui_logic_private.h
@@ -11,7 +11,6 @@ typedef struct
11 Eina_Bool (*_layout_clear)(const Gui_Context *ctx); 11 Eina_Bool (*_layout_clear)(const Gui_Context *ctx);
12 Eina_Bool (*_editor_ctx_call)(const Gui_Context *ctx); 12 Eina_Bool (*_editor_ctx_call)(const Gui_Context *ctx);
13 void (*_editor_selected_wdg_del_cb)(); 13 void (*_editor_selected_wdg_del_cb)();
14 void (*_editor_factory_wdg_create)(const char *class_name, const Gui_Widget *focused_wdg);
15 const Gui_Widget *(*_editor_selected_wdg_get)(); 14 const Gui_Widget *(*_editor_selected_wdg_get)();
16 15
17 void (*_project_close)(const Gui_Context *ctx); 16 void (*_project_close)(const Gui_Context *ctx);