2 #include "e_mod_main.h"
4 static E_Module *shot_module = NULL;
6 static E_Action *act = NULL;
7 static E_Int_Menu_Augmentation *maug = NULL;
8 static Ecore_Timer *timer = NULL;
9 static E_Win *win = NULL;
10 static Evas_Object *o_bg = NULL, *o_box = NULL, *o_content = NULL;
11 static Evas_Object *o_event = NULL, *o_img = NULL, *o_hlist = NULL;
12 static E_Manager *sman = NULL;
13 static E_Container *scon = NULL;
14 static int quality = 90;
15 static int screen = -1;
17 static Evas_Object *o_rectdim[MAXZONES] = { NULL };
18 static Evas_Object *o_radio_all = NULL;
19 static Evas_Object *o_radio[MAXZONES] = { NULL };
20 static Evas_Object *o_fsel = NULL;
21 static Evas_Object *o_label = NULL;
22 static Evas_Object *o_entry = NULL;
23 static unsigned char *fdata = NULL;
25 static Ecore_Con_Url *url_up = NULL;
26 static Eina_List *handlers = NULL;
27 static char *url_ret = NULL;
30 _win_delete_cb(E_Win *w __UNUSED__)
34 e_object_del(E_OBJECT(win));
40 _win_resize_cb(E_Win *w __UNUSED__)
42 evas_object_resize(o_bg, win->w, win->h);
46 _on_focus_cb(void *data __UNUSED__, Evas_Object *obj)
48 if (obj == o_content) e_widget_focused_object_clear(o_box);
49 else if (o_content) e_widget_focused_object_clear(o_content);
53 _key_down_cb(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event)
55 Evas_Event_Key_Down *ev = event;
57 if (!strcmp(ev->keyname, "Tab"))
59 if (evas_key_modifier_is_set(evas_key_modifier_get(e_win_evas_get(win)), "Shift"))
61 if (e_widget_focus_get(o_box))
63 if (!e_widget_focus_jump(o_box, 0))
65 e_widget_focus_set(o_content, 0);
66 if (!e_widget_focus_get(o_content))
67 e_widget_focus_set(o_box, 0);
72 if (!e_widget_focus_jump(o_content, 0))
73 e_widget_focus_set(o_box, 0);
78 if (e_widget_focus_get(o_box))
80 if (!e_widget_focus_jump(o_box, 1))
82 e_widget_focus_set(o_content, 1);
83 if (!e_widget_focus_get(o_content))
84 e_widget_focus_set(o_box, 1);
89 if (!e_widget_focus_jump(o_content, 1))
90 e_widget_focus_set(o_box, 1);
94 else if (((!strcmp(ev->keyname, "Return")) ||
95 (!strcmp(ev->keyname, "KP_Enter")) ||
96 (!strcmp(ev->keyname, "space"))))
98 Evas_Object *o = NULL;
100 if ((o_content) && (e_widget_focus_get(o_content)))
101 o = e_widget_focused_object_get(o_content);
103 o = e_widget_focused_object_get(o_box);
104 if (o) e_widget_activate(o);
109 _screen_change_cb(void *data __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info __UNUSED__)
114 EINA_LIST_FOREACH(scon->zones, l, z)
117 evas_object_color_set(o_rectdim[z->num], 0, 0, 0, 0);
118 else if (screen == (int)z->num)
119 evas_object_color_set(o_rectdim[z->num], 0, 0, 0, 0);
121 evas_object_color_set(o_rectdim[z->num], 0, 0, 0, 200);
126 _save_to(const char *file)
128 char *extn = strrchr(file, '.');
134 (_("Error - Unknown format"),
135 _("File has an unspecified extension.<br>"
136 "Please use '.jpg' or '.png' extensions<br>"
137 "only as other formats are not<br>"
138 "supported currently."));
141 if (!((!strcasecmp(extn, ".png")) ||
142 (!strcasecmp(extn, ".jpg")) ||
143 (!strcasecmp(extn, ".jpeg"))))
146 (_("Error - Unknown format"),
147 _("File has an unrecognized extension.<br>"
148 "Please use '.jpg' or '.png' extensions<br>"
149 "only as other formats are not<br>"
150 "supported currently."));
153 if (!strcasecmp(extn, ".png"))
154 snprintf(opts, sizeof(opts), "compress=%i", 9);
156 snprintf(opts, sizeof(opts), "quality=%i", quality);
159 evas_object_image_save(o_img, file, NULL, opts);
167 EINA_LIST_FOREACH(scon->zones, l, z)
169 if (screen == (int)z->num) break;
174 unsigned char *src, *dst, *s, *d;
177 o = evas_object_image_add(evas_object_evas_get(o_img));
178 evas_object_image_colorspace_set(o, EVAS_COLORSPACE_ARGB8888);
179 evas_object_image_alpha_set(o, EINA_FALSE);
180 evas_object_image_size_set(o, z->w, z->h);
181 src = evas_object_image_data_get(o_img, EINA_FALSE);
182 sstd = evas_object_image_stride_get(o_img);
183 dst = evas_object_image_data_get(o, EINA_TRUE);
184 dstd = evas_object_image_stride_get(o);
186 for (y = 0; y < z->h; y++)
188 s = src + (sstd * y) + (z->x * 4);
189 memcpy(d, s, z->w * 4);
192 evas_object_image_save(o, file, NULL, opts);
199 _file_select_ok_cb(void *data __UNUSED__, E_Dialog *dia)
203 file = e_widget_fsel_selection_path_get(o_fsel);
204 if (file) _save_to(file);
205 if (dia) e_util_defer_object_del(E_OBJECT(dia));
208 e_object_del(E_OBJECT(win));
214 _file_select_cancel_cb(void *data __UNUSED__, E_Dialog *dia)
216 if (dia) e_util_defer_object_del(E_OBJECT(dia));
219 e_object_del(E_OBJECT(win));
225 _win_save_cb(void *data __UNUSED__, void *data2 __UNUSED__)
231 dia = e_dialog_new(scon, "E", "_e_shot_fsel");
232 e_dialog_title_set(dia, _("Select screenshot save location"));
233 o = e_widget_fsel_add(dia->win->evas, "~/", "/", NULL, NULL,
238 e_widget_size_min_get(o, &mw, &mh);
239 e_dialog_content_set(dia, o, mw, mh);
240 e_dialog_button_add(dia, _("OK"), NULL,
241 _file_select_ok_cb, NULL);
242 e_dialog_button_add(dia, _("Cancel"), NULL,
243 _file_select_cancel_cb, NULL);
244 e_dialog_resizable_set(dia, 1);
245 e_win_centered_set(dia->win, 1);
252 Ecore_Event_Handler *h;
254 EINA_LIST_FREE(handlers, h) ecore_event_handler_del(h);
263 ecore_con_url_free(url_up);
266 ecore_con_url_shutdown();
270 _upload_ok_cb(void *data __UNUSED__, E_Dialog *dia)
272 // ok just hides dialog and does background upload
274 if (dia) e_util_defer_object_del(E_OBJECT(dia));
277 e_object_del(E_OBJECT(win));
284 _upload_cancel_cb(void *data __UNUSED__, E_Dialog *dia)
286 if (dia) e_util_defer_object_del(E_OBJECT(dia));
289 e_object_del(E_OBJECT(win));
295 _upload_data_cb(void *data __UNUSED__, int ev_type __UNUSED__, void *event)
297 Ecore_Con_Event_Url_Data *ev = event;
298 if (ev->url_con != url_up) return EINA_TRUE;
299 if ((o_label) && (ev->size < 1024))
301 char *txt = alloca(ev->size + 1);
303 memcpy(txt, ev->data, ev->size);
306 printf("GOT %i bytes: '%s'\n", ev->size, txt);
308 for (i = 0; i < ev->size; i++) printf("%02x.", ev->data[i]);
311 if (!url_ret) url_ret = strdup(txt);
316 n = malloc(strlen(url_ret) + ev->size + 1);
330 _upload_progress_cb(void *data __UNUSED__, int ev_type __UNUSED__, void *event)
332 Ecore_Con_Event_Url_Progress *ev = event;
333 if (ev->url_con != url_up) return EINA_TRUE;
338 snprintf(buf, sizeof(buf),
339 "Uploaded %1.1fKB / %1.1fKB",
341 ev->up.total / 1024);
342 e_widget_label_text_set(o_label, buf);
348 _upload_complete_cb(void *data __UNUSED__, int ev_type __UNUSED__, void *event)
350 Ecore_Con_Event_Url_Complete *ev = event;
351 if (ev->url_con != url_up) return EINA_TRUE;
352 if (ev->status != 200)
355 (_("Error - Upload Failed"),
356 _("Upload failed with status code:<br>"
362 if ((o_entry) && (url_ret))
363 e_widget_entry_text_set(o_entry, url_ret);
369 _win_share_cb(void *data __UNUSED__, void *data2 __UNUSED__)
377 if (quality == 100) snprintf(buf, sizeof(buf), "/tmp/e-shot-XXXXXX.png");
378 else snprintf(buf, sizeof(buf), "/tmp/e-shot-XXXXXX.jpg");
382 (_("Error - Can't create File"),
383 _("Cannot create temporary file:\n"
388 e_object_del(E_OBJECT(win));
396 e_object_del(E_OBJECT(win));
399 f = fopen(buf, "rb");
405 fseek(f, 0, SEEK_END);
414 if (fdata) free(fdata);
415 fdata = malloc(fsize);
422 if (fread(fdata, fsize, 1, f) != 1)
431 ecore_file_unlink(buf);
435 if (!ecore_con_url_init())
443 handlers = eina_list_append
444 (handlers, ecore_event_handler_add
445 (ECORE_CON_EVENT_URL_DATA, _upload_data_cb, NULL));
446 handlers = eina_list_append
447 (handlers, ecore_event_handler_add
448 (ECORE_CON_EVENT_URL_PROGRESS, _upload_progress_cb, NULL));
449 handlers = eina_list_append
450 (handlers, ecore_event_handler_add
451 (ECORE_CON_EVENT_URL_COMPLETE, _upload_complete_cb, NULL));
453 url_up = ecore_con_url_new("http://www.enlightenment.org/shot.php");
454 ecore_con_url_post(url_up, fdata, fsize, "application/x-e-shot");
456 dia = e_dialog_new(scon, "E", "_e_shot_share");
457 e_dialog_title_set(dia, _("Uploading screenshot"));
459 o = e_widget_list_add(dia->win->evas, 0, 0);
462 o = e_widget_label_add(dia->win->evas, _("Uploading ..."));
464 e_widget_list_object_append(ol, o, 0, 0, 0.5);
466 o = e_widget_label_add(dia->win->evas,
467 _("Screenshot is available at this location:"));
468 e_widget_list_object_append(ol, o, 0, 0, 0.5);
470 o = e_widget_entry_add(dia->win->evas, NULL, NULL, NULL, NULL);
472 e_widget_list_object_append(ol, o, 1, 0, 0.5);
474 e_widget_size_min_get(ol, &mw, &mh);
475 e_dialog_content_set(dia, ol, mw, mh);
476 e_dialog_button_add(dia, _("OK"), NULL, _upload_ok_cb, NULL);
477 e_dialog_button_add(dia, _("Cancel"), NULL, _upload_cancel_cb, NULL);
478 e_dialog_resizable_set(dia, 1);
479 e_win_centered_set(dia->win, 1);
484 _win_cancel_cb(void *data __UNUSED__, void *data2 __UNUSED__)
488 e_object_del(E_OBJECT(win));
494 _rect_down_cb(void *data __UNUSED__, Evas *e __UNUSED__, Evas_Object *obj __UNUSED__, void *event_info)
496 Evas_Event_Mouse_Down *ev = event_info;
500 if (ev->button != 1) return;
502 e_widget_radio_toggle_set(o_radio_all, 0);
503 EINA_LIST_FOREACH(scon->zones, l, z)
505 if (obj == o_rectdim[z->num])
508 e_widget_radio_toggle_set(o_radio[z->num], 1);
511 e_widget_radio_toggle_set(o_radio[z->num], 0);
514 EINA_LIST_FOREACH(scon->zones, l, z)
517 evas_object_color_set(o_rectdim[z->num], 0, 0, 0, 0);
518 else if (screen == (int)z->num)
519 evas_object_color_set(o_rectdim[z->num], 0, 0, 0, 0);
521 evas_object_color_set(o_rectdim[z->num], 0, 0, 0, 200);
526 _shot_now(E_Zone *zone)
529 Ecore_X_Window_Attributes att;
532 int bpl = 0, rows = 0, bpp = 0;
534 Evas_Object *o, *oa, *op, *ol;
536 Evas_Modifier_Mask mask;
539 sman = zone->container->manager;
540 scon = zone->container;
541 memset(&att, 0, sizeof(Ecore_X_Window_Attributes));
542 ecore_x_window_attributes_get(sman->root, &att);
543 img = ecore_x_image_new(sman->w, sman->h, att.visual, att.depth);
544 ecore_x_image_get(img, sman->root, 0, 0, 0, 0, sman->w, sman->h);
545 src = ecore_x_image_data_get(img, &bpl, &rows, &bpp);
546 if (!ecore_x_image_is_argb32_get(img))
548 dst = malloc(sman->w * sman->h * sizeof(int));
549 ecore_x_image_to_argb_convert(src, bpp, bpl, att.colormap, att.visual,
550 0, 0, sman->w, sman->h,
551 dst, (sman->w * sizeof(int)), 0, 0);
554 dst = (unsigned int *)src;
556 if (win) e_object_del(E_OBJECT(win));
557 win = e_win_new(e_container_current_get(e_manager_current_get()));
559 evas = e_win_evas_get(win);
560 e_win_title_set(win, _("Where to put Screenshot..."));
561 e_win_delete_callback_set(win, _win_delete_cb);
562 e_win_resize_callback_set(win, _win_resize_cb);
563 e_win_dialog_set(win, 1);
564 e_win_centered_set(win, 1);
565 e_win_name_class_set(win, "E", "_shot_dialog");
567 o = edje_object_add(evas);
569 e_theme_edje_object_set(o, "base/theme/dialog", "e/widgets/dialog/main");
570 evas_object_move(o, 0, 0);
573 o = e_widget_list_add(evas, 0, 0);
575 e_widget_size_min_get(o, &w, &h);
576 edje_extern_object_min_size_set(o, w, h);
577 edje_object_part_swallow(o_bg, "e.swallow.content", o);
581 if (w < 220) w = 220;
582 h = (w * sman->h) / sman->w;
584 o = e_widget_aspect_add(evas, w, h);
586 o = e_widget_preview_add(evas, w, h);
589 evas2 = e_widget_preview_evas_get(op);
591 o = evas_object_image_filled_add(evas2);
593 evas_object_image_colorspace_set(o, EVAS_COLORSPACE_ARGB8888);
594 evas_object_image_alpha_set(o, EINA_FALSE);
595 evas_object_image_size_set(o, sman->w, sman->h);
596 evas_object_image_data_copy_set(o, dst);
597 if (dst != (unsigned int *)src) free(dst);
598 ecore_x_image_free(img);
599 evas_object_image_data_update_add(o, 0, 0, sman->w, sman->h);
600 e_widget_preview_extern_object_set(op, o);
603 evas_object_show(op);
604 evas_object_show(oa);
606 e_widget_aspect_child_set(oa, op);
607 e_widget_list_object_append(o_content, oa, 0, 0, 0.5);
609 o = e_widget_list_add(evas, 1, 1);
612 o = e_widget_framelist_add(evas, _("Quality"), 0);
615 rg = e_widget_radio_group_new(&quality);
616 o = e_widget_radio_add(evas, _("Perfect"), 100, rg);
617 e_widget_framelist_object_append(ol, o);
618 o = e_widget_radio_add(evas, _("High"), 90, rg);
619 e_widget_framelist_object_append(ol, o);
620 o = e_widget_radio_add(evas, _("Medium"), 70, rg);
621 e_widget_framelist_object_append(ol, o);
622 o = e_widget_radio_add(evas, _("Low"), 50, rg);
623 e_widget_framelist_object_append(ol, o);
625 e_widget_list_object_append(o_hlist, ol, 1, 0, 0.5);
628 if (eina_list_count(scon->zones) > 1)
634 o = e_widget_framelist_add(evas, _("Screen"), 0);
637 rg = e_widget_radio_group_new(&screen);
638 o = e_widget_radio_add(evas, _("All"), -1, rg);
640 evas_object_smart_callback_add(o, "changed", _screen_change_cb, NULL);
641 e_widget_framelist_object_append(ol, o);
643 EINA_LIST_FOREACH(scon->zones, l, z)
647 if (z->num >= MAXZONES) continue;
648 snprintf(buf, sizeof(buf), "%i", z->num);
649 o = e_widget_radio_add(evas, buf, z->num, rg);
651 evas_object_smart_callback_add(o, "changed", _screen_change_cb, NULL);
652 e_widget_framelist_object_append(ol, o);
654 o = evas_object_rectangle_add(evas2);
655 evas_object_event_callback_add(o, EVAS_CALLBACK_MOUSE_DOWN,
656 _rect_down_cb, NULL);
657 o_rectdim[z->num] = o;
658 evas_object_color_set(o, 0, 0, 0, 0);
660 evas_object_geometry_get(o_img, NULL, NULL, &w, &h);
662 (z->x * w) / sman->w,
663 (z->y * h) / sman->h);
664 evas_object_resize(o,
665 (z->w * w) / sman->w,
666 (z->h * h) / sman->h);
670 e_widget_list_object_append(o_hlist, ol, 1, 0, 0.5);
673 e_widget_list_object_append(o_content, o_hlist, 0, 0, 0.5);
676 e_widget_size_min_get(o, &w, &h);
677 edje_extern_object_min_size_set(o, w, h);
678 edje_object_part_swallow(o_bg, "e.swallow.content", o);
681 ///////////////////////////////////////////////////////////////////////
683 o = e_widget_list_add(evas, 1, 1);
685 e_widget_on_focus_hook_set(o, _on_focus_cb, NULL);
686 edje_object_part_swallow(o_bg, "e.swallow.buttons", o);
688 o = e_widget_button_add(evas, _("Save"), NULL, _win_save_cb, win, NULL);
689 e_widget_list_object_append(o_box, o, 1, 0, 0.5);
690 o = e_widget_button_add(evas, _("Share"), NULL, _win_share_cb, win, NULL);
691 e_widget_list_object_append(o_box, o, 1, 0, 0.5);
692 o = e_widget_button_add(evas, _("Cancel"), NULL, _win_cancel_cb, win, NULL);
693 e_widget_list_object_append(o_box, o, 1, 0, 0.5);
696 e_widget_size_min_get(o, &w, &h);
697 edje_extern_object_min_size_set(o, w, h);
698 edje_object_part_swallow(o_bg, "e.swallow.buttons", o);
700 o = evas_object_rectangle_add(evas);
703 if (!evas_object_key_grab(o, "Tab", mask, ~mask, 0)) printf("grab err\n");
704 mask = evas_key_modifier_mask_get(evas, "Shift");
705 if (!evas_object_key_grab(o, "Tab", mask, ~mask, 0)) printf("grab err\n");
707 if (!evas_object_key_grab(o, "Return", mask, ~mask, 0)) printf("grab err\n");
709 if (!evas_object_key_grab(o, "KP_Enter", mask, ~mask, 0)) printf("grab err\n");
710 evas_object_event_callback_add(o, EVAS_CALLBACK_KEY_DOWN, _key_down_cb, NULL);
712 edje_object_size_min_calc(o_bg, &w, &h);
713 evas_object_resize(o_bg, w, h);
714 e_win_resize(win, w, h);
715 e_win_size_min_set(win, w, h);
716 e_win_size_max_set(win, 99999, 99999);
718 e_win_border_icon_set(win, "enlightenment/shot");
720 if (!e_widget_focus_get(o_bg)) e_widget_focus_set(o_box, 1);
724 _shot_delay(void *data)
734 if (timer) ecore_timer_del(timer);
735 timer = ecore_timer_add(1.0, _shot_delay, zone);
739 _e_mod_menu_cb(void *data __UNUSED__, E_Menu *m, E_Menu_Item *mi __UNUSED__)
741 if (m->zone) _shot(m->zone);
745 _e_mod_action_cb(E_Object *obj, const char *params __UNUSED__)
751 if (obj->type == E_MANAGER_TYPE)
752 zone = e_util_zone_current_get((E_Manager *)obj);
753 else if (obj->type == E_CONTAINER_TYPE)
754 zone = e_util_zone_current_get(((E_Container *)obj)->manager);
755 else if (obj->type == E_ZONE_TYPE)
756 zone = ((E_Zone *)obj);
758 zone = e_util_zone_current_get(e_manager_current_get());
760 if (!zone) zone = e_util_zone_current_get(e_manager_current_get());
764 ecore_timer_del(timer);
771 _e_mod_menu_add(void *data __UNUSED__, E_Menu *m)
775 mi = e_menu_item_new(m);
776 e_menu_item_label_set(mi, _("Take Screenshot"));
777 e_util_menu_item_theme_icon_set(mi, "screenshot");
778 e_menu_item_callback_set(mi, _e_mod_menu_cb, NULL);
782 EAPI E_Module_Api e_modapi =
784 E_MODULE_API_VERSION,
789 e_modapi_init(E_Module *m)
791 e_module_delayed_set(m, 1);
794 act = e_action_add("shot");
797 act->func.go = _e_mod_action_cb;
798 e_action_predef_name_set(_("Screen"), _("Take Screenshot"),
799 "shot", NULL, NULL, 0);
801 maug = e_int_menus_menu_augmentation_add_sorted
802 ("main/2", _("Take Screenshot"), _e_mod_menu_add, NULL, NULL, NULL);
807 e_modapi_shutdown(E_Module *m __UNUSED__)
812 e_object_del(E_OBJECT(win));
817 ecore_timer_del(timer);
822 e_int_menus_menu_augmentation_del("main/2", maug);
827 e_action_predef_name_del(_("Screen"), _("Take Screenshot"));
828 e_action_del("shot");
836 e_modapi_save(E_Module *m __UNUSED__)